Synchronize and Demodulate Oversampled Waveform
This example shows how to synchronize, demodulate an oversampled IEEE® 802.11be™ (Wi-Fi™ 7) waveform consisting of extremely high-throughput (EHT) format packets. Processing the oversampled waveform at the receiver front end avoids the complication of designing a downsampling filter. In this example you:
Generate an oversampled EHT waveform for a sequence of bits.
Pass the waveform through a TGax fading channel.
Synchronize and demodulate the waveform using front-end processing functions.
Recover bits from the EHT-Data field and compare them to the bits you transmitted.
Packet Configuration
Use the EHT format configuration object, wlanEHTMUConfig
, to configure the transmission properties of an EHT packet. This example configures an EHT waveform for a 320 MHz channel bandwidth.
chanBW = "CBW320"; cfg = wlanEHTMUConfig(chanBW); cfg.GuardInterval = 0.8; %Guard interval in microseconds cfg.User{1}.APEPLength = 10000; %APEP length in bytes cfg.User{1}.MCS = 7;
Waveform Generation
Specify an oversampling factor of two.
osf = 2;
Specify seed 0
for the random number generator. Get the PSDU length of the configuration in bytes.
rng(0); psdu = psduLength(cfg);
Generate a random sequence of data bits for the configuration. Use these bits with the wlanWaveformGenerator
function to generate an oversampled time-domain waveform for the configuration.
data = randi([0 1],psdu*8,1); % Multiply by 8 to convert from bytes to bits
txWaveform = wlanWaveformGenerator(data,cfg,OversamplingFactor=osf);
Obtain and display the baseband sampling rate of the waveform. It is twice the channel bandwidth because the oversampling factor is two.
sr = wlanSampleRate(cfg,OversamplingFactor=osf);
disp(sr) %Sample rate in Hz
640000000
Channel and Noise
Create a wlanTGaxChannel
System object™, specifying its sample rate as the baseband sampling rate.
chan = wlanTGaxChannel; chan.DelayProfile = "Model-A"; chan.NumTransmitAntennas = cfg.NumTransmitAntennas; chan.NumReceiveAntennas = cfg.NumTransmitAntennas; chan.ChannelBandwidth = chanBW; chan.SampleRate = sr; chan.RandomStream = "mt19937ar with seed";
Append zeros at the start and end of the waveform to compensate for the delay that the channel filter introduces.
txWaveform = [zeros(50,1);txWaveform;zeros(100,1)];
Pass the waveform through the channel and add AWGN with a signal-to-noise ratio of 40 dB.
chanOut = chan(txWaveform); snrVal = 40; rxWaveform = awgn(chanOut,snrVal,0);
Front-End Processing
Get field indices for the configuration and the packet offset of the waveform, specifying the oversampling factor.
ind = wlanFieldIndices(cfg,OversamplingFactor=osf); pktOffset = wlanPacketDetect(rxWaveform,chanBW,OversamplingFactor=osf);
Extract the length of the waveform. Check that:
The output of the
wlanPacketDetect
function is nonempty.The gap between the start of the preamble and the end of the L-SIG field is smaller than the size of the whole waveform.
If either of these conditions are false, the wlanPacketDetect
function has not successfully detected a packet.
rxWaveLen = size(rxWaveform,1); % Adjust packet offset if isempty(pktOffset) || (pktOffset + ind.LSIG(2) > rxWaveLen) error("** No packet detected **"); end
Extract the part of the waveform that corresponds to the legacy short training field (L-STF). Use the L-STF to perform coarse frequency offset estimation. Use the estimate with the frequencyOffset
function to correct the offset.
rxLSTF = rxWaveform(pktOffset+(ind.LSTF(1):ind.LSTF(2)), :); coarseFreqOffset = wlanCoarseCFOEstimate(rxLSTF,chanBW,OversamplingFactor=osf); rxWaveform = frequencyOffset(rxWaveform,sr,-coarseFreqOffset);
Extract the part of the waveform that corresponds to the L-STF, legacy long training field (L-LTF), and legacy signaling (L-SIG) field. Use the wlanSymbolTimingEstimate
function to get the timing offset of the packet. Combine the timing offset with the packet offset.
searchBufferLLTF = rxWaveform(pktOffset+(ind.LSTF(1):ind.LSIG(2)),:); timeOffset = wlanSymbolTimingEstimate(searchBufferLLTF,chanBW,OversamplingFactor=osf); pktOffset = pktOffset + timeOffset;
Extract the part of the waveform that corresponds to the L-LTF. Use the L-LTF to perform fine frequency offset estimation. Use the estimate with the frequencyOffset
function to correct the offset.
rxLLTF = rxWaveform(pktOffset+(ind.LLTF(1):ind.LLTF(2)),:); fineFreqOffset = wlanFineCFOEstimate(rxLLTF,chanBW,OversamplingFactor=osf); rxWaveform = frequencyOffset(rxWaveform,sr,-fineFreqOffset);
Extract the part of the waveform that corresponds to the extremely high-throughput long training field (EHT-LTF). Demodulate the EHT-LTF and use its symbols to estimate the channel.
rxEHTLTF = rxWaveform(pktOffset+(ind.EHTLTF(1):ind.EHTLTF(2)),:);
ehtltfDemod = wlanEHTDemodulate(rxEHTLTF,"EHT-LTF",cfg,OversamplingFactor=osf);
[chanEst,pilotEst] = wlanEHTLTFChannelEstimate(ehtltfDemod,cfg);
Extract the part of the waveform that corresponds to the EHT-Data field. Demodulate the EHT-Data field and perform pilot phase error correction. After demodulation, the waveform is at the nominal baseband sampling rate.
rxData = rxWaveform(pktOffset+(ind.EHTData(1):ind.EHTData(2)),:); demodSym = wlanEHTDemodulate(rxData,"EHT-Data",cfg,OversamplingFactor=osf); demodSym = wlanEHTTrackPilotError(demodSym,chanEst,cfg,"EHT-Data");
Get OFDM information for the EHT-Data field. Estimate noise at the pilot symbols.
ofdmInfo = wlanEHTOFDMInfo("EHT-Data",cfg);
nVarEst = wlanEHTDataNoiseEstimate(demodSym(ofdmInfo.PilotIndices,:,:),pilotEst,cfg);
Extract the demodulated data symbols and the channel estimate at them.
demodDataSym = demodSym(ofdmInfo.DataIndices,:,:); chanEstData = chanEst(ofdmInfo.DataIndices,:,:);
Equalize the data symbols and recover the data bits. Check that the received bits are equal to the transmitted bits.
eqSym = wlanEHTEqualize(demodDataSym,chanEstData,nVarEst,cfg,"EHT-Data");
rxData = wlanEHTDataBitRecover(eqSym,nVarEst,cfg);
isequal(data,rxData)
ans = logical
1
See Also
wlanPacketDetect
| wlanSymbolTimingEstimate
| wlanCoarseCFOEstimate
| wlanFineCFOEstimate