📄 stfa_ics.c
字号:
} else { private->buffer_rx = 0; } private->buffer_tx = swr_malloc( MAX_BUFFER_SIZE ); if ( !( private->buffer_rx || ( private->nbr_stfa % 2 ) ) || !private->buffer_tx ) { PR_DBG( 0, "Couldn't allocate all necessary memory for the DMA!\n" "Aborting! This is SERIOUS\n" ); return -1; } memset( private->buffer_tx, 0, MAX_BUFFER_SIZE ); if ( private->buffer_rx ){ memset( private->buffer_rx, 0, MAX_BUFFER_SIZE ); } // Setting up the antenna-parameters i = swr_ant_get_rx_tx_delay( private->nbr_stfa ); PR_DBG( 4, "Rx-tx delay is %i\n", i ); private->rx_tx_delay_blocks = i / DAQ_DMA_BLOCK_SIZE_BYTES; private->rx_tx_delay_bytes = i % DAQ_DMA_BLOCK_SIZE_BYTES; //Tell the antenna that we transmitt complex data// swr_ant_set_is_complex( private->ant_index, 1 );// PR_DBG( 4, "antenna %i is told to transmitt complex data \n",// private->ant_index ); // Now we can begin initialising things depending on private-> stats->blocks_per_slot = 0; stats->slots_per_frame = 0; stats->frame_count = 0; stats->rx.data = private->buffer_rx; stats->rx.type = SIG_SYMBOL_COMPLEX_S32; stats->tx.data = private->buffer_tx; stats->tx.type = SIG_SYMBOL_COMPLEX; // Initialise the slots for ( i=0; i < MAX_SLOTS; i++ ) { port_in(i).data = 0; port_in(i).size = 0; port_in(i).flags = SWR_PORT_OWN_MALLOC; port_out(i).data = 0; port_out(i).size = 0; port_out(i).flags = SWR_PORT_OWN_MALLOC; // And initialise the notice-queues private->notice_sdb[i] = -1; private->notice_f[i] = NULL; } // This is only valid with the old RF-cards! private->attn_tx = private->attn_rx = config->attn_tx = config->attn_rx = 0; swr_ant_set_attn( private->ant_index, config->attn_rx, config->attn_tx); swr_sdb_free_stats_struct( context->id, (void**)&stats ); swr_sdb_free_config_struct( context->id, (void**)&config ); return 0;}/** * The initialisation with regard to the slots and frame is quite complex, * so it's outsourced... */int init_slots_frame( swr_sdb_t *context, config_t *config, stats_t *stats ) { if ( private->running ) { PR_DBG( 0, "Can't change slot/frame parameters while running!\n" ); return -1; } if ( config->slots_per_frame <= config->slot_send_offset ) { PR_DBG( 0, "Can't ask to build a slot more than 1 frame in advance.\n" "Offending assertion: slots_per_frame(%i) <= slot_send_offset(%i)\n", config->slots_per_frame, config->slot_send_offset ); return -1; } if ( config->slots_per_frame * config->blocks_per_slot <= private->rx_tx_delay_blocks ) { PR_DBG( 0, "There are less blocks in the frame (%i) than the delay between\n" "the reception and transmission (%i). Aborting\n", config->slots_per_frame * config->blocks_per_slot, private->rx_tx_delay_blocks ); return -1; } // Update the stats (for others) and private (for us) parameters private->slots_per_frame = stats->slots_per_frame = config->slots_per_frame; private->blocks_per_slot = stats->blocks_per_slot = config->blocks_per_slot; private->slot_bytes = private->blocks_per_slot * DAQ_DMA_BLOCK_SIZE_BYTES; private->len_frame_blocks = private->blocks_per_slot * private->slots_per_frame; private->dma_bytes = private->slot_bytes * private->slots_per_frame; // And tell the antenna what we're doing PR_DBG( 3, "Slot-length: %i\n", private->blocks_per_slot ); swr_ant_set_slot_len( private->nbr_stfa, private->blocks_per_slot ); if ( private->buffer_rx ){ swr_ant_set_frame_params( private->nbr_stfa, DMA_BEGIN_RX, DMA_BEGIN_TX ); } // Put the right length for outside viewers. We want to show the whole // frame including the two buffer-spaces, this is the reason for the // + 2 * private->slot_bytes // For the moment, channel 1 and 2 are mixed in stats->rx, because // of the behaviour of the 554's stats->rx.size = 2 * ( private->dma_bytes + 2 * private->slot_bytes ) / DAQ_BYTES_PER_QI_SAMPLE; stats->tx.size = ( private->dma_bytes + 2 * private->slot_bytes ) / DAQ_BYTES_PER_QI_SAMPLE; // Some debugging info (more to come ;-) PR_DBG( 2, "Buffer size:%i*%i*block_size=%i tx@%p-%p and rx@%p-%p\n", private->slots_per_frame, private->blocks_per_slot, private->len_frame_blocks * private->slot_bytes, private->buffer_tx, DMA_BEGIN_TX, private->buffer_rx, DMA_BEGIN_RX ); return 0;}/** * Every time somebody from the outside changes a configuration value, * this function is called just before the working-function */int spc_reconfig( swr_sdb_t *context ) { config_t *config; int ret = 0, slot, offset_samples; stats_t *stats; INIT_WATCH(4); swr_sdb_get_config_struct( context->id, (void**)&config ); swr_sdb_get_stats_struct( context->id, (void**)&stats ); // RF-reconfiguration if(config->freq != private->freq || config->side != private->side){ swr_ant_ch_set_synth( private->ant_index, 0, config->freq, config->side); private->freq=config->freq; private->side=config->side; } if ( config->freq_diff != private->freq_diff ){ swr_ant_ch_set_freq_diff( private->ant_index, config->freq_diff ); private->freq_diff = config->freq_diff; } if(config->attn_rx != private->attn_rx || config->attn_tx != private->attn_tx){ swr_ant_set_attn( private->ant_index, config->attn_rx, config->attn_tx); private->attn_rx=config->attn_rx; private->attn_tx=config->attn_tx; } if(config->tx != private->tx ){ swr_ant_ch_tx_enable( private->ant_index, config->tx); private->tx=config->tx; } // If there is another STFA in the chain, contact it private->stfa_id = config->stfa_id; if( private->stfa_id >= 0 ){ PR_DBG( 4, "Putting values to %i\n", config->stfa_id ); if ( !( private->nbr_stfa % 2 ) ){ PR_DBG( 3, "Passing buffer_rx @ %p\n", private->buffer_rx ); swr_sdb_set_config_pointer( -config->stfa_id, "buffer_rx", private->buffer_rx ); } swr_sdb_set_config_int( -config->stfa_id, "slot_send_offset", config->slot_send_offset ); swr_sdb_set_config_int( -config->stfa_id, "offset_chips_rcv", config->offset_chips_rcv ); swr_sdb_set_config_int( -config->stfa_id, "offset_samples_rcv", config->offset_samples_rcv ); swr_sdb_set_config_int( -config->stfa_id, "offset_samples_send", config->offset_samples_send ); swr_sdb_set_config_int( -config->stfa_id, "slots_per_frame", config->slots_per_frame ); swr_sdb_set_config_int( -config->stfa_id, "blocks_per_slot", config->blocks_per_slot ); swr_sdb_set_config_int( -config->stfa_id, "guard_period_chips", config->guard_period_chips ); swr_sdb_set_config_int( -config->stfa_id, "attn_tx", config->attn_tx ); swr_sdb_set_config_int( -config->stfa_id, "attn_rx", config->attn_rx ); swr_sdb_set_config_int( -config->stfa_id, "side", config->side ); swr_sdb_set_config_int( -config->stfa_id, "tx", config->tx ); swr_sdb_set_config_int( -config->stfa_id, "freq", config->freq ); // This config-call will update the other stfa swr_sdb_set_config_int( config->stfa_id, "freq_diff", config->freq_diff ); WATCH_CLOCK( "Set up other stfas\n" ); } if ( private->nbr_stfa % 2 ){ if ( config->buffer_rx ){ PR_DBG( 3, "Getting buffer_rx at %p\n", config->buffer_rx ); private->buffer_rx = config->buffer_rx; } stats->rx.data = private->buffer_rx; } if ( config->slots_per_frame && config->blocks_per_slot ) { if ( ( config->slots_per_frame != private->slots_per_frame ) || ( config->blocks_per_slot != private->blocks_per_slot ) ) { PR_DBG( 2, "spf: %i->%i, bps: %i->%i\n", private->slots_per_frame, config->slots_per_frame, private->blocks_per_slot, config->blocks_per_slot ); if ( init_slots_frame( context, config, stats ) < 0 ) { PR_DBG( 0, "Couldn't set new slot/frame-parameters!\n" ); return -1; } WATCH_CLOCK( "Set up init_slots_frame" ); } } // Re-calculate the internal offsets stats->offset_chips = config->offset_chips_rcv; offset_samples = config->offset_chips_rcv * DAQ_QI_SAMPLES_PER_CHIP + config->offset_samples_rcv; if ( offset_samples != stats->offset_samples ){ PR_DBG( 4, "New offset samples: %i\n", offset_samples ); stats->offset_samples = offset_samples; } private->sso = config->slot_send_offset; private->offset_rcv_bytes = ( offset_samples % DAQ_DMA_BLOCK_SIZE_QI_SAMPLES ) * DAQ_BYTES_PER_QI_SAMPLE; private->offset_rcv_blocks = offset_samples / DAQ_DMA_BLOCK_SIZE_QI_SAMPLES; private->offset_send_bytes = config->offset_samples_send * DAQ_BYTES_PER_QI_SAMPLE; swr_ant_adjust_offset( private->nbr_stfa, private->offset_rcv_blocks ); private->guard_period_bytes = config->guard_period_chips * DAQ_QI_SAMPLES_PER_CHIP * DAQ_BYTES_PER_QI_SAMPLE; WATCH_CLOCK( "Re-calculated offsets" ); // Fill in the slots, the guard-period is after the // slot. for ( slot=0; slot<private->slots_per_frame; slot++ ) { unsigned int data_size; data_size = ( private->slot_bytes - private->guard_period_bytes ) / DAQ_BYTES_PER_QI_SAMPLE;; port_in(slot).data = private->buffer_tx + BUFFER_OFFSET_TX( slot ); port_in(slot).size = data_size; port_out(slot).data = private->buffer_rx + BUFFER_OFFSET_RX( slot ); port_out(slot).size = data_size; } WATCH_CLOCK( "Set up ports" ); if ( config->attn_tx != private->attn_tx ){ private->attn_tx = config->attn_tx; swr_ant_set_attn_tx( private->nbr_stfa, private->attn_tx ); } if (config->attn_rx != private->attn_rx ){ private->attn_rx = config->attn_rx; swr_ant_set_attn_rx( private->nbr_stfa, private->attn_rx ); } WATCH_CLOCK( "Set up rf-cards" ); swr_sdb_free_stats_struct( context->id, (void**)&stats ); swr_sdb_free_config_struct( context->id, (void**)&config ); WATCH_CLOCK( "Finished" ); return ret;}/** * The main working function. Here is decided what to do with the * requests from the ANT-module, which module to inform aso. */void spc_slot( swr_sdb_t *context, swr_ant_notify_t *notify ) { stats_t *stats; int slot_send, slot_rcv, b; // private->sso is the send-slot-offset, so how many slots // we have to calculate in advance slot_send = ( notify->slots + private->sso ) % private->slots_per_frame; slot_rcv = ( notify->slots + private->slots_per_frame - 2 ) % private->slots_per_frame; PR_DBG( 4, "STFA(%i) send/rcv: %8x:%8x\n", private->nbr_stfa, BUFFER_OFFSET_RX( slot_rcv ), BUFFER_OFFSET_TX( slot_send ) ); if ( !( private->nbr_stfa % 2 ) ){ // DMA_RX of channel 1 and 2 is common, so only do it in // even stfa's (even stfa's drive odd ones) // Arrange some wrap-arounds for the reception-part. // Copy the end of the rx-buffer to the beginning, if necessary b = DMA_OFFSET_RX( slot_rcv ) - TX2RX( private->slot_bytes / 2 ); if ( b < 0 ) { void *c = DMA_BEGIN_RX + b; memcpy( c, c + TX2RX( private->dma_bytes ), -b ); } else { b = DMA_OFFSET_RX( slot_rcv ) +
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -