- // frame does not fit in remaing portion of the CAP
- if (elapsed < call CapLen.getNow()){
- m_backoffElapsed += call CapLen.getNow() - elapsed;
- if (m_backoffElapsed > m_backoff)
- m_backoffElapsed = m_backoff;
+ // slotted CSMA-CA
+ uint32_t capLen = call CapLen.getNow(), capStart = call CapStart.getNow();
+ uint32_t elapsed, totalTime;
+ totalTime = IEEE154_RADIO_TX_SEND_DELAY +
+ m_backoff - m_backoffElapsed + m_transactionTime + IEEE154_RADIO_GUARD_TIME;
+ if (totalTime > capLen)
+ totalTime = capLen; // CAP is too short
+ elapsed = call TimeCalc.timeElapsed(capStart, call CapEndAlarm.getNow());
+ elapsed += (20 - (elapsed % 20)); // round to backoff boundary
+ if (!call TimeCalc.hasExpired(capStart, capLen - totalTime)){
+ call RadioTx.transmit(call CapStartRefTime.getNow(),
+ elapsed + IEEE154_RADIO_TX_SEND_DELAY + m_backoff - m_backoffElapsed,
+ m_numCCA,
+ m_currentFrame->header->mhr[0] & FC1_ACK_REQUEST ? TRUE : FALSE);
+ next = WAIT_FOR_TXDONE; // this will NOT clear the lock
+ } else {
+ // frame does not fit in remaing portion of the CAP
+ if (elapsed < call CapLen.getNow()){
+ m_backoffElapsed += call CapLen.getNow() - elapsed;
+ if (m_backoffElapsed > m_backoff)
+ m_backoffElapsed = m_backoff;
+ }
+ next = SWITCH_OFF;