00001
00038 #include <string.h>
00039 #include <errno.h>
00040 #include <stdlib.h>
00041 #include <stdio.h>
00042
00043 #include "xparameters.h"
00044 #include "xutil.h"
00045 #include "ofdm_pktdetector_mimo_regMacros.h"
00046 #include "warp_timer_regMacros.h"
00047 #include "ofdm_txrx_mimo_regMacros.h"
00048 #include "warpmac.h"
00049 #include "warpphy.h"
00050 #include "rtsctsMac.h"
00051 #include "rtsctsTest.h"
00052 #include "ascii_characters.h"
00053
00054
00056 struct {
00058 Macframe rx;
00060 Macframe rts;
00062 Macframe cts;
00064 Macframe dat;
00066 Macframe ack;
00068 Macframe bcd;
00069 } pkt;
00070
00072 enum {IDLE,BUSY};
00073
00075 enum {RTS=1,CTS=2,DAT=3,ACK=4,BCD=5,ETH=6};
00076
00078 struct {
00080 unsigned short slot;
00082 unsigned short SIFS;
00084 unsigned short DIFS;
00086 unsigned short EIFS;
00087
00089 unsigned short header;
00091 unsigned short transmit[5];
00093 unsigned short timeout[5];
00094 } delay;
00095
00097 unsigned int pktCtr[4][7];
00099 enum {TX=0, RXGOOD=1, RXUNEXP=2, RXBAD=3, DROP=3};
00100
00102 struct {
00104 unsigned char antA[8];
00106 unsigned char antB[8];
00108 unsigned char half[8];
00110 unsigned char otherhalf[8];
00112 unsigned char alternating[8];
00114 unsigned char * current;
00115 } csi = {
00116 .antA = {0, 0, 0, 0, 0, 0, 0, 0},
00117 .antB = {0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF},
00118 .half = {0,0,0,0,0xFF,0xFF,0xFF,0xFF},
00119 .otherhalf = {0xFF,0xFF,0xFF,0xFF,0,0,0,0},
00120 .alternating = {0x55,0x55,0x55,0x55,0x55,0x55,0x55,0x55},
00121 };
00122
00123
00125 const unsigned char modMasks[64] = {
00126 0x0,0xF,0xF,0xF,0xF,0xF,0xF,0x0, 0xF,0xF,0xF,0xF,0xF,0xF,0xF,0xF,
00127 0xF,0xF,0xF,0xF,0xF,0x0,0xF,0xF, 0xF,0xF,0xF,0x0,0x0,0x0,0x0,0x0,
00128 0x0,0x0,0x0,0x0,0x0,0x0,0xF,0xF, 0xF,0xF,0xF,0x0,0xF,0xF,0xF,0xF,
00129 0xF,0xF,0xF,0xF,0xF,0xF,0xF,0xF, 0xF,0x0,0xF,0xF,0xF,0xF,0xF,0xF};
00130
00132 const unsigned char modFlags[64] = {
00133 0,1,1,1,1,1,1,0, 1,1,1,1,1,1,1,1,
00134 1,1,1,1,1,0,1,1, 1,1,1,0,0,0,0,0,
00135 0,0,0,0,0,0,1,1, 1,1,1,0,1,1,1,1,
00136 1,1,1,1,1,1,1,1, 1,0,1,1,1,1,1,1};
00137
00139 struct {
00141 unsigned short rtsThreshold;
00143 unsigned char feedback_en;
00145 unsigned char mac;
00147 unsigned char chan;
00149 unsigned char currentAnt;
00151 unsigned char myID;
00153 unsigned char GPIOval;
00155 const unsigned char baseRate;
00157 const unsigned char fullRate;
00159 const unsigned char csiLength;
00160
00162 struct {
00164 unsigned short rts;
00166 unsigned short dat;
00167 } maxResend;
00168
00170 struct {
00172 unsigned char my[6];
00174 const unsigned char bc[6];
00176 const unsigned char net[4];
00177 } addr;
00178
00180 struct {
00181 unsigned char addr[6];
00182 } routeTable[16];
00183
00184 } state = {
00185 .rtsThreshold = 0,
00186 .feedback_en = 0,
00187 .mac = IDLE,
00188 .chan = 14,
00189 .currentAnt = 0,
00190 .GPIOval = 0,
00191 .baseRate = QPSK,
00192 .fullRate = QPSK,
00193 .csiLength = 0,
00194 .maxResend.rts = 4,
00195 .maxResend.dat = 2,
00196 .addr.bc = {0xff,0xff,0xff,0xff,0xff,0xff},
00197 .addr.net = {10,0,0,0},
00198 };
00199
00200
00201
00207 static inline unsigned int ceil_div_uint(unsigned int a, unsigned int b) {
00208 return (a+b-1)/b;
00209 }
00210
00211
00216 static inline void setCSMAIdleTime(unsigned int newTime) {
00217 ofdm_pktDetector_mimo_WriteReg_csma_difsPeriod(PKTDET_BASEADDR, newTime*80);
00218 }
00219
00220
00226 static inline void setTXModMasks(unsigned char * newCSI) {
00227 unsigned char modIndex, csiByte, csiMask, antAmask, antBmask;
00228
00229
00230
00231
00232
00233
00234
00235
00236
00237
00238
00239
00240
00241
00242 for(modIndex=0; modIndex<64; modIndex++) {
00243 if(modFlags[modIndex]) {
00244 csiByte = newCSI[modIndex/8];
00245 if((csiByte >> (modIndex % 8)) & 1) {
00246 XIo_Out32(XPAR_OFDM_TXRX_MIMO_PLBW_0_MEMMAP_TXMODULATION+(modIndex*sizeof(int)), 0);
00247 XIo_Out32(XPAR_OFDM_TXRX_MIMO_PLBW_0_MEMMAP_TXMODULATION+((modIndex+64)*sizeof(int)), 0xF);
00248 } else {
00249 XIo_Out32(XPAR_OFDM_TXRX_MIMO_PLBW_0_MEMMAP_TXMODULATION+(modIndex*sizeof(int)), 0xF);
00250 XIo_Out32(XPAR_OFDM_TXRX_MIMO_PLBW_0_MEMMAP_TXMODULATION+((modIndex+64)*sizeof(int)), 0);
00251 }
00252 }
00253 }
00254
00255
00256
00257
00258
00259
00260
00261
00262
00263
00264
00265
00266
00267
00268
00269
00270
00271
00272
00273
00274
00275
00276
00277
00278
00279 }
00280
00281
00284 void unlockRXantenna() {
00285 if(state.feedback_en) {
00286 warpphy_setSISOAntenna(state.currentAnt = 0);
00287 mimo_ofdmRx_setOptions(mimo_ofdmRx_getOptions() | SWITCHING_DIV_EN,
00288 DEFAULT_INTERRUPTS);
00289 }
00290 }
00291
00292
00296 void lockRXantenna() {
00297 if(state.feedback_en) {
00298 mimo_ofdmRx_setOptions(mimo_ofdmRx_getOptions() & ~SWITCHING_DIV_EN,
00299 DEFAULT_INTERRUPTS);
00300 unsigned int g = ofdm_AGC_GetGains();
00301
00302 state.currentAnt = (((g >> 8) & 0x7F) < (g & 0x7F)) ? 1 : 0;
00303 warpphy_setSISOAntenna(state.currentAnt);
00304 }
00305 }
00306
00307
00311 void loadCSI(unsigned char * newCSI) {
00312 extern Maccontrol controlStruct;
00313 if(state.csiLength > 0) {
00314 memcpy((unsigned char *)(warpphy_getBuffAddr(3) + NUM_HEADER_BYTES),
00315 (unsigned char *)newCSI,
00316 state.csiLength);
00317 }
00318 }
00319
00320
00325 void updateTimer(unsigned char type, unsigned int newTime) {
00326 extern Maccontrol controlStruct;
00327 switch(type) {
00328 case TIMEOUT:
00329 if(!warp_timer_isActive(NAV)) {
00330
00331 newTime = (newTime + delay.slot) * 80;
00332 if(warp_timer_isActive(BACKOFF))
00333 warp_timer_pause(BACKOFF);
00334 warp_timer_setVal(TIMEOUT, newTime);
00335 warp_timer_start(TIMEOUT);
00336 }
00337 break;
00338 case BACKOFF:
00339 state.mac = IDLE;
00340 newTime = randNum(controlStruct.currBackoff) * delay.slot * 80;
00341 if(!warp_timer_isActive(TIMEOUT) && !warp_timer_isActive(NAV)) {
00342 if(warp_timer_isPaused(BACKOFF)) {
00343 warp_timer_resume(BACKOFF);
00344 } else {
00345 warp_timer_setVal(BACKOFF, newTime);
00346 warp_timer_start(BACKOFF);
00347 if(controlStruct.currBackoff < controlStruct.maxBackoff)
00348 controlStruct.currBackoff++;
00349 }
00350 } else {
00351 warp_timer_stop(BACKOFF);
00352 warp_timer_setVal(BACKOFF, newTime);
00353 warp_timer_start(BACKOFF);
00354 warp_timer_pause(BACKOFF);
00355 if(controlStruct.currBackoff < controlStruct.maxBackoff)
00356 controlStruct.currBackoff++;
00357 }
00358 break;
00359 case NAV:
00360
00361 newTime = newTime * 80;
00362 if(warp_timer_isActive(TIMEOUT))
00363 warp_timer_stop(TIMEOUT);
00364 if(warp_timer_isActive(BACKOFF))
00365 warp_timer_pause(BACKOFF);
00366 if(warp_timer_isActive(NAV)) {
00367 warp_timer_pause(NAV);
00368 if(warp_timer_timeLeft(NAV) < newTime) {
00369 warp_timer_setVal(NAV, newTime);
00370 warp_timer_start(NAV);
00371 } else {
00372 warp_timer_resume(NAV);
00373 }
00374 } else {
00375 warp_timer_setVal(NAV, newTime);
00376 warp_timer_start(NAV);
00377 }
00378
00379 break;
00380 }
00381 }
00382
00383
00386 int rtsmac_timer_callback(unsigned char unused) {
00387 extern unsigned char timerIntStatus;
00388 if(timerIntStatus & 2) {
00389
00390 if(pkt.bcd.isNew)
00391 sendBCD();
00392 else if(pkt.dat.isNew)
00393 initTX();
00394 } else {
00395
00396
00397 updateTimer(BACKOFF, 0);
00398 }
00399 unlockRXantenna();
00400 return 0;
00401 }
00402
00403
00406 void dropPacket() {
00407 pkt.dat.isNew = 0;
00408 pkt.bcd.isNew = 0;
00409 state.mac = IDLE;
00410 pktCtr[DROP][ETH]++;
00411 warpmac_enableEthernet();
00412 }
00413
00414
00423 int rtsmac_emacRx_callback(Xuint32 length, char* payload) {
00424 UTime time;
00425 warpmac_disableEthernet();
00426 pktCtr[RXGOOD][ETH]++;
00427
00428 if(*(unsigned char *)(payload+33)<16
00429 && *(unsigned char *)(payload+32)==state.addr.net[2]
00430 && *(unsigned char *)(payload+31)==state.addr.net[1]
00431 && *(unsigned char *)(payload+30)==state.addr.net[0]) {
00432
00433
00434 pkt.dat.header.reserved4 = (length > state.rtsThreshold) ? 0 : 1;
00435 pkt.dat.header.length = length;
00436 memcpy(pkt.dat.header.destAddr,
00437 state.routeTable[*(unsigned char *)(payload+33)].addr,
00438 6);
00439 pkt.dat.header.currReSend = 0;
00440 pkt.dat.isNew = 1;
00441
00442
00443 delay.transmit[DAT] = delay.header + 8*ceil_div_uint((length+4), (state.fullRate & 0xF)*6);
00444 delay.timeout[DAT] = delay.transmit[DAT] + 44;
00445
00446 memcpy(pkt.rts.header.destAddr, pkt.dat.header.destAddr, 6);
00447 pkt.rts.header.currReSend = 0;
00448 time.uint16 = delay.timeout[CTS] + delay.timeout[DAT] + delay.timeout[ACK];
00449 pkt.rts.header.reserved1 = time.uint8[0];
00450 pkt.rts.header.reserved2 = time.uint8[1];
00451
00452 initTX();
00453 } else {
00454
00455 pkt.bcd.header.length = length;
00456 pkt.bcd.isNew = 1;
00457 warpmac_prepPhyForXmit(&pkt.bcd,1);
00458 sendBCD();
00459 }
00460
00461 return 0;
00462 }
00463
00464
00472 void initTX() {
00473 if(pkt.dat.isNew) {
00474 if((pkt.rts.header.currReSend <= state.maxResend.rts) && (pkt.dat.header.currReSend <= state.maxResend.dat)) {
00475 if(!warp_timer_isActive(NAV) && !warp_timer_isActive(TIMEOUT)) {
00476 if(warpmac_carrierSense()) {
00477 if(pkt.dat.header.reserved4 == 1) {
00478
00479 warpmac_prepPhyForXmit(&pkt.dat, 1);
00480 sendDAT();
00481 } else {
00482
00483 warpmac_prepPhyForXmit(&pkt.rts, 2);
00484 warpmac_startPhyXmit(2);
00485 state.mac = CTS;
00486 pktCtr[TX][RTS]++;
00487 pkt.rts.header.currReSend++;
00488 warpmac_finishPhyXmit();
00489 updateTimer(TIMEOUT, delay.timeout[CTS]);
00490
00491 pkt.dat.header.fullRate = (state.feedback_en) ? (state.fullRate | (state.fullRate<<4)) : state.fullRate;
00492
00493 warpmac_prepPhyForXmit(&pkt.dat, 1);
00494 }
00495 setCSMAIdleTime(delay.DIFS);
00496 } else {
00497 updateTimer(BACKOFF, 0);
00498 }
00499 }
00500 } else {
00501
00502 dropPacket();
00503 }
00504 }
00505 }
00506
00507
00512 void sendCTS(Macframe* packet) {
00513 UTime time;
00514
00515 if(state.feedback_en) {
00516 lockRXantenna();
00517 loadCSI(csi.current);
00518 }
00519
00520 memcpy(pkt.cts.header.destAddr,packet->header.srcAddr,6);
00521
00522 time.uint8[0] = packet->header.reserved1;
00523 time.uint8[1] = packet->header.reserved2;
00524
00525 time.uint16 = time.uint16 - delay.timeout[CTS];
00526 pkt.cts.header.reserved1 = time.uint8[0];
00527 pkt.cts.header.reserved2 = time.uint8[1];
00528
00529 delay.timeout[DAT] = time.uint16 - delay.timeout[ACK];
00530
00531 warpmac_prepPhyForXmit(&pkt.cts, 3);
00532
00533
00534 if(!warp_timer_isActive(NAV)) {
00535 warpmac_startPhyXmit(3);
00536 pktCtr[TX][CTS]++;
00537 state.mac = DAT;
00538 warpmac_finishPhyXmit();
00539 updateTimer(TIMEOUT, delay.timeout[DAT]);
00540 }
00541 }
00542
00543
00545 void sendDAT() {
00546 extern Maccontrol controlStruct;
00547 if(state.feedback_en) {
00548
00549 setTXModMasks(csi.current);
00550
00551 warpmac_enableMisoMode();
00552 warpmac_startPhyXmit(1);
00553 warpmac_finishPhyXmit();
00554 warpmac_disableMisoMode();
00555 } else {
00556 warpmac_startPhyXmit(1);
00557 warpmac_finishPhyXmit();
00558 }
00559 pktCtr[TX][DAT]++;
00560 pkt.dat.header.currReSend++;
00561 state.mac = ACK;
00562 updateTimer(TIMEOUT, delay.timeout[ACK]);
00563 }
00564
00565
00568 void sendBCD() {
00569 if(!warp_timer_isActive(NAV) && !warp_timer_isActive(TIMEOUT)) {
00570 if(warpmac_carrierSense()) {
00571 warpmac_startPhyXmit(1);
00572 pkt.bcd.isNew = 0;
00573 pktCtr[TX][BCD]++;
00574 setCSMAIdleTime(delay.DIFS);
00575 warpmac_finishPhyXmit();
00576 warpmac_enableEthernet();
00577 }
00578 updateTimer(BACKOFF, 0);
00579 }
00580 }
00581
00582
00584 int rtsmac_phyRx_badHeader_callback() {
00585 updateTimer(BACKOFF, 0);
00586 setCSMAIdleTime(delay.EIFS);
00587 unlockRXantenna();
00588 warpmac_incrementLEDLow();
00589 return 0;
00590 }
00591
00592
00600 int rtsmac_phyRx_goodHeader_callback(Macframe* packet) {
00601 extern Maccontrol controlStruct;
00602 unsigned char rxStatus = INCOMPLETE;
00603 if(warpmac_addressedToMe(packet) && !warp_timer_isActive(NAV)) {
00604 warp_timer_stop(TIMEOUT);
00605
00606 if(packet->header.pktType == RTS && (state.mac == IDLE || state.mac == DAT)) {
00607 while(rxStatus == INCOMPLETE) {
00608 rxStatus = warpphy_pollRxStatus();
00609 }
00610 if(rxStatus == GOODPACKET) {
00611 sendCTS(packet);
00612 }
00613 } else if(packet->header.pktType == CTS && state.mac == CTS) {
00614 while(rxStatus == INCOMPLETE) {
00615 rxStatus = warpphy_pollRxStatus();
00616 }
00617 if(rxStatus == GOODPACKET) {
00618 sendDAT();
00619 }
00620 } else if(packet->header.pktType == DAT
00621 && (state.mac == DAT && packet->header.reserved4 == 0
00622 || state.mac == IDLE && packet->header.reserved4 == 1)) {
00623 memcpy(pkt.ack.header.destAddr,packet->header.srcAddr,6);
00624 warpmac_prepPhyForXmit(&pkt.ack,2);
00625 while(rxStatus == INCOMPLETE) {
00626 rxStatus = warpphy_pollRxStatus();
00627 }
00628 if(rxStatus == GOODPACKET) {
00629
00630 warpmac_startPhyXmit(2);
00631
00632 warpmac_prepEmacForXmit(packet);
00633 pktCtr[TX][ACK]++;
00634 pktCtr[TX][ETH]++;
00635
00636 warpmac_finishPhyXmit();
00637
00638 warpmac_startEmacXmit(packet);
00639 updateTimer(BACKOFF, 0);
00640 unlockRXantenna();
00641 }
00642 } else if(packet->header.pktType == ACK && state.mac == ACK) {
00643
00644 while(rxStatus == INCOMPLETE) {
00645 rxStatus = warpphy_pollRxStatus();
00646 }
00647 if(rxStatus == GOODPACKET) {
00648 pkt.dat.isNew = 0;
00649 controlStruct.currBackoff = 0;
00650 updateTimer(BACKOFF, 0);
00651 warpmac_enableEthernet();
00652 }
00653 } else {
00654
00655 while(rxStatus == INCOMPLETE) {
00656 rxStatus = warpphy_pollRxStatus();
00657 }
00658 if(rxStatus == GOODPACKET) {
00659 pktCtr[RXGOOD][packet->header.pktType]--;
00660 pktCtr[RXUNEXP][packet->header.pktType]++;
00661 updateTimer(BACKOFF, 0);
00662 }
00663 }
00664 } else if(packet->header.pktType == BCD) {
00665
00666 while(rxStatus == 0) {
00667 rxStatus = warpphy_pollRxStatus();
00668 }
00669 if(rxStatus == GOODPACKET) {
00670
00671 warpmac_prepEmacForXmit(packet);
00672
00673 warpmac_startEmacXmit(packet);
00674 updateTimer(BACKOFF, 0);
00675 }
00676 } else {
00677
00678 UTime time;
00679 time.uint8[0] = packet->header.reserved1;
00680 time.uint8[1] = packet->header.reserved2;
00681 if(time.uint16 > 0) {
00682 updateTimer(NAV,time.uint16);
00683 }
00684 }
00685
00686 if(rxStatus == GOODPACKET) {
00687 pktCtr[RXGOOD][packet->header.pktType]++;
00688 warpmac_incrementLEDHigh();
00689 } else if(rxStatus == BADPACKET) {
00690 pktCtr[RXBAD][packet->header.pktType]++;
00691 rtsmac_phyRx_badHeader_callback();
00692 }
00693
00694 return 0;
00695 }
00696
00697
00698
00699
00703 int main() {
00704 xil_printf("\r\nInitializing RTS/CTS MAC...\r\n");
00705
00706
00707 warpmac_init();
00708
00709 initDelays();
00710 initAddresses();
00711 initHeaders();
00712
00713 state.mac = IDLE;
00714 clearPktCtr();
00715
00716
00717 warp_timer_setMode(TIMEOUT, DISABLECSMA);
00718 warp_timer_setMode(BACKOFF, ENABLECSMA);
00719 warp_timer_setMode(NAV, DISABLECSMA);
00720
00721
00722 warpmac_setRxBuffer(&pkt.rx,0);
00723
00724 warpmac_setTxBuffer(1);
00725
00726 warpmac_setBadHeaderCallback((void *)rtsmac_phyRx_badHeader_callback);
00727 warpmac_setGoodHeaderCallback((void *)rtsmac_phyRx_goodHeader_callback);
00728 warpmac_setTimerCallback((void *)rtsmac_timer_callback);
00729 warpmac_setEmacCallback((void *)rtsmac_emacRx_callback);
00730 warpmac_setUpButtonCallback((void *)rtsmac_up);
00731 warpmac_setMiddleButtonCallback((void *)rtsmac_middle);
00732 warpmac_setLeftButtonCallback((void *)rtsmac_left);
00733 warpmac_setRightButtonCallback((void *)rtsmac_right);
00734
00735
00736 warpphy_setChannel(GHZ_2, state.chan);
00737
00738 warpmac_enableCSMA();
00739 warpmac_enableEthernet();
00740
00741
00742 warpmac_setBaseRate(state.baseRate);
00743
00744
00745 warpmac_leftHex((state.rtsThreshold) == 0 ? 1 : 0);
00746
00747 csi.current = csi.antA;
00748
00749
00750
00751
00752
00753
00754
00755 xil_printf(" finished.");
00756 while(1)
00757 {
00758 volatile unsigned char uartByte = 0;
00759
00760 warpmac_pollEthernet();
00761
00762
00763
00764
00765
00766
00767
00768
00769
00770
00771
00772
00773
00774
00775
00776
00777
00778
00779
00780
00781
00782
00783 }
00784
00785 return 0;
00786 }
00787
00788
00789
00790
00791
00792
00793
00794
00795
00796
00797
00801 void initFeedback() {
00802
00803 warpphy_setSISOAntenna(state.currentAnt ^= 1);
00804 warpphy_setSISOAntenna(state.currentAnt ^= 1);
00805
00806 unlockRXantenna();
00807
00808 if(0 && state.myID == 2) {
00809 state.feedback_en = 1;
00810 }
00811
00812 setTXModMasks(csi.antA);
00813 }
00814
00815
00817 void initDelays() {
00818
00819 delay.header = 64;
00820 delay.transmit[CTS] = delay.header
00821 + ( (state.csiLength > 0) ? ceil_div_uint(state.csiLength + 4, 6*(state.fullRate & 0xF))*8 : 0 );
00822 delay.transmit[ACK] = delay.header;
00823
00824
00825 delay.slot = 9;
00826 delay.SIFS = 46;
00827 delay.DIFS = delay.SIFS + 2*delay.slot;
00828 delay.EIFS = delay.SIFS + delay.DIFS + delay.transmit[ACK];
00829
00830
00831 delay.timeout[CTS] = delay.slot + delay.transmit[CTS] + 46;
00832 delay.timeout[ACK] = delay.slot + delay.transmit[ACK] + 24;
00833
00834
00835 setCSMAIdleTime(delay.DIFS);
00836
00837 warpmac_setMaxCW(5);
00838 }
00839
00840
00842 void initAddresses() {
00843 unsigned char i;
00844
00845
00846
00847 state.myID = warpmac_getMyId();
00848
00849
00850 state.addr.my[0] = 0x16; state.addr.my[1] = 0x24; state.addr.my[2] = 0x63;
00851 state.addr.my[3] = 0x53; state.addr.my[4] = 0xe2; state.addr.my[5] = 0xc2+state.myID;
00852
00853
00854 for(i=0;i<16;i++) {
00855 state.routeTable[i].addr[0] = state.addr.my[0];
00856 state.routeTable[i].addr[1] = state.addr.my[1];
00857 state.routeTable[i].addr[2] = state.addr.my[2];
00858 state.routeTable[i].addr[3] = state.addr.my[3];
00859 state.routeTable[i].addr[4] = state.addr.my[4];
00860 state.routeTable[i].addr[5] = state.addr.my[5]+i-state.myID;
00861 }
00862
00863 warpmac_setMacAddr((unsigned char *)(&state.addr.my));
00864 }
00865
00866
00868 void initHeaders() {
00869 UTime time;
00870
00871
00872 pkt.rts.header.fullRate = state.fullRate;
00873 pkt.rts.header.reserved4 = 0;
00874 pkt.rts.header.length = 0;
00875 pkt.rts.header.pktType = RTS;
00876 memcpy(pkt.rts.header.srcAddr,(unsigned char *)state.addr.my,6);
00877 pkt.rts.header.currReSend = 0;
00878
00879
00880 pkt.cts.header.fullRate = state.fullRate;
00881 pkt.cts.header.reserved4 = 0;
00882 pkt.cts.header.length = state.csiLength;
00883 pkt.cts.header.pktType = CTS;
00884 memcpy(pkt.cts.header.srcAddr,(unsigned char *)state.addr.my,6);
00885 pkt.cts.header.currReSend = 0;
00886
00887
00888 pkt.dat.header.fullRate = state.fullRate;
00889 pkt.dat.header.pktType = DAT;
00890 memcpy(pkt.dat.header.srcAddr,(unsigned char *)state.addr.my,6);
00891 time.uint16 = delay.timeout[ACK];
00892 pkt.dat.header.currReSend = 0;
00893 pkt.dat.header.reserved1 = time.uint8[0];
00894 pkt.dat.header.reserved2 = time.uint8[1];
00895
00896
00897 pkt.ack.header.fullRate = state.fullRate;
00898 pkt.ack.header.reserved4 = 0;
00899 pkt.ack.header.length = 0;
00900 pkt.ack.header.pktType = ACK;
00901 pkt.ack.header.currReSend = 0;
00902 pkt.ack.header.reserved1 = 0;
00903 pkt.ack.header.reserved2 = 0;
00904
00905
00906 pkt.bcd.header.fullRate = state.fullRate;
00907 pkt.bcd.header.reserved4 = 0;
00908 pkt.bcd.header.pktType = BCD;
00909 memcpy(pkt.bcd.header.destAddr,(unsigned char *)state.addr.bc,6);
00910 memcpy(pkt.bcd.header.srcAddr,(unsigned char *)state.addr.my,6);
00911 pkt.bcd.header.currReSend = 0;
00912 pkt.bcd.header.reserved1 = 0;
00913 pkt.bcd.header.reserved2 = 0;
00914 }
00915
00916
00917
00918
00919
00922 void rtsmac_left() {
00923 extern unsigned char txGain;
00924 warpphy_setGainMinus(ceil_div_uint(txGain,8));
00925
00926
00927
00928
00929
00930
00931
00932
00933
00934
00935
00936
00937
00938
00939
00940
00941
00942
00943
00944
00945
00946
00947
00948
00949
00950
00951
00952
00953
00954
00955
00956
00957
00958
00959
00960 }
00961
00962
00965 void rtsmac_middle() {
00966 printState();
00967 printTvars();
00968 printStatistics();
00969 }
00970
00971
00974 void rtsmac_right() {
00975 extern unsigned char txGain;
00976 warpphy_setGainPlus(ceil_div_uint(txGain,8));
00977 }
00978
00979
00982 void rtsmac_up() {
00983 state.rtsThreshold = (state.rtsThreshold == 0) ? 65535 : 0;
00984 warpmac_leftHex((state.rtsThreshold) == 0 ? 1 : 0);
00985 }
00986
00987
00988
00989
00990
00992 void printState() {
00993 extern Maccontrol controlStruct;
00994 xil_printf("\nMAC=%d,NAV=%d,dat.isNew=%d,bcd.isNew=%d,currentAnt=%d,"
00995 "timeLeft_0=%d,timeLeft_1=%d,timeLeft_2=%d,timeLeft_3=%d,tstatus=%x",
00996 state.mac,
00997 warp_timer_isActive(NAV),
00998 pkt.dat.isNew,
00999 pkt.bcd.isNew,
01000 state.currentAnt,
01001 warp_timer_timeLeft(0),
01002 warp_timer_timeLeft(1),
01003 warp_timer_timeLeft(2),
01004 warp_timer_timeLeft(3),
01005 warp_timer_getStatuses());
01006 }
01007
01008
01010 void clearPktCtr() {
01011 unsigned char i, j;
01012 for(i = 0; i < 4; i++){
01013 for(j = 0; j < 7; j++){
01014 pktCtr[i][j] = 0;
01015 }
01016 }
01017 }
01018
01019
01025 void printStatistics() {
01026 unsigned char i = 0;
01027 char pktType[7][8] = {"TOTAL","RTS","CTS","DAT","ACK","BCD","ETH"};
01028 xil_printf("\n | TX | RX_good |RX_unexp | RX_bad |\n");
01029 pktCtr[TX][0] = 0;
01030 pktCtr[RXGOOD][0] = 0;
01031 pktCtr[RXUNEXP][0] = 0;
01032 pktCtr[RXBAD][0] = 0;
01033 for(i = 1; i < 5; i++) {
01034 pktCtr[TX][0] += pktCtr[TX][i];
01035 pktCtr[RXGOOD][0] += pktCtr[RXGOOD][i];
01036 pktCtr[RXUNEXP][0] += pktCtr[RXUNEXP][i];
01037 pktCtr[RXBAD][0] += pktCtr[RXBAD][i];
01038 xil_printf("%8s|%9d|%9d|%9d|%9d|\n",
01039 (unsigned char *)pktType[i],
01040 pktCtr[TX][i],
01041 pktCtr[RXGOOD][i],
01042 pktCtr[RXUNEXP][i],
01043 pktCtr[RXBAD][i]);
01044 }
01045 xil_printf("%8s|%9d|%9d|%9d|%9d|\n",
01046 (unsigned char *)pktType[0],
01047 pktCtr[TX][0],
01048 pktCtr[RXGOOD][0],
01049 pktCtr[RXUNEXP][0],
01050 pktCtr[RXBAD][0]);
01051 xil_printf("-------------------------------------------------\n");
01052 xil_printf(" | TX | RX |\n");
01053 xil_printf("%8s|%9d|%9d|\n",
01054 (unsigned char *)pktType[BCD],
01055 pktCtr[TX][BCD],
01056 pktCtr[RXGOOD][BCD]);
01057 xil_printf("-------------------------------------------------\n");
01058 xil_printf(" | TX | RX | DROP |\n");
01059 xil_printf("%8s|%9d|%9d|%9d|\n",
01060 (unsigned char *)pktType[ETH],
01061 pktCtr[TX][ETH],
01062 pktCtr[RXGOOD][ETH],
01063 pktCtr[DROP][ETH]);
01064 }