📄 mac_rx.s51
字号:
// 386 * the receiver will just be off at this point after a hard disable. The check described
// 387 * above will account for this case too. However, if a hard disable were immediately
// 388 * followed by an enable, the receiver would be on. To catch this case, the receive
// 389 * FIFO is also tested to see if it is empty. Recovery is identical to the other cases.
// 390 */
// 391 if (!macRxOnFlag || MAC_RADIO_RX_FIFO_IS_EMPTY())
MOV DPTR,#macRxOnFlag
MOVX A,@DPTR
JZ ??rxStartIsr_2
MOV DPTR,#-0x209e
MOVX A,@DPTR
MOV C,0xE0 /* A */.3
JC ??rxStartIsr_3
MOVX A,@DPTR
MOV C,0xE0 /* A */.2
JC ??rxStartIsr_3
// 392 {
// 393 /* reset active flag */
// 394 macRxActive = MAC_RX_ACTIVE_NO_ACTIVITY;
??rxStartIsr_2:
CLR A
MOV DPTR,#macRxActive
MOVX @DPTR,A
// 395
// 396 /*
// 397 * To be absolutely bulletproof, must make sure no transmit queue'ed up during
// 398 * the tiny, tiny window when macRxActive was not zero.
// 399 */
// 400 rxPostRxUpdates();
; Setup parameters for call to function rxPostRxUpdates
MOV DPTR,#(??rxPostRxUpdates & 0xffff)
MOV A,#((??rxPostRxUpdates >> 16) & 0xff)
??rxStartIsr_4:
LCALL ?BCALL ; Banked call to: DPTR()
// 401
// 402 /* return immediately from here */
// 403 return;
LJMP ??rxStartIsr_5 & 0xFFFF
// 404 }
// 405
// 406 /*
// 407 * If interrupts are held off for too long it's possible the previous "transmit done"
// 408 * callback is pending. If this is the case, it needs to be completed before
// 409 * continuing with the receive logic.
// 410 */
// 411 MAC_RADIO_FORCE_TX_DONE_IF_PENDING();
??rxStartIsr_3:
; Setup parameters for call to function macCspForceTxDoneIfPending
MOV DPTR,#(macCspForceTxDoneIfPending & 0xffff)
MOV A,#((macCspForceTxDoneIfPending >> 16) & 0xff)
LCALL ?BCALL ; Banked call to: DPTR()
// 412
// 413 /*
// 414 * It's possible receive logic is still waiting for confirmation of an ACK that went out
// 415 * for the previous receive. This is OK but the callback needs to be canceled at this point.
// 416 * That callback execute receive cleanup logic that will run at the completion
// 417 * of *this* receive. Also, it is important the flag for the outgoing ACK to be cleared.
// 418 */
// 419 MAC_RADIO_CANCEL_ACK_TX_DONE_CALLBACK();
; Setup parameters for call to function macMcuAndRFIM
MOV R1,#-0x11
MOV DPTR,#(macMcuAndRFIM & 0xffff)
MOV A,#((macMcuAndRFIM >> 16) & 0xff)
LCALL ?BCALL ; Banked call to: DPTR()
// 420 macRxOutgoingAckFlag = 0;
CLR A
MOV DPTR,#macRxOutgoingAckFlag
MOVX @DPTR,A
// 421
// 422 /*
// 423 * Make a module-local copy of macRxFilter. This prevents the selected
// 424 * filter from changing in the middle of a receive.
// 425 */
// 426 rxFilter = macRxFilter;
MOV DPTR,#macRxFilter
MOVX A,@DPTR
MOV DPTR,#??rxFilter
MOVX @DPTR,A
// 427
// 428 /*-------------------------------------------------------------------------------
// 429 * Read initial frame information from FIFO.
// 430 *
// 431 * This code is not triggered until the following are in the RX FIFO:
// 432 * frame length - one byte containing length of MAC frame (excludes this field)
// 433 * frame control field - two bytes defining frame type, addressing fields, control flags
// 434 * sequence number - one byte unique sequence identifier
// 435 * additional two bytes - these bytes are available in case the received frame is an ACK,
// 436 * if so, the frame can be verified and responded to immediately,
// 437 * if not an ACK, these bytes will be processed normally
// 438 */
// 439
// 440 /* read frame length, frame control field, and sequence number from FIFO */
// 441 MAC_RADIO_READ_RX_FIFO(rxBuf, MAC_PHY_PHR_LEN + MAC_FCF_FIELD_LEN + MAC_SEQ_NUM_FIELD_LEN);
; Setup parameters for call to function macMemReadRxFifo
MOV R1,#0x4
MOV R2,#(??rxBuf & 0xff)
MOV R3,#((??rxBuf >> 8) & 0xff)
MOV DPTR,#(macMemReadRxFifo & 0xffff)
MOV A,#((macMemReadRxFifo >> 16) & 0xff)
LCALL ?BCALL ; Banked call to: DPTR()
// 442
// 443 /* bytes to read from FIFO equals frame length minus length of MHR fields just read from FIFO */
// 444 rxUnreadLen = (rxBuf[0] & PHY_PACKET_SIZE_MASK) - MAC_FCF_FIELD_LEN - MAC_SEQ_NUM_FIELD_LEN;
MOV DPTR,#??rxBuf
MOVX A,@DPTR
ANL A,#0x7f
ADD A,#-0x3
MOV DPTR,#??rxUnreadLen
MOVX @DPTR,A
// 445
// 446 /*
// 447 * Workaround for chip bug. The receive buffer can sometimes be corrupted by hardware.
// 448 * This usually occurs under heavy traffic. If a corrupted receive buffer is detected
// 449 * the entire receive buffer is flushed.
// 450 *
// 451 * In the case that this workaround is not needed, an assert is used to make sure the
// 452 * receive length field is not corrupted. This is important because a corrupted receive
// 453 * length field is utterly fatal and, if not caught here, extremely hard to track down.
// 454 */
// 455 #ifdef MAC_RADIO_RXBUFF_CHIP_BUG
// 456 if ((rxUnreadLen > (MAC_A_MAX_PHY_PACKET_SIZE - MAC_FCF_FIELD_LEN - MAC_SEQ_NUM_FIELD_LEN)) ||
// 457 (MAC_FRAME_TYPE(&rxBuf[1]) > MAC_FRAME_TYPE_MAX_VALID))
CLR C
SUBB A,#0x7d
JNC ??rxStartIsr_6
MOV DPTR,#(??rxBuf + 1)
MOVX A,@DPTR
ANL A,#0x7
CLR C
SUBB A,#0x4
JC ??rxStartIsr_7
// 458 {
// 459 MAC_RADIO_FLUSH_RX_FIFO();
??rxStartIsr_6:
MOV 0xe1,#-0x1a
MOV 0xe1,#-0x1a
SJMP ??rxStartIsr_8
// 460 rxDone();
// 461 return;
// 462 }
// 463 #else
// 464 /* radio supplied a corrupted receive buffer length */
// 465 MAC_ASSERT(rxUnreadLen <= (MAC_A_MAX_PHY_PACKET_SIZE - MAC_FCF_FIELD_LEN - MAC_SEQ_NUM_FIELD_LEN));
// 466 #endif
// 467
// 468
// 469
// 470 /*-------------------------------------------------------------------------------
// 471 * Process ACKs.
// 472 *
// 473 * If this frame is an ACK, process it immediately and exit from here.
// 474 * If this frame is not an ACK and transmit is listening for an ACK, let
// 475 * the transmit logic know an non-ACK was received so transmit can complete.
// 476 *
// 477 * In promiscuous mode ACKs are treated like any other frame.
// 478 */
// 479 if ((MAC_FRAME_TYPE(&rxBuf[1]) == MAC_FRAME_TYPE_ACK) && (rxPromiscuousMode == PROMISCUOUS_MODE_OFF))
??rxStartIsr_7:
MOVX A,@DPTR
ANL A,#0x7
XRL A,#0x2
JNZ ??rxStartIsr_9
MOV DPTR,#??rxPromiscuousMode
MOVX A,@DPTR
JNZ ??rxStartIsr_9
// 480 {
// 481 uint8 fcsBuf[MAC_FCF_FIELD_LEN];
// 482 /*
// 483 * There are guaranteed to be two unread bytes in the FIFO. By defintion, for ACK frames
// 484 * these two bytes will be the FCS.
// 485 */
// 486
// 487 /* read FCS from FIFO (threshold set so bytes are guaranteed to be there) */
// 488 MAC_RADIO_READ_RX_FIFO(fcsBuf, MAC_FCS_FIELD_LEN);
; Setup parameters for call to function macMemReadRxFifo
MOV R1,#0x2
MOV DPL,?XSP + 0
MOV DPH,?XSP + 1
MOV R2,DPL
MOV R3,DPH
MOV DPTR,#(macMemReadRxFifo & 0xffff)
MOV A,#((macMemReadRxFifo >> 16) & 0xff)
LCALL ?BCALL ; Banked call to: DPTR()
// 489
// 490 /* see if transmit is listening for an ACK */
// 491 if (macTxActive == MAC_TX_ACTIVE_LISTEN_FOR_ACK)
MOV DPTR,#macTxActive
MOVX A,@DPTR
XRL A,#0x85
JNZ ??rxStartIsr_8
// 492 {
// 493 /*
// 494 * An ACK was received so transmit logic needs to know. If the FCS failed,
// 495 * the transmit logic still needs to know. In that case, treat the frame
// 496 * as a non-ACK to complete the active transmit.
// 497 */
// 498 if (PROPRIETARY_FCS_CRC_OK(fcsBuf))
MOV A,#0x1
LCALL ?XSTACK_DISP0_8
MOVX A,@DPTR
MOV C,0xE0 /* A */.7
JNC ??rxStartIsr_10
// 499 {
// 500 /* call transmit logic to indicate ACK was received */
// 501 macTxAckReceivedCallback(MAC_SEQ_NUMBER(&rxBuf[1]), MAC_FRAME_PENDING(&rxBuf[1]));
; Setup parameters for call to function macTxAckReceivedCallback
MOV DPTR,#(??rxBuf + 1)
MOVX A,@DPTR
ANL A,#0x10
MOV R2,A
MOV DPTR,#(??rxBuf + 3)
MOVX A,@DPTR
MOV R1,A
MOV DPTR,#(macTxAckReceivedCallback & 0xffff)
MOV A,#((macTxAckReceivedCallback >> 16) & 0xff)
SJMP ??rxStartIsr_11
// 502 }
// 503 else
// 504 {
// 505 macTxAckNotReceivedCallback();
??rxStartIsr_10:
; Setup parameters for call to function macTxAckNotReceivedCallback
MOV DPTR,#(macTxAckNotReceivedCallback & 0xffff)
MOV A,#((macTxAckNotReceivedCallback >> 16) & 0xff)
??rxStartIsr_11:
LCALL ?BCALL ; Banked call to: DPTR()
// 506 }
// 507 }
// 508
// 509 /* receive is done, exit from here */
// 510 rxDone();
??rxStartIsr_8:
; Setup parameters for call to function rxDone
MOV DPTR,#(??rxDone & 0xffff)
MOV A,#((??rxDone >> 16) & 0xff)
LJMP ??rxStartIsr_4 & 0xFFFF
// 511 return;
// 512 }
// 513 else if (macTxActive == MAC_TX_ACTIVE_LISTEN_FOR_ACK)
??rxStartIsr_9:
MOV DPTR,#macTxActive
MOVX A,@DPTR
XRL A,#0x85
JNZ ??rxStartIsr_12
// 514 {
// 515 macTxAckNotReceivedCallback();
; Setup parameters for call to function macTxAckNotReceivedCallback
MOV DPTR,#(macTxAckNotReceivedCallback & 0xffff)
MOV A,#((macTxAckNotReceivedCallback >> 16) & 0xff)
LCALL ?BCALL ; Banked call to: DPTR()
// 516 }
// 517
// 518 /*-------------------------------------------------------------------------------
// 519 * Apply filtering.
// 520 *
// 521 * For efficiency, see if filtering is even 'on' before processing. Also test
// 522 * to make sure promiscuous mode is disabled. If promiscuous mode is enabled,
// 523 * do not apply filtering.
// 524 */
// 525 if ((rxFilter != RX_FILTER_OFF) && !rxPromiscuousMode)
??rxStartIsr_12:
MOV DPTR,#??rxFilter
MOVX A,@DPTR
JZ ??rxStartIsr_13
MOV DPTR,#??rxPromiscuousMode
MOVX A,@DPTR
JNZ ??rxStartIsr_13
// 526 {
// 527 if (/* filter all frames */
// 528 (rxFilter == RX_FILTER_ALL) ||
// 529
// 530 /* filter non-beacon frames */
// 531 ((rxFilter == RX_FILTER_NON_BEACON_FRAMES) &&
// 532 (MAC_FRAME_TYPE(&rxBuf[1]) != MAC_FRAME_TYPE_BEACON)) ||
// 533
// 534 /* filter non-command frames */
// 535 ((rxFilter == RX_FILTER_NON_COMMAND_FRAMES) &&
// 536 ((MAC_FRAME_TYPE(&rxBuf[1]) != MAC_FRAME_TYPE_COMMAND))))
MOV DPTR,#??rxFilter
MOVX A,@DPTR
XRL A,#0x1
JNZ $+5
LJMP ??rxStartIsr_14 & 0xFFFF
MOVX A,@DPTR
XRL A,#0x2
JZ $+5
LJMP ??rxStartIsr_15 & 0xFFFF
MOV DPTR,#(??rxBuf + 1)
MOVX A,@DPTR
ANL A,#0x7
JZ $+5
LJMP ??rxStartIsr_14 & 0xFFFF
// 537 {
// 538 /* discard rest of frame */
// 539 rxDiscardFrame();
// 540 return;
// 541 }
// 542 }
// 543
// 544 /*-------------------------------------------------------------------------------
// 545 * Compute length of addressing fields. Compute payload length.
// 546 */
// 547
// 548 /* decode addressing modes */
// 549 dstAddrMode = MAC_DEST_ADDR_MODE(&rxBuf[1]);
??rxStartIsr_13:
MOV DPTR,#(??rxBuf + 2)
MOVX A,@DPTR
MOV R2,A
RRC A
RRC A
ANL A,#0x3f
ANL A,#0x3
MOV ?V0 + 0,A
// 550 srcAddrMode = MAC_SRC_ADDR_MODE(&rxBuf[1]);
MOV A,R2
SWAP A
RRC A
RRC A
ANL A,#0x3
MOV ?V0 + 1,A
// 551
// 552 /*
// 553 * Workaround for chip bug. The receive buffer can sometimes be corrupted by hardware.
// 554 * This usually occurs under heavy traffic.
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -