/*****************************************************************************/ /** * @file link_layer.h * @author FanHao (hao_fan_bit_ee@163.com) * @brief DF Linklayer header file. * @version 0.1 * @date 2023-05-06 * * @copyright Copyright(c) 2024 Beijing Institute of Technology.\n * Lab of Communication and Network * ******************************************************************************/ /** * @defgroup LinkLayer * @{ */ #ifndef __LINK_LAYER_H_ #define __LINK_LAYER_H_ /***************************** Include Files *********************************/ #include #include "link_layer_types.h" #include "schdevent.h" #include "node_list.h" #include "msg_def.h" #include "circ_queue.h" #include "../phy_layer/phy_layer.h" #include "../../systembus/systembus.h" /************************** Constant Definitions *****************************/ /***************** Macros (Inline Functions) Definitions *********************/ #define AssertL2Event(instPtr, event) (Linklayer_EventHandler((instPtr), (event))) /**************************** Type Definitions *******************************/ /** * @struct L2_CONFIG * @brief A struct holds all linklayer initialization parameters */ typedef struct { L2_NODE_TYPE myType; ///< node type uint8_t clustId; ///< node cluster id uint8_t myId; ///< node id uint8_t headId; ///< head node id uint8_t netScale; ///< net scale L2_SVC_RATE serviceRate; ///< service data rate L2_RTNE_TABLE_ENTRY **initTable; L2_RTNE_TABLE_ENTRY **normalTable; PHY_INST *phyInstPtr; ///< pointer to system physical layer instance TMC_INST *tmcInstPtr; ///< pointer to system timer controller layer instance } L2_CONFIG; /** * @struct L2_LOG * @brief A struct holds linklayer operating log */ typedef struct { uint32_t frameRx; ///< total rx frame count uint32_t frameTx; ///< total tx frame count uint32_t frameRecv; ///< total received frame count uint32_t frameCorrect; ///< total correctly received frame count uint32_t advRxCnt; ///< advertise rx frame count uint32_t advTxCnt; ///< advertise tx frame count uint32_t advRecvCnt; ///< advertise received frame count uint32_t advCorrectCnt; ///< advertise correctly received frame count uint32_t ackRxCnt; ///< acknowledgement rx frame count uint32_t ackTxCnt; ///< acknowledgement tx frame count uint32_t ackRecvCnt; ///< acknowledgement received frame count uint32_t ackCorrectCnt; ///< acknowledgement correctly received frame count uint32_t disRxCnt; ///< distribution rx frame count uint32_t disTxCnt; ///< distribution tx frame count uint32_t disRecvCnt; ///< distribution received frame count uint32_t disCorrectCnt;///< distribution correctly received frame count uint32_t mngRxCnt; ///< management rx frame count uint32_t mngTxCnt; ///< management tx frame count uint32_t mngRecvCnt; ///< management received frame count uint32_t mngCorrectCnt; ///< management correctly received frame count uint32_t rttRxCnt; ///< rtt rx frame count uint32_t rttTxCnt; ///< rtt tx frame count uint32_t rttRecvCnt; ///< rtt received frame count uint32_t rttCorrectCnt; ///< rtt correctly received frame count uint32_t svcRxCnt; ///< service rx frame count uint32_t svcTxCnt; ///< service tx frame count uint32_t svcRecvCnt; ///< service received frame count uint32_t svcCorrectCnt; ///< service correctly received frame count int64_t timeDev; ///< last time deviation estimation result uint32_t reconnectCnt; ///< reconnect trial count L2_MSG_RECORD rxLog; L2_MSG_RECORD txLog; } L2_LOG; /** * @struct L2_INST * @brief A linklayer instance */ typedef struct { L2_CONFIG config; ///< linklayer configuration parameters L2_NODE_INFO myInfo; ///< current node info NODE_LIST *nodeList; ///< discovered node list L2_SCHD_POOL *schdEventPool; ///< event schedule pool uint32_t netStartTime; ///< network start time bool isEnable; ///< indicates if the node is connected to the network bool dataAvail; ///< indicates if there is a valid received frame data in rx buffer bool cxn2Net; ///< indicates if the node is connected to the network L2_RCD frameNum; ///< stores the last current and next frame number. L2_RCD slotNum; ///< stores the last current and next slot number. L2_RCD frame; ///< stores the last current and next link layer frame type. L2_RCD tor; ///< stores the last current and next link layer tx/rx state. L2_NODE_STATE mainState; ///< the main state of link layer state L2_NODE_STATE nextState; ///< next state of link layer state, which will be applied to mainState every second. L2_RTNE_CONFIG rtneConfig; ///< current routine table configuration and status. L2_SCAN_FSM *scanFSM; ///< FSM of scan net (link set up) L2_SVC_FSM *serviceFSM; ///< FSM of service net (data service) uint8_t *sendPktData; ///< send data buffer uint8_t *recvPktData; ///< received data buffer L2_LOG log; ///< Linklayer operating log // for system log SYSINFO sysInfo; ///< system info LINKLOG linkLog; ///< linklayer log for system monitor } L2_INST; /************************** Variable Definitions *****************************/ extern L2_RTNE_TABLE_ENTRY *initRoutTable[L2_INIT_RTNE_PERIOD]; extern L2_RTNE_TABLE_ENTRY *normalRoutTable0[L2_INIT_RTNE_PERIOD]; extern L2_RTNE_TABLE_ENTRY *normalRoutTable1[L2_INIT_RTNE_PERIOD]; extern L2_RTNE_TABLE_ENTRY *normalRoutTable2[L2_INIT_RTNE_PERIOD]; /************************** Function Prototypes ******************************/ /** * @defgroup LinkLayer_Main * @{ */ int32_t Linklayer_Init(L2_INST **instPtr, const L2_CONFIG *config); int32_t Linklayer_Reconfig(L2_INST *instPtr, const L2_CONFIG *config); void Linklayer_Destroy(L2_INST *instPtr); int32_t Linklayer_Start(L2_INST *instPtr); int32_t Linklayer_Halt(L2_INST *instPtr); int32_t Linklayer_Proc(L2_INST *instPtr); int32_t Linklayer_EventHandler(L2_INST *instPtr, const L2_EVENT *l2Event); int32_t Linklayer_PktHandler(L2_INST *instPtr); int32_t L2_SetupNextSlot(L2_INST *instPtr, L2_TOR_TYPE txrxMode, L2_FRAME_TYPE frameType); /** @} LinkLayer_Main*/ /** * @defgroup LinkLayer_Framing * @{ */ void L2_FrameInsertChunk(uint8_t *frame, size_t offset, size_t bytes, const void *chunk); void L2_FrameGetChunk(uint8_t *frame, size_t offset, size_t bytes, void *chunk); int32_t L2_CrcAppend(uint8_t *dataBuff, uint32_t dataLen, uint32_t crcPos, L2_CRC_TYPE crcType); int32_t L2_CrcGen(uint8_t *dataBuff, uint32_t dataLen, L2_CRC_TYPE crcType, uint32_t *crc); bool L2_CrcCheck(uint8_t *dataBuff, uint32_t dataLen, L2_CRC_TYPE crcType); /** @} LinkLayer_Framing*/ /** * @defgroup LinkLayer_Scheduler * @{ */ void L2_EventPoolHandler(L2_INST *instPtr); int32_t L2_ScheduleEventAt(L2_INST *instPtr, L2_SCHD_EVENT *schdEvent, uint32_t frameNo, uint32_t slotNo); int32_t L2_ScheduleEventAfter(L2_INST *instPtr, L2_SCHD_EVENT *schdEvent, uint32_t numSlots); int32_t L2_RescheduleEventAt(L2_INST *instPtr, L2_SCHD_EVENT *schdEvent, uint32_t frameNo, uint32_t slotNo); int32_t L2_RescheduleEventAfter(L2_INST *instPtr, L2_SCHD_EVENT *schdEvent, uint32_t numSlots); /** @} LinkLayer_Scheduler*/ /** * @defgroup LinkLayer_Scan * @{ */ int32_t L2_Scan_Init(L2_SCAN_FSM **scanFSMPtr); void L2_Scan_Reset(L2_SCAN_FSM *scanFSMPtr); void L2_Scan_Destroy(L2_SCAN_FSM *scanFSMPtr); int32_t L2_Scan_Proc(L2_INST *instPtr); int32_t L2_Scan_PktHandler(L2_INST *instPtr, uint8_t *msg); int32_t L2_Scan_Routine(L2_INST *instPtr, const L2_RTNE_TABLE_ENTRY *schedEntry); /** @} LinkLayer_Scan*/ /** * @defgroup LinkLayer_Service * @{ */ int32_t L2_Service_Init(L2_SVC_FSM **svcFSMPtr); void L2_Service_Reset(L2_SVC_FSM *svcFSMPtr); void L2_Service_Destroy(L2_SVC_FSM *svcFSMPtr); int32_t L2_Service_PktHandler(L2_INST *instPtr, uint8_t *msg); int32_t L2_Service_Proc(L2_INST *instPtr); int32_t L2_Service_Routine(L2_INST *instPtr, const L2_RTNE_TABLE_ENTRY *schedEntry); /** @} LinkLayer_Service*/ /** * @defgroup LinkLayer_TimeSync * @{ */ int32_t L2_GetTimeDeviation(L2_INST *instPtr, uint32_t frameNum, uint32_t slotNum, bool relative, int64_t *timeDev); void L2_TimeAdjust(L2_INST *instPtr, const int64_t *timeDev); /** @} LinkLayer_TimeSync*/ /** * @defgroup LinkLayer_Utility * @{ */ uint8_t L2_GetNodeId(L2_INST *instPtr); uint8_t L2_GetClusterId(L2_INST *instPtr); uint8_t L2_GetHeadId(L2_INST *instPtr); L2_NODE_TYPE L2_GetNodeType(L2_INST *instPtr); L2_NODE_STATE L2_GetMainState(L2_INST *instPtr); bool L2_isStarted(L2_INST *instPtr); bool L2_isDataAvail(L2_INST *instPtr); bool L2_isCxn2Net(L2_INST *instPtr); uint32_t L2_GetFrameLen(L2_FRAME_TYPE l2FrameType, L2_SVC_RATE l2SvcRate); uint32_t L2_GetLastFrameNum(L2_INST *instPtr); uint32_t L2_GetLastSlotNum(L2_INST *instPtr); L2_FRAME_TYPE L2_GetLastFrameType(L2_INST *instPtr); L2_TOR_TYPE L2_GetLastTor(L2_INST *instPtr); uint32_t L2_GetCurrentFrameNum(L2_INST *instPtr); uint32_t L2_GetCurrentSlotNum(L2_INST *instPtr); L2_FRAME_TYPE L2_GetCurrentFrameType(L2_INST *instPtr); L2_TOR_TYPE L2_GetCurrentTor(L2_INST *instPtr); uint32_t L2_GetNextFrameNum(L2_INST *instPtr); uint32_t L2_GetNextSlotNum(L2_INST *instPtr); L2_FRAME_TYPE L2_GetNextFrameType(L2_INST *instPtr); L2_TOR_TYPE L2_GetNextTor(L2_INST *instPtr); L1_FRAME_TYPE L2_L2frame2L1frame(L2_FRAME_TYPE l2Frame, L2_SVC_RATE l2SvcRate); size_t L2_GetSvcPacketLen(L2_SVC_RATE l2SvcRate); size_t L2_GetSvcPayloadLen(L2_SVC_RATE l2SvcRate); PHY_ANT_INDEX L2_AntId2AntIndex(uint8_t antId); /** @} LinkLayer_Utility*/ #endif /* __LINK_LAYER_H_ */ /** @} LinkLayer*/