📄 mac-802_11.cc
字号:
*/ discard(pktDx_, "---"); goto done; } //printf("STEP FINAL\n"); switch(type) { case MAC_Type_Control: switch(subtype) { case MAC_Subtype_ACK: recvACK(pktDx_); break; default: fprintf(stderr,"recvTimer1:Invalid MAC Control Subtype %x\n", subtype); exit(1); } break; case MAC_Type_Data: //printf("DATA RECEIVED\n"); switch(subtype) { case MAC_Subtype_Data: recvDATA(pktDx_); break; default: fprintf(stderr, "recv_timer2:Invalid MAC Data Subtype %x\n", subtype); exit(1); } break; default: fprintf(stderr, "recv_timer3:Invalid MAC Type %x\n", subtype); exit(1); } done: pktDx_ = 0; dx_resume();}voidMac802_11::recv_timer(){ u_int32_t src; hdr_cmn *ch = HDR_CMN(pktRx_); hdr_mac802_11 *mh = HDR_MAC802_11(pktRx_);//JUNGMIN struct beacon_frame *beacon;//end of JUNGMIN u_int32_t dst = ETHER_ADDR(mh->dh_da); // XXX debug //struct cts_frame *cf = (struct cts_frame*)pktRx_->access(hdr_mac::offset_); //u_int32_t src = ETHER_ADDR(mh->dh_sa); u_int8_t type = mh->dh_fc.fc_type; u_int8_t subtype = mh->dh_fc.fc_subtype; assert(pktRx_); assert(rx_state_ == MAC_RECV || rx_state_ == MAC_COLL); /* * If the interface is in TRANSMIT mode when this packet * "arrives", then I would never have seen it and should * do a silent discard without adjusting the NAV. */ if(tx_active_) { Packet::free(pktRx_); goto done; } /* * Handle collisions. */ if(!(type == MAC_Type_Management && subtype == MAC_Subtype_Beacon)) { if(rx_state_ == MAC_COLL) { discard(pktRx_, DROP_MAC_COLLISION); set_nav(usec(eifs_)); goto done; } } /* * Check to see if this packet was received with enough * bit errors that the current level of FEC still could not * fix all of the problems - ie; after FEC, the checksum still * failed. */ if( ch->error() ) { Packet::free(pktRx_); set_nav(usec(eifs_)); goto done; } /* * IEEE 802.11 specs, section 9.2.5.6 * - update the NAV (Network Allocation Vector) */ //Must modify this to make intelligent channel selection if(dst != (u_int32_t)index_) { set_nav(mh->dh_duration); if(type == MAC_Type_Management) { if(subtype == MAC_Subtype_ATIMRSH) { recvOtherATIMRSH(pktRx_); } else if(subtype == MAC_Subtype_ATIMACK) { recvOtherATIMACK(pktRx_); } } else if(type == MAC_Type_Control) { if(subtype == MAC_Subtype_DCTS) { recvOtherDCTS(pktRx_); } else if(subtype == MAC_Subtype_DRSH) { recvOtherDRSH(pktRx_); } } } /* tap out - */ if (tap_ && type == MAC_Type_Data && MAC_Subtype_Data == subtype ) tap_->tap(pktRx_); /* * Adaptive Fidelity Algorithm Support - neighborhood infomation * collection * * Hacking: Before filter the packet, log the neighbor node * I can hear the packet, the src is my neighbor */ if (netif_->node()->energy_model() && netif_->node()->energy_model()->adaptivefidelity()) { src = ETHER_ADDR(mh->dh_sa); netif_->node()->energy_model()->add_neighbor(src); } /* * Address Filtering */ if(dst != (u_int32_t)index_ && dst != MAC_BROADCAST) { /* * We don't want to log this event, so we just free * the packet instead of calling the drop routine. */ discard(pktRx_, "---"); goto done; } switch(type) { case MAC_Type_Management://JUNGMIN switch(subtype) { case MAC_Subtype_Beacon: beacon = (struct beacon_frame *)pktRx_->access(hdr_mac::offset_); macmib_->dot11BeaconPeriod = beacon->bf_binterval;//if waiting to send beacon, stop it. beacon_received(); mac_log(pktRx_); break; case MAC_Subtype_ATIM: recvATIM(pktRx_); break; case MAC_Subtype_ATIMACK: recvATIMACK(pktRx_); break; case MAC_Subtype_ATIMRSH: recvATIMRSH(pktRx_); break; default: discard(pktRx_, DROP_MAC_PACKET_ERROR); }//end of JUNGMIN goto done; break; case MAC_Type_Control: switch(subtype) { case MAC_Subtype_RTS: recvRTS(pktRx_); break; case MAC_Subtype_CTS: recvCTS(pktRx_); break; case MAC_Subtype_DRTS: recvDRTS(pktRx_); break; case MAC_Subtype_DCTS: recvDCTS(pktRx_); break; case MAC_Subtype_DRSH: recvDRSH(pktRx_); break; case MAC_Subtype_ACK: recvACK(pktRx_); break; default: fprintf(stderr,"recvTimer1:Invalid MAC Control Subtype %x\n", subtype); exit(1); } break;//JUNGMIN case MAC_Type_Data: switch(subtype) { case MAC_Subtype_Data: recvDATA(pktRx_); break;//end of JUNGMIN default: fprintf(stderr, "recv_timer2:Invalid MAC Data Subtype %x\n", subtype); exit(1); } break; default: fprintf(stderr, "recv_timer3:Invalid MAC Type %x\n", subtype); exit(1); } done: pktRx_ = 0; rx_resume();}voidMac802_11::recvRTS(Packet *p){ struct rts_frame *rf = (struct rts_frame*)p->access(hdr_mac::offset_); if(tx_state_ != MAC_IDLE) { discard(p, DROP_MAC_BUSY); return; } /* * If I'm responding to someone else, discard this RTS. */ if(pktCTRL_) { discard(p, DROP_MAC_BUSY); return; } sendCTS(ETHER_ADDR(rf->rf_ta), rf->rf_duration); /* * Stop deferring - will be reset in tx_resume(). */ if(mhDefer_.busy()) mhDefer_.stop(); tx_resume(); mac_log(p);}voidMac802_11::recvDRTS(Packet *p){ struct dca_rts_frame *drts = (struct dca_rts_frame*)p->access(hdr_mac::offset_); if(tx_state_ != MAC_IDLE) { discard(p, DROP_MAC_BUSY); return; } /* * If I'm responding to someone else, discard this RTS. */ if(pktCTRL_) { discard(p, DROP_MAC_BUSY); return; } for(int i=0; i<NUMBER_OF_CHANNELS; i++) { dca_recved_fcl_[i] = drts->drts_channel_list[i]; } sendDCTS(ETHER_ADDR(drts->drts_sa), drts->drts_data_transfer_time); /* * Stop deferring - will be reset in tx_resume(). */ if(mhDefer_.busy()) mhDefer_.stop(); tx_resume(); mac_log(p);}//JUNGMINvoidMac802_11::recvATIM(Packet *p){ struct atim_frame *atf = (struct atim_frame*)p->access(hdr_mac::offset_); if(tx_state_ != MAC_IDLE) { discard(p, DROP_MAC_BUSY); return; } //if I'm responding to someone else, discard this ATIM. if(pktATIMACK_) { discard(p, DROP_MAC_BUSY); return; } SelectChannel(atf); sendATIMACK(ETHER_ADDR(atf->atf_sa)); if(mhDefer_.busy()) mhDefer_.stop(); tx_resume(); mac_log(p);}voidMac802_11::DCABuildFreeChannelList(int* fcl){ fcl[0] = 0; for(int i=1; i<NUMBER_OF_CHANNELS; i++) { if(dca_cul_[i] == 0) fcl[i] = 1; else fcl[i] = 0; }}void Mac802_11::ConfirmChannel(struct atimack_frame* aaf){ if(selected_channel_ == -1) { selected_channel_ = aaf->aaf_selected_channel; }}voidMac802_11::SelectChannel(struct atim_frame* atf){ //Channel Selection Algorithm int* cl = atf->atf_channel_list; int j, potentia, p_index, dye; //1. Receiver Selected if(selected_channel_ != -1) return; //2. Sender preferable for(j=0; j<NUMBER_OF_CHANNELS; j++) { if(cl[j] == -1) { fcl_[j] = -1; selected_channel_ = j; //update mine return; } } p_index = 0; potentia = fcl_[p_index]; //3. Receiver Free for(j=0; j<NUMBER_OF_CHANNELS; j++) { if(fcl_[j] <= potentia) { if(fcl_[j] == potentia) { p_index = j; } else { potentia = fcl_[j]; p_index = j; } } } //4. Sender Free for(j=0; j<NUMBER_OF_CHANNELS; j++) { if(cl[j] < potentia) { potentia = cl[j]; p_index = j; } } fcl_[p_index] = -1; selected_channel_ = p_index; return;}intMac802_11::DCASelectChannel(int* fcl){ for(int i=1; i<NUMBER_OF_CHANNELS; i++) { if(dca_cul_[i] == 0) return i; } return -1;}doubleMac802_11::FindNearestChannelFreeTime(){ double nearest = dca_cul_[1]; int i; for(i=2; i<NUMBER_OF_CHANNELS; i++) { if(dca_cul_[i] < nearest) { nearest = dca_cul_[i]; } } return nearest;}voidMac802_11::ResetChannelInfo(){ for(int j=0; j<NUMBER_OF_CHANNELS; j++) { fcl_[j] = 0; } selected_channel_ = -1; active_channel_ = 0;}voidMac802_11::ResetNeighborChannelStateInfo(){ for(int j=0; j<MAX_NODES; j++) { channel_state_[j] = -1; }} voidMac802_11::ResetDestInfo(){ for(int i=0; i<MAX_NODES; i++) { dest_state_[i] = 0; //Did I send ATIM packet to dest i? }}voidMac802_11::ResetAtBeacon(){ ResetChannelInfo(); ResetDestInfo(); ResetNeighborChannelStateInfo();}//end of JUNGMIN/* * txtime() - pluck the precomputed tx time from the packet header */doubleMac802_11::txtime(Packet *p) { struct hdr_cmn *ch = HDR_CMN(p); double t = ch->txtime(); if (t < 0.0) { drop(p, "XXX"); exit(1); } return t; } /* * txtime() - calculate tx time for packet of size "psz" bytes * at rate "drt" bps */doubleMac802_11::txtime(double psz, double drt){ double dsz = psz - PLCP_HDR_LEN; int plcp_hdr = PLCP_HDR_LEN << 3; int datalen = (int)dsz << 3; double t = (((double)plcp_hdr)/phymib_->PLCPDataRate) + (((double)datalen)/drt); return(t);}//JUNGMINvoidMac802_11::recvDCTS(Packet *p){ if(tx_state_ != MAC_RTS) { discard(p, DROP_MAC_INVALID_STATE); return; } assert(pktRTS_); Packet::free(pktRTS_); pktRTS_ = 0; assert(pktTx_); mhSend_.stop(); ssrc_ = 0; rst_cw(); struct dca_cts_frame *dcts = (struct dca_cts_frame*)p->access(hdr_mac::offset_); if(dcts->dcts_selected_channel != -1) { active_channel_ = dcts->dcts_selected_channel; sendDRSH(ETHER_ADDR(dcts->dcts_ra), dcts->dcts_usage_time); tx_resume(); } else { //postpone the transmission and start waitTimer pktTx_ = 0; if(NOW - dcts->dcts_wait_time > 0) { if(mhWait_.busy()) mhWait_.stop(); mhWait_.start(difs_); } else { if(mhWait_.busy()) mhWait_.stop(); mhWait_.start(dcts->dcts_wait_time - NOW); } tx_resume(); } mac_log(p);}//end of JUNGMINvoidMac802_11::recvCTS(Packet *p){ if(tx_state_ != MAC_RTS) { discard(p, DROP_MAC_INVALID_STATE); return; } assert(pktRTS_); Packet::free(pktRTS_); pktRTS_ = 0; assert(pktTx_); mhSend_.stop(); /* * The successful reception of this CTS packet implies * that our RTS was successful. Hence, we can reset * the Short Retry Count and the CW. */ ssrc_ = 0; rst_cw(); tx_resume(); mac_log(p);}//JUNGMINvoidMac802_11::recvDATA(Packet *p){ struct hdr_mac802_11 *dh = HDR_MAC802_11(p); u_int32_t dst, src, size; struct hdr_cmn *ch = HDR_CMN(p); { dst = ETHER_ADDR(dh->dh_da); src = ETHER_ADDR(dh->dh_sa); size = ch->size(); /* * Adjust the MAC packet size - ie; strip * off the mac header */ ch->size() -= ETHER_HDR_LEN11; ch->num_forwards()
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -