#include <stdio.h>
#include <stdlib.h>
#include <math.h>
#include "Setting.H"
#include "RS.H"
#include "Function.H"
#include "FrameOfdm.H"
WordType TxSymbolMark = 0; /* Indicates the symbol index in
* SrcToChan()
*/
WordType TxBitMark = 0; /* Indicates the bit index of a
* symbol in SrcToChan()
*/
WordType RxPosMark = 0; /* Indicates the received bit
* index in ChanToSrc()
*/
extern WordType FrameTx; /* Indicates transmitted subframe
* number
*/
extern WordType FrameRx; /* Indicates received subframe
* number
*/
extern float DataBuffer[NullSampleSize / 2 + NullSampleSize + SymbolSize * 3];
/* Processed data buffer in
* FindFrame()
*/
DType OriInforTx[52]; /* Data buffer for the input of
* channel encoder;
* Data is converted from source
* coded information by SrcToChan()
*/
WordType OriInforRx[3 * SrcVector]; /* Data buffer for the output of
* channel decoder;
* Data is converted from demodulated
* information by ChanToSrc()
*/
DType RefPhaseTx[UsedCarrier]; /* Buffer for transmit reference
* phase
*/
float RefPhaseRx[UsedCarrier]; /* Buffer for received reference
* phase
*/
unsigned int Seed = 101; /* Initial seed of Random() */
WordType Transmit(short SourceCode[], short FinalData[])
{
WordType i, k;
//float j;
DType ChannelData[RSTotalSym];
DType ConvData[UsedCarrier * SymPerFrame];
int TmpDataR[FFTSize], TmpDataI[FFTSize];
/* Convert SrcVector bits to required data mode (RSInforBit bits per symbol) */
SrcToChan(SourceCode, OriInforTx, &TxSymbolMark, &TxBitMark);
/* Proceed RS coding and OFDM when all information symbols arrive */
/* Get the available data */
if (TxSymbolMark > (RSInforSym - 2))
{
/* First part of 5 source coded frames */
if (TxSymbolMark > (RSInforSym - 1))
{
for (i = 0; i < RSInforSym; i++)
{
ChannelData[i] = OriInforTx[i];
}
for (i = RSInforSym; i <= TxSymbolMark; i++)
{
OriInforTx[i - RSInforSym] = OriInforTx[i];
}
TxSymbolMark -= RSInforSym;
}
/* Second part of 5 source coded frames */
else
{
for (i = 0; i < RSInforSym; i++)
{
ChannelData[i] = OriInforTx[i];
}
TxSymbolMark = 0;
TxBitMark = 0;
}
/* RS encoding */
Encode_RS(&ChannelData[0], &ChannelData[RSInforSym]);
/* Proceed OFDM below */
if (FrameTx == TotalFrame) /* First subframe of OFDM */
{
FrameTx = 1;
/* Add NullSampleSize padded zero */
for (i = 0; i < NullSampleSize; i++)
{
FinalData[i] = 0;
}
k = NullSampleSize;
/* Two additive lines for frame synchronization & reference phase */
/* Add frame synchronization below in time waveform */
for (i = 0; i < UsedCarrier; i++)
{
RefPhaseTx[i] = (DType) Random(&Seed, 3);
}
for (i = 0; i < FFTSize; i++)
{
if ((i > CarrierJumpPos - 2) && (i < CarrierJumpPos + UsedCarrier - 1))
{
switch (RefPhaseTx[i + 1 - CarrierJumpPos])
{
case 0: TmpDataR[i] = 16384; TmpDataI[i] = 0; break; //2^14
case 1: TmpDataR[i] = 0; TmpDataI[i] = 16384; break;
case 2: TmpDataR[i] = -16384; TmpDataI[i] = 0; break;
case 3: TmpDataR[i] = 0; TmpDataI[i] = -16384;
}
}
else
{
TmpDataR[i] = 0;
TmpDataI[i] = 0;
}
}
for (i = 1; i < FFTSize; i += 2)
{
TmpDataR[i] = 0;
TmpDataI[i] = 0;
}
FFT(TmpDataR, TmpDataI, -1);
for (i = GuardTimeSize; i > 0; i--)
{
FinalData[k] = (short)(TmpDataR[FFTSize - i]) ;
k++;
}
for (i = 0; i < FFTSize; i++)
{
FinalData[k] = (short)(TmpDataR[i]);
k++;
}
/* Add reference phase below in time waveform */
for (i = 0; i < UsedCarrier; i++)
{
RefPhaseTx[i] = (DType) Random(&Seed, 3);
}
for (i = 0; i < FFTSize; i++)
{
if ((i > CarrierJumpPos - 2) && (i < CarrierJumpPos + UsedCarrier - 1))
{
switch (RefPhaseTx[i + 1 - CarrierJumpPos])
{
case 0: TmpDataR[i] = 16384; TmpDataI[i] = 0; break;
case 1: TmpDataR[i] = 0; TmpDataI[i] = 16384; break;
case 2: TmpDataR[i] = -16384; TmpDataI[i] = 0; break;
case 3: TmpDataR[i] = 0; TmpDataI[i] = -16384;
}
}
else
{
TmpDataR[i] = 0;
TmpDataI[i] = 0;
}
}
FFT(TmpDataR, TmpDataI, -1);
for (i = GuardTimeSize; i > 0; i--)
{
FinalData[k] = (short)(TmpDataR[FFTSize - i]);
k++;
}
for (i = 0; i < FFTSize; i++)
{
FinalData[k] = (short)(TmpDataR[i]);
k++;
}
/* Adjust amplitude of frame synchronization & reference phase */
/* j = 0;
for (i = k - 2 * SymbolSize; i < k; i++)
{
if (j < (float)fabs(FinalData[i]))
{
j = (float)fabs(FinalData[i]);
}
}
for (i = k - 2 * SymbolSize; i < k; i++)
{
FinalData[i] *= (float) (0.95 / j);
}*/
}
else
{
FrameTx++;
k = 0;
}
/* Convert the data base to CodewordBit */
ConvBase(ChannelData, ConvData, RSTotalSym, 1);
ConvData[UsedCarrier * SymPerFrame -1] = 0;
/* Change to Gray code */
Gray2(ConvData, RSTotalSym * RSInforBit / CodewordBit);
/* OFDM modulation */
OFDMModu(ConvData, &FinalData[k], RefPhaseTx);
/* Adjust amplitude of transmit data */
/* j = 0;
for (i = k; i < k + SymbolSize * SymPerFrame; i++)
{
if (j < (float)fabs(FinalData[i]))
{
j = (float)fabs(FinalData[i]);
}
}
for (i = k; i < k + SymbolSize * SymPerFrame; i++)
{
FinalData[i] *= (float) (0.95 / j);
}*/
for(i = 0; i < k + SymbolSize * SymPerFrame; i++)
FinalData[i] = FinalData[i] & 0xffe0;
return (k + SymbolSize * SymPerFrame);
}
else
{
return 0;
}
}
WordType Receive(float RecData[], short SourceCode[])
{
WordType i, k;
DType ChanCodeData[RSTotalSym];
DType ConvData[UsedCarrier * SymPerFrame];
float TmpDataR[FFTSize], TmpDataI[FFTSize];
if (FrameRx == TotalFrame)
{
FrameRx = 1;
/* Two additive lines for frame synchronization & reference phase */
/* Remove NullSampleSize padded zero & frame synchronization below */
k = SymbolSize;
/* Get reference phase below */
for (i = 0; i < FFTSize; i++)
{
TmpDataR[i] = RecData[k + GuardTimeSize];
TmpDataI[i] = 0;
k++;
}
k += GuardTimeSize; /* Adjust the address access point */
FFT(TmpDataR, TmpDataI, 1);
for (i = CarrierJumpPos - 1; i < CarrierJumpPos + UsedCarrier - 1; i++)
{
RefPhaseRx[i - CarrierJumpPos + 1] =
(float) atan2((double)(TmpDataI[i]), (double)(TmpDataR[i]));
if (RefPhaseRx[i - CarrierJumpPos + 1] < 0)
{
RefPhaseRx[i - CarrierJumpPos + 1] += (float)(PI * 2);
}
}
}
else
{
FrameRx++;
k = 0;
}
/* OFDM modulation */
OFDMDemo(&RecData[k], ConvData, RefPhaseRx);
/* Change to Gray code */
Gray2(ConvData, RSTotalSym * RSInforBit / CodewordBit);
/* Convert the data base to CodewordBit */
ConvBase(ConvData, ChanCodeData, RSTotalSym * RSInforBit / CodewordBit, 0);
/* RS decoding */
i = Decode_RS(ChanCodeData);
/* Convert RS data to required data mode (SrcVector bits per frame) */
ChanToSrc(ChanCodeData, OriInforRx, &RxPosMark);
/* Decompress the source data */
if (RxPosMark < (3 * SrcVector - 1))
{
for (i = 0; i < (2 * SrcVector); i++)
{
SourceCode[i] = OriInforRx[i];
}
for (i = (2 * SrcVector); i < RxPosMark; i++)
{
OriInforRx[i