www.pudn.com > wimax_ofdm_implementation_code.rar > pseudo_channel.c
/*****************************************************************************/
/* FIle Name : pseudo_channel.c */
/* Description : Wi-Max SC Pseudo Channel Estimatitor */
/* mode : [3] 1:step 0:bilinear interpolation */
/* : [1:0] 0:drift both in freq & time domain */
/* : [1:0] 1:drift only in freq_domain */
/* multi : number of multiple paths */
/* level : White Noise level 0:-120dB@peak 6:-114dB...120:0dB*/
/* tx_freqerr : Transmitter's Frequency error */
/* : 0:0ppm 1:0.01ppm -10:-0.1ppm(-0.1<=f<=0.1ppm)*/
/* rx_freqerr : Receiver's Frequency error */
/* : 0:0ppm 1:0.01ppm -10:-0.1ppm(-0.1<=f<=0.1ppm)*/
/* author : miffie */
/* Date : oct/20/05 */
/* Copyright (c) 2005 miffie All rights reserved. */
/*****************************************************************************/
//In Wi-MAX SC the SS's clock is locked to BS.
//And only allowed 1ppm of clock frequecny error.
struct complexset pseudo_channel(struct complexset datain,
char mode, char multi, char level,
char tx_freqerr, char rx_freqerr ) {
int ii,kk ;
int size ;
int tmp0 ;
int startpoint ;
double tx_clock, rx_clock ;
double tx_carrierclock, rx_carrierclock ;
double tx_phase, rx_phase ;
double rx_time ;
struct complex *top ;
struct complex *cdata ;
struct complex tmp1, tmp2 , tmp3;
int tx_floor , tx_ceil ;
struct complexset ctop ;
double white ;
char NO_NOISE = 0 ;
static double sample_period = 125 ; //ns //8MHz
static double carrier_period = 0.1 ; //ns //10GHz
static int delay = 60 ; //ns
PRINTF("pseudo_channel size=%d multi=%d level=%d tx_freqerr=%d rx_freqerr=%d\n",
datain.size , multi, level, tx_freqerr, rx_freqerr) ;
if (mode<4) { //doubler
tx_clock = (sample_period/2.0)*(1.0+(tx_freqerr/100000000.0)) ; //ns
rx_clock = (sample_period)*(1.0+(rx_freqerr/100000000.0)) ; //ns
size = (datain.size/2) +32 ; //+32 for extention
} //doubler
else { //single
tx_clock = (sample_period)*(1.0+(tx_freqerr/100000000.0)) ; //ns
rx_clock = (sample_period)*(1.0+(rx_freqerr/100000000.0)) ; //ns
size = datain.size +32 ; //+32 for extention
} //single
tx_carrierclock = carrier_period*(1.0+(tx_freqerr/100000000.0)) ; //ns
rx_carrierclock = carrier_period*(1.0+(rx_freqerr/100000000.0)) ; //ns
//noises
NO_NOISE = (multi==0) && (level==0) ; //if 1 NO Noise
white = pow(2, ((double)level-120.0)/6.0) ; //WhiteNoiseGain
//sampling clock width
if (((top = (struct complex *)malloc(size*sizeof(struct complex)) ) == NULL) |
((cdata = (struct complex *)malloc((datain.size+200)*sizeof(struct complex)) ) == NULL)){
PRINTF( " malloc failed in pseudo_channel.c\n") ;
} //fail
else { //allocated
//initialize
for( ii=0;ii=1) rx_time += delay - gamma_random(delay) ;
} //NO_NOISE
//rotation
if(kk==0) { //first path's gain is fixed
tmp3.realp = 1.0 ;
tmp3.image = 0 ;
} else { //second path and beyond
tmp3.realp = ((double)int_random(8)+8)/32.0 ;
tmp3.image = ((double)int_random(8)+8)/32.0 ;
tmp3.realp = (int_random(2)) ? -tmp3.realp : tmp3.realp ;
tmp3.image = (int_random(2)) ? -tmp3.image : tmp3.image ;
}
printf("rx_time %8.5f r=%8.5f i=%8.5f\n" , rx_time , tmp3.realp , tmp3.image) ;
for( ii=0;ii