1013 lines
		
	
	
		
			28 KiB
		
	
	
	
		
			C
		
	
	
	
	
	
		
		
			
		
	
	
			1013 lines
		
	
	
		
			28 KiB
		
	
	
	
		
			C
		
	
	
	
	
	
|  | /****************************************************************************
 | ||
|  | 
 | ||
|  | Copyright(c) 2019 by Aerospace C.Power (Chongqing) Microelectronics. ALL RIGHTS RESERVED. | ||
|  | 
 | ||
|  | This Information is proprietary to Aerospace C.Power (Chongqing) Microelectronics and MAY NOT | ||
|  | be copied by any method or incorporated into another program without | ||
|  | the express written consent of Aerospace C.Power. This Information or any portion | ||
|  | thereof remains the property of Aerospace C.Power. The Information contained herein | ||
|  | is believed to be accurate and Aerospace C.Power assumes no responsibility or | ||
|  | liability for its use in any way and conveys no license or title under | ||
|  | any patent or copyright and makes no representation or warranty that this | ||
|  | Information is free from patent or copyright infringement. | ||
|  | 
 | ||
|  | ****************************************************************************/ | ||
|  | 
 | ||
|  | /* os shim includes */ | ||
|  | #include "os_types.h"
 | ||
|  | #include "os_mem.h"
 | ||
|  | #include "os_task.h"
 | ||
|  | #include "os_event.h"
 | ||
|  | 
 | ||
|  | /* common includes */ | ||
|  | #include "iot_module.h"
 | ||
|  | #include "iot_queue.h"
 | ||
|  | #include "iot_errno.h"
 | ||
|  | #include "iot_bitops.h"
 | ||
|  | #include "iot_io.h"
 | ||
|  | #include "iot_plc_pm_api.h"
 | ||
|  | #include "iot_task_api.h"
 | ||
|  | 
 | ||
|  | /* mac module internal includes */ | ||
|  | #include "mac.h"
 | ||
|  | #include "mac_msg.h"
 | ||
|  | #include "beacon.h"
 | ||
|  | #include "mac_vdev.h"
 | ||
|  | #include "mac_pdev.h"
 | ||
|  | #include "sw_sched.h"
 | ||
|  | #include "mac_data.h"
 | ||
|  | #include "mac_rx_hw.h"
 | ||
|  | #include "mac_cert_test.h"
 | ||
|  | #include "mac_sched.h"
 | ||
|  | #include "mac_zc.h"
 | ||
|  | #include "mac_ppm_scan.h"
 | ||
|  | #include "mac_reset.h"
 | ||
|  | #include "mac_pm.h"
 | ||
|  | #include "mac_channel.h"
 | ||
|  | #include "mac_check_spur_cco.h"
 | ||
|  | #include "mac_check_spur_sta.h"
 | ||
|  | 
 | ||
|  | /* public api includes */ | ||
|  | #include "plc_fr.h"
 | ||
|  | 
 | ||
|  | #include "mac_pdev.h"
 | ||
|  | #include "mac_dbg_pkt_mode.h"
 | ||
|  | #include "mac_hplc_ext.h"
 | ||
|  | #include "mac_channel_tools.h"
 | ||
|  | #include "mac_hw_tsfm.h"
 | ||
|  | #include "mac_rf_cert_test.h"
 | ||
|  | #include "mac_rf_scan.h"
 | ||
|  | 
 | ||
|  | #if HPLC_RF_DEV_SUPPORT
 | ||
|  | #include "mac_rf_rx_hw.h"
 | ||
|  | #include "mac_rf_rx_buf_ring.h"
 | ||
|  | #endif
 | ||
|  | 
 | ||
|  | /* define the quota of each mac message queue. 0 means disable quota.
 | ||
|  |  * quota rule: | ||
|  |  * 1. quota disabled queues first | ||
|  |  * 2. then quota available queues | ||
|  |  * 3. quota exhausted queues last | ||
|  |  */ | ||
|  | static uint8_t g_mac_msg_q_quota[MAC_MSG_QUEUE_MAX_PRIO] = | ||
|  | { | ||
|  |     /* MAC_MSG_QUEUE_HP */ | ||
|  |     0, | ||
|  |     /* MAC_MSG_QUEUE_MP */ | ||
|  |     2, | ||
|  |     /* MAC_MSG_QUEUE_LP */ | ||
|  |     1 | ||
|  | }; | ||
|  | 
 | ||
|  | static void mac_handle_msg_mac(mac_global_t * glb,mac_msg_t * msg) | ||
|  | { | ||
|  |     (void)glb; | ||
|  | 
 | ||
|  |     switch (msg->id) { | ||
|  |     case MAC_MSG_ID_MAC_WARM_RESET_WAR: | ||
|  |     { | ||
|  |         mac_warm_reset_war(msg->data1); | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_MAC_DEBUG_TX_HANG: | ||
|  |     { | ||
|  |         mac_tx_hang_handle(); | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_MAC_ZC_SET_FUNC_CMD: | ||
|  |     { | ||
|  |         mac_zc_set_func_cmd_internal(msg->data1 & 0xFF, | ||
|  |             (msg->data1 >> 8) & 0xFF, msg->data2); | ||
|  |         break; | ||
|  |     } | ||
|  |     default: | ||
|  |         IOT_ASSERT(0); | ||
|  |         break; | ||
|  |     } | ||
|  | } | ||
|  | static void mac_handle_msg_cvg(mac_global_t *glb, mac_msg_t *msg) | ||
|  | { | ||
|  |     uint8_t pdev_id, vdev_id, tmp, sn; | ||
|  |     uint8_t stop_band_scan_flag = 0; | ||
|  |     (void)glb; | ||
|  | 
 | ||
|  |     switch (msg->id) { | ||
|  |     case MAC_MSG_ID_CVG_START_BC: | ||
|  |     { | ||
|  |         pdev_id = (msg->data1 >> 8) & 0xFF; | ||
|  |         vdev_id = msg->data1 & 0xFF; | ||
|  |         mac_start_beacon_internal(pdev_id, vdev_id); | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_CVG_STOP_BC: | ||
|  |     { | ||
|  |         pdev_id = (msg->data1 >> 8) & 0xFF; | ||
|  |         vdev_id = msg->data1 & 0xFF; | ||
|  |         mac_stop_beacon_internal(pdev_id, vdev_id); | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_CVG_UPDATE_BC: | ||
|  |     { | ||
|  |         pdev_id = (msg->data1 >> 8) & 0xFF; | ||
|  |         vdev_id = msg->data1 & 0xFF; | ||
|  |         msg->data1 = mac_update_beacon_internal(pdev_id, vdev_id, msg->data2, | ||
|  |             &tmp); | ||
|  |         msg->data2 = (void *)((uint32_t)tmp); | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_CVG_CREATE_VDEV: | ||
|  |     { | ||
|  |         pdev_id = (uint8_t)(msg->data1 & 0xFF); | ||
|  |         vdev_id = msg->data1 & 0xFF; | ||
|  |         msg->data1 = mac_create_vdev_internal(pdev_id, &vdev_id, msg->data2); | ||
|  | #if PLC_SUPPORT_DBG_PKT_MODE
 | ||
|  |         /* since the PLC_DEFAULT_VDEV == 0, then it must create cvg call
 | ||
|  |          * vdev first. | ||
|  |          */ | ||
|  |         //TODO: will fix create dbg pkt vdev in create vdev function
 | ||
|  |         mac_create_dbg_pkt_vdev(pdev_id, msg->data2); | ||
|  | #endif
 | ||
|  |         msg->data2 = (void *)((uint32_t)vdev_id); | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_CVG_START_VDEV: | ||
|  |     { | ||
|  |         pdev_id = (msg->data1 >> 8) & 0xFF; | ||
|  |         vdev_id = msg->data1 & 0xFF; | ||
|  |         msg->data1 = mac_start_vdev_internal(pdev_id, vdev_id, msg->data2); | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_CVG_SET_VDEV_CFG: | ||
|  |     { | ||
|  |         pdev_id = (msg->data1 >> 8) & 0xFF; | ||
|  |         vdev_id = msg->data1 & 0xFF; | ||
|  |         msg->data1 = mac_set_vdev_cfg_internal(pdev_id, vdev_id, msg->data2); | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_CVG_STOP_VDEV: | ||
|  |     { | ||
|  |         pdev_id = (msg->data1 >> 8) & 0xFF; | ||
|  |         vdev_id = msg->data1 & 0xFF; | ||
|  |         msg->data1 = mac_stop_vdev_internal(pdev_id, vdev_id); | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_CVG_MSDU_SEND: | ||
|  |     { | ||
|  |         iot_pkt_t* msdu_buf; | ||
|  |         pdev_id = (msg->data1 >> 8) & 0xFF; | ||
|  |         vdev_id = msg->data1 & 0xFF; | ||
|  |         msdu_buf = msg->data2; | ||
|  |         mac_tx_info *tx_info = msg->data3; | ||
|  |         if (tx_info->is_rf_data) { | ||
|  |             msg->data1 = mac_send_rf_msdu_ex_internal(pdev_id, vdev_id, | ||
|  |                 msdu_buf, msg->data3); | ||
|  |         } else { | ||
|  |             msg->data1 = mac_send_msdu_ex_internal(pdev_id, vdev_id, | ||
|  |                 msdu_buf, msg->data3); | ||
|  |         } | ||
|  |         /* if no memery,then free buf */ | ||
|  |         if (ERR_OK != msg->data1) { | ||
|  |             iot_pkt_free_tx_done(msdu_buf, IOT_PKT_STATE_TX_FAIL); | ||
|  |             msg->data2 = NULL; | ||
|  |         } | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_CVG_CERT_MODE_SEL: | ||
|  |     { | ||
|  |         uint8_t mt_mode_sel = msg->data1 & 0xFF; | ||
|  |         mac_cert_test_g_set(mt_mode_sel); | ||
|  |         stop_band_scan_flag = 1; | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_CVG_CERT_BAND: | ||
|  |     { | ||
|  |         uint8_t band_id; | ||
|  |         band_id = msg->data1 & 0xFF; | ||
|  |         mac_cert_test_band_cfg(band_id); | ||
|  |         stop_band_scan_flag = 1; | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_CVG_CERT_TONEMASK: | ||
|  |     { | ||
|  |         uint8_t tonemask_id; | ||
|  |         tonemask_id = msg->data1 & 0xFF; | ||
|  |         mac_cert_test_tonemast_cfg(tonemask_id); | ||
|  |         stop_band_scan_flag = 1; | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_CVG_SET_PDEV_CFG: | ||
|  |     { | ||
|  |         cfg_data_tlv *tlv = (cfg_data_tlv *)msg->data2; | ||
|  | 
 | ||
|  |         pdev_id = msg->data1 & 0xFF; | ||
|  |         msg->data1 = mac_set_pdev_cfg_internal(pdev_id, msg->data2); | ||
|  |         if (tlv->type == PLC_PDEV_CFG_SET_BAND && msg->data1 == ERR_OK) { | ||
|  |             stop_band_scan_flag = 1; | ||
|  |         } | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_CVG_START_ZC_NTB: | ||
|  |     { | ||
|  |         pdev_id = (msg->data1 >> 8) & 0xFF; | ||
|  |         vdev_id = msg->data1 & 0xFF; | ||
|  |         msg->data1 = mac_start_zc_ntb_collect_internal(pdev_id, vdev_id, | ||
|  |             (iot_pkt_t *)msg->data2); | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_CVG_EXT_FRAME_SEND: | ||
|  |     { | ||
|  |         uint8_t ext_type; | ||
|  |         pdev_id = (msg->data1 >> 24) & 0xFF; | ||
|  |         sn = (msg->data1 >> 16) & 0xFF; | ||
|  |         vdev_id = (msg->data1 >> 8) & 0xff; | ||
|  |         ext_type = msg->data1 & 0xFF; | ||
|  | 
 | ||
|  |         mac_send_ext_frame_internal(ext_type, pdev_id, vdev_id, msg->data2, | ||
|  |             msg->data3, sn); | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_CVG_GET_PDEV_CFG: | ||
|  |     { | ||
|  |         pdev_id = msg->data1 & 0xFF; | ||
|  |         msg->data1 = mac_get_pdev_cfg_internal(pdev_id, msg->data2); | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_CVG_HW_TSFM_SEND: | ||
|  |     { | ||
|  |         pdev_id = (msg->data1 >> 8) & 0xFF; | ||
|  |         vdev_id = msg->data1 & 0xFF; | ||
|  |         msg->data1 = mac_hw_tsfm_send_internal(pdev_id, vdev_id, msg->data2); | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_CVG_CERT_HPLC2RF: | ||
|  |     { | ||
|  |         uint8_t phr_mcs = (msg->data1 >> 16) & 0xFF; | ||
|  |         uint8_t pld_mcs = (msg->data1 >> 8) & 0xFF ; | ||
|  |         uint8_t pb_idx = msg->data1 & 0xFF; | ||
|  |         mac_rf_cert_test_set_phy_hplc2rf_lp(phr_mcs, pld_mcs, pb_idx); | ||
|  |         stop_band_scan_flag = 1; | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_CVG_CERT_SEC_MODE: | ||
|  |     { | ||
|  |         mac_cert_test_sec_mode_set((uint8_t)msg->data1); | ||
|  |         stop_band_scan_flag = 1; | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_CVG_CERT_RF_CFG: | ||
|  |     { | ||
|  |         uint8_t rf_option, rf_channel; | ||
|  |         rf_channel = msg->data1 & 0xFF; | ||
|  |         rf_option = (msg->data1 >> 8) & 0xFF; | ||
|  |         mac_rf_cert_test_option_channel_cfg(rf_option, rf_channel); | ||
|  |         stop_band_scan_flag = 1; | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_CVG_GET_VDEV_CFG: | ||
|  |     { | ||
|  |         pdev_id = (msg->data1 >> 8) & 0xFF; | ||
|  |         vdev_id = msg->data1 & 0xFF; | ||
|  |         msg->data1 = mac_get_vdev_cfg_internal(pdev_id, vdev_id, msg->data2); | ||
|  |         break; | ||
|  |     } | ||
|  |     default: | ||
|  |         IOT_ASSERT(0); | ||
|  |         break; | ||
|  |     } | ||
|  | 
 | ||
|  |     mac_pdev_t *pdev = get_pdev_ptr(PLC_PDEV_ID); | ||
|  |     /* NOTE: if need stop band scan after some msg from cvg */ | ||
|  |     if (stop_band_scan_flag == 1 && | ||
|  |         !mac_scan_get_band_selected(&pdev->scan)) { | ||
|  | #if STATIC_POWER_SAVE
 | ||
|  |         /* stop power save */ | ||
|  |         mac_pm_stop(pdev); | ||
|  | #endif
 | ||
|  |         /* stop the scan to sync the bcn */ | ||
|  |         mac_scan_stop(&pdev->scan); | ||
|  |         mac_scan_set_band_selected(&pdev->scan, true); | ||
|  |         /* stop rf scan timer */ | ||
|  |         mac_rf_scan_stop(); | ||
|  |         /* set channel selected */ | ||
|  |         mac_rf_scan_set_channel_selected(1); | ||
|  |     } | ||
|  | } | ||
|  | 
 | ||
|  | static void mac_handle_msg_dsr(mac_global_t *glb, mac_msg_t *msg) | ||
|  | { | ||
|  |     (void)glb; | ||
|  | 
 | ||
|  |     switch (msg->id) { | ||
|  |     case MAC_MSG_ID_DSR_RX_TO_MSG: | ||
|  |     { | ||
|  |         void *pdev = msg->data2; | ||
|  |         uint32_t ring_id = msg->data1 & 0xFFFF; | ||
|  | 
 | ||
|  | #if HPLC_RF_DEV_SUPPORT
 | ||
|  |         if (msg->data1 & (1 << 16)) { | ||
|  |             /* rf ring */ | ||
|  |             msg->data1 = mac_rf_rx_hw_mpdu_internal(pdev, ring_id, | ||
|  |                 (uint32_t)msg->data3); | ||
|  |             rx_buf_ring_t *rf_ring; //TODO: fix to rf rx ring context
 | ||
|  | #if HW_PLATFORM == HW_PLATFORM_SIMU
 | ||
|  |             rf_ring = &((mac_rf_pdev_t*)pdev)->simu.rx_ring[ring_id]; | ||
|  | #else
 | ||
|  |             rf_ring = &((mac_rf_pdev_t*)pdev)->ring_hdl.ring[ring_id]; | ||
|  | #endif
 | ||
|  |             if (ERR_OK == msg->data1) { | ||
|  |                 /* TODO: this is assume in the same task of MAC */ | ||
|  |                 rf_ring->msg_delivered = 0; | ||
|  |             } | ||
|  |         } else | ||
|  | #endif /* HPLC_RF_DEV_SUPPORT */
 | ||
|  |         { | ||
|  |             /* plc ring */ | ||
|  |             msg->data1 = mac_rx_hw_mpdu_internal(pdev, ring_id, | ||
|  |                 (uint32_t)msg->data3); | ||
|  |             rx_buf_ring_t *plc_ring; | ||
|  | #if HW_PLATFORM == HW_PLATFORM_SIMU
 | ||
|  |             plc_ring = &((mac_pdev_t*)pdev)->simu.rx_ring[ring_id]; | ||
|  | #else
 | ||
|  |             plc_ring = &((mac_pdev_t*)pdev)->ring_hdl.ring[ring_id]; | ||
|  | #endif
 | ||
|  |             if (ERR_OK == msg->data1) { | ||
|  |                 /* TODO: this is assume in the same task of MAC */ | ||
|  |                 plc_ring->msg_delivered = 0; | ||
|  |             } | ||
|  |         } | ||
|  |         break; | ||
|  |     } | ||
|  |     default: | ||
|  |         IOT_ASSERT(0); | ||
|  |         break; | ||
|  |     } | ||
|  | } | ||
|  | 
 | ||
|  | static void mac_handle_msg_timer(mac_global_t *glb, mac_msg_t *msg) | ||
|  | { | ||
|  |     (void)glb; | ||
|  |     mac_vdev_t *vdev; | ||
|  |     uint8_t pdev_id, vdev_id; | ||
|  | 
 | ||
|  |     switch (msg->id) { | ||
|  |     case MAC_MSG_ID_SCHED_TX: | ||
|  |     { | ||
|  |         pdev_id = (msg->data1 >> 8) & 0xFF; | ||
|  |         vdev_id = msg->data1 & 0xFF; | ||
|  |         vdev = get_vdev_ptr(pdev_id, vdev_id); | ||
|  |         if (vdev) | ||
|  |             mac_sched_nn_tx(vdev); | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_ZC_TRAIN_HW_TIMER: | ||
|  |     { | ||
|  |         mac_zc_train_hw_timeout_internal(msg->data1, msg->data2); | ||
|  |         break; | ||
|  |     } | ||
|  | 
 | ||
|  | #if !PM_USE_DSR
 | ||
|  |     case MAC_MSG_ID_SYSTEM_SLEEP: | ||
|  |     { | ||
|  |         sleep_cfg_internal(msg->data2); | ||
|  |         break; | ||
|  |     } | ||
|  | #endif
 | ||
|  | 
 | ||
|  | #if K48_STA_MULTI_CHANNEL_SELECT_ENABLE
 | ||
|  |     case MAC_MSG_ID_CHANNEL_SCAN_TIMER: | ||
|  |     { | ||
|  |         iot_mac_k48sta_switch_next_channel(msg->data2); | ||
|  |         break; | ||
|  |     } | ||
|  | #endif
 | ||
|  |     case MAC_MSG_ID_CCO_CHECK_SPUR_TIMER: | ||
|  |     { | ||
|  |         /* msg->data2 point to pdev */ | ||
|  |         mac_cco_check_spur_start(msg->data2); | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_STA_CHECK_SPUR_TIMER: | ||
|  |     { | ||
|  |         mac_sta_check_spur(msg->data2); | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_STA_PERIOD_CHECK_SPUR: | ||
|  |     { | ||
|  |         mac_sta_period_check_spur(); | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_DEL_STREAM_TIMER: | ||
|  |     { | ||
|  |         mac_vdev_del_timeout_stream_internal(msg->data2, msg->data1); | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_RF_SCAN_TIMER: | ||
|  |     { | ||
|  |         mac_rf_scan_next_target(msg->data2); | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_PPM_RECORD_TIMER: | ||
|  |     { | ||
|  |         mac_ppm_record_refresh_handle(msg->data2); | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_MAC_CERT_WAR_TIMER: | ||
|  |     { | ||
|  |         mac_cert_war_trans_handle(); | ||
|  |         break; | ||
|  |     } | ||
|  |     default: | ||
|  |         IOT_ASSERT(0); | ||
|  |         break; | ||
|  |     } | ||
|  | } | ||
|  | 
 | ||
|  | static void mac_handle_msg_sch(mac_global_t *glb, mac_msg_t *msg) | ||
|  | { | ||
|  |     (void)glb; | ||
|  |     uint8_t pdev_id, vdev_id; | ||
|  | 
 | ||
|  |     switch (msg->id) { | ||
|  |     case MAC_MSG_ID_SCH_TX: | ||
|  |         /* call frame selection handler */ | ||
|  |         /* TODO: place call here ... */ | ||
|  |         pdev_id = (msg->data1 >> 8) & 0xFF; | ||
|  |         vdev_id = msg->data1 & 0xFF; | ||
|  |         mac_swsch_post_msdu(pdev_id,vdev_id); | ||
|  |         break; | ||
|  |     default: | ||
|  |         IOT_ASSERT(0); | ||
|  |         break; | ||
|  |     } | ||
|  | } | ||
|  | 
 | ||
|  | static void mac_handle_msg_pm(mac_global_t *glb, mac_msg_t *msg) | ||
|  | { | ||
|  |     (void)glb; | ||
|  |     uint8_t pdev_id, vdev_id; | ||
|  | 
 | ||
|  |     switch (msg->id) { | ||
|  |     case MAC_MSG_ID_PM_OFF: | ||
|  |     { | ||
|  |         if (msg->data1 == IOT_PLC_PM_MSG_POWER_COLLAPSED) { | ||
|  |             for(pdev_id = 0; pdev_id < MAX_PDEV_NUM; pdev_id++) { | ||
|  |                 for(vdev_id = 0; vdev_id < MAX_VDEV_NUM; vdev_id++) { | ||
|  |                     mac_pdev_t *pdev = get_pdev_ptr(pdev_id); | ||
|  |                     if(pdev->vdev[vdev_id]) { | ||
|  |                         mac_pm_rx_power_off_internal(pdev_id, vdev_id); | ||
|  |                     } | ||
|  |                 } | ||
|  |             } | ||
|  |         } else if (msg->data1 == IOT_PLC_PM_MSG_POWER_RECOVERED) { | ||
|  |             for (pdev_id = 0; pdev_id < MAX_PDEV_NUM; pdev_id++) { | ||
|  |                 for (vdev_id = 0; vdev_id < MAX_VDEV_NUM; vdev_id++) { | ||
|  |                     mac_pdev_t *pdev = get_pdev_ptr(pdev_id); | ||
|  |                     if (pdev->vdev[vdev_id]) { | ||
|  |                         mac_pm_power_recover_internal(pdev_id, vdev_id); | ||
|  |                     } | ||
|  |                 } | ||
|  |             } | ||
|  |         } | ||
|  |         break; | ||
|  |     } | ||
|  |     case MAC_MSG_ID_PWR_CHANGE: | ||
|  |     { | ||
|  |         low_pwr_for_powroff_cfg_internal(msg->data1, msg->data2); | ||
|  |         break; | ||
|  |     } | ||
|  |     default: | ||
|  |         IOT_ASSERT(0); | ||
|  |         break; | ||
|  |     } | ||
|  | } | ||
|  | 
 | ||
|  | static void mac_handle_msg_phy(mac_global_t *glb, mac_msg_t *msg) | ||
|  | { | ||
|  |     (void)glb; | ||
|  | 
 | ||
|  |     switch (msg->id) { | ||
|  | #if (IOT_STA_CONTROL_MODE == IOT_STA_CONTROL_TYPE_STA)
 | ||
|  |     case MAC_MSG_ID_CHANNEL_TEST_STOP: | ||
|  |         mac_channel_test_end_internal(); | ||
|  |         break; | ||
|  | #endif
 | ||
|  |     case MAC_MSG_ID_CHANNEL_ESTIMATED: | ||
|  |         mac_check_spur_cert(msg->data1); | ||
|  |         break; | ||
|  |     default: | ||
|  |         IOT_ASSERT(0); | ||
|  |         break; | ||
|  |     } | ||
|  | } | ||
|  | 
 | ||
|  | static void mac_handle_msg_cli(mac_global_t *glb, mac_msg_t *msg) | ||
|  | { | ||
|  |     (void)glb; | ||
|  | 
 | ||
|  |     switch (msg->id) { | ||
|  | #if (IOT_STA_CONTROL_MODE == IOT_STA_CONTROL_TYPE_STA)
 | ||
|  |     case MAC_MSG_ID_CHANNEL_DUMP_TEST: | ||
|  |         mac_channel_dump_start_internal(msg->data2); | ||
|  |         break; | ||
|  | #endif
 | ||
|  |     default: | ||
|  |         IOT_ASSERT(0); | ||
|  |         break; | ||
|  |     } | ||
|  | } | ||
|  | 
 | ||
|  | /* mac msg handling function */ | ||
|  | static inline void mac_handle_msg(mac_global_t *glb, mac_msg_t *msg) | ||
|  | { | ||
|  |     switch (msg->type) { | ||
|  |     case MAC_MSG_TYPE_CVG: | ||
|  |         mac_handle_msg_cvg(glb, msg); | ||
|  |         break; | ||
|  |     case MAC_MSG_TYPE_DSR: | ||
|  |         mac_handle_msg_dsr(glb, msg); | ||
|  |         break; | ||
|  |     case MAC_MSG_TYPE_TIMER: | ||
|  |         mac_handle_msg_timer(glb, msg); | ||
|  |         break; | ||
|  |     case MAC_MSG_TYPE_SCH: | ||
|  |         mac_handle_msg_sch(glb, msg); | ||
|  |         break; | ||
|  |     case MAC_MSG_TYPE_MAC: | ||
|  |         mac_handle_msg_mac(glb, msg); | ||
|  |         break; | ||
|  |     case MAC_MSG_TYPE_PM: | ||
|  |         mac_handle_msg_pm(glb, msg); | ||
|  |         break; | ||
|  |     case MAC_MSG_TYPE_PHY: | ||
|  |         mac_handle_msg_phy(glb, msg); | ||
|  |         break; | ||
|  |     case MAC_MSG_TYPE_CLI: | ||
|  |         mac_handle_msg_cli(glb, msg); | ||
|  |         break; | ||
|  |     default: | ||
|  |         IOT_ASSERT(0); | ||
|  |         break; | ||
|  |     } | ||
|  | 
 | ||
|  |     if (msg->sync) { | ||
|  |         /* notify message sender that message handling is done. */ | ||
|  |         mac_msg_sync_t *msg_sync = (mac_msg_sync_t *)msg; | ||
|  |         os_set_event(msg_sync->event); | ||
|  |     } else { | ||
|  |         /* free non-sync message. for sync message, message sender will
 | ||
|  |          * free it. | ||
|  |          */ | ||
|  |         mac_free_msg(msg); | ||
|  |     } | ||
|  | } | ||
|  | 
 | ||
|  | static void mac_handle_msg_cvg_cancel(mac_global_t *glb, mac_msg_t *msg) | ||
|  | { | ||
|  |     iot_printf("%s glb %p msg %lu\n", __FUNCTION__, glb, msg->id); | ||
|  | 
 | ||
|  |     switch (msg->id) { | ||
|  |     case MAC_MSG_ID_CVG_START_BC: | ||
|  |     case MAC_MSG_ID_CVG_STOP_BC: | ||
|  |     case MAC_MSG_ID_CVG_UPDATE_BC: | ||
|  |     case MAC_MSG_ID_CVG_CREATE_VDEV: | ||
|  |     case MAC_MSG_ID_CVG_START_VDEV: | ||
|  |     case MAC_MSG_ID_CVG_SET_VDEV_CFG: | ||
|  |     case MAC_MSG_ID_CVG_STOP_VDEV: | ||
|  |     case MAC_MSG_ID_CVG_MSDU_SEND: | ||
|  |     case MAC_MSG_ID_CVG_CERT_MODE_SEL: | ||
|  |     case MAC_MSG_ID_CVG_CERT_BAND: | ||
|  |     case MAC_MSG_ID_CVG_CERT_TONEMASK: | ||
|  |     case MAC_MSG_ID_CVG_SET_PDEV_CFG: | ||
|  |     case MAC_MSG_ID_CVG_START_ZC_NTB: | ||
|  |     case MAC_MSG_ID_CVG_EXT_FRAME_SEND: | ||
|  |     case MAC_MSG_ID_CVG_GET_PDEV_CFG: | ||
|  |     case MAC_MSG_ID_CVG_HW_TSFM_SEND: | ||
|  |     case MAC_MSG_ID_CVG_CERT_HPLC2RF: | ||
|  |     case MAC_MSG_ID_CVG_CERT_SEC_MODE: | ||
|  |     case MAC_MSG_ID_CVG_CERT_RF_CFG: | ||
|  |     case MAC_MSG_ID_CVG_GET_VDEV_CFG: | ||
|  |     { | ||
|  |         break; | ||
|  |     } | ||
|  |     default: | ||
|  |         IOT_ASSERT(0); | ||
|  |         break; | ||
|  |     } | ||
|  | } | ||
|  | 
 | ||
|  | static void mac_handle_msg_mac_cancel(mac_global_t *glb, mac_msg_t *msg) | ||
|  | { | ||
|  |     iot_printf("%s glb %p msg %lu\n", __FUNCTION__, glb, msg->id); | ||
|  | 
 | ||
|  |     switch (msg->id) { | ||
|  |     case MAC_MSG_ID_MAC_WARM_RESET_WAR: | ||
|  |     case MAC_MSG_ID_MAC_DEBUG_TX_HANG: | ||
|  |     case MAC_MSG_ID_MAC_ZC_SET_FUNC_CMD: | ||
|  |         break; | ||
|  |     default: | ||
|  |         IOT_ASSERT(0); | ||
|  |         break; | ||
|  |     } | ||
|  | } | ||
|  | 
 | ||
|  | static void mac_handle_msg_dsr_cancel(mac_global_t *glb, mac_msg_t *msg) | ||
|  | { | ||
|  |     iot_printf("%s glb %p msg %lu\n", __FUNCTION__, glb, msg->id); | ||
|  | 
 | ||
|  |     switch (msg->id) { | ||
|  |     case MAC_MSG_ID_DSR_RX_TO_MSG: | ||
|  |         break; | ||
|  |     default: | ||
|  |         IOT_ASSERT(0); | ||
|  |         break; | ||
|  |     } | ||
|  | } | ||
|  | 
 | ||
|  | static void mac_handle_msg_timer_cancel(mac_global_t *glb, | ||
|  |     mac_msg_t *msg) | ||
|  | { | ||
|  |     iot_printf("%s glb %p msg %lu\n", __FUNCTION__, glb, msg->id); | ||
|  | 
 | ||
|  |     switch (msg->id) { | ||
|  |     case MAC_MSG_ID_SCHED_TX: | ||
|  |         break; | ||
|  | #if !PM_USE_DSR
 | ||
|  |     case MAC_MSG_ID_SYSTEM_SLEEP: | ||
|  |         break; | ||
|  | #endif
 | ||
|  |     case MAC_MSG_ID_ZC_TRAIN_HW_TIMER: | ||
|  |         break; | ||
|  | #if K48_STA_MULTI_CHANNEL_SELECT_ENABLE
 | ||
|  |     case MAC_MSG_ID_CHANNEL_SCAN_TIMER: | ||
|  |         break; | ||
|  | #endif
 | ||
|  |     case MAC_MSG_ID_CCO_CHECK_SPUR_TIMER: | ||
|  |         break; | ||
|  |     case MAC_MSG_ID_STA_CHECK_SPUR_TIMER: | ||
|  |         break; | ||
|  |     case MAC_MSG_ID_STA_PERIOD_CHECK_SPUR: | ||
|  |         break; | ||
|  |     case MAC_MSG_ID_DEL_STREAM_TIMER: | ||
|  |         break; | ||
|  |     case MAC_MSG_ID_RF_SCAN_TIMER: | ||
|  |         break; | ||
|  |     case MAC_MSG_ID_PPM_RECORD_TIMER: | ||
|  |         break; | ||
|  |     case MAC_MSG_ID_MAC_CERT_WAR_TIMER: | ||
|  |         break; | ||
|  |     default: | ||
|  |         IOT_ASSERT(0); | ||
|  |         break; | ||
|  |     } | ||
|  | } | ||
|  | 
 | ||
|  | static void mac_handle_msg_sch_cancel(mac_global_t *glb, | ||
|  |     mac_msg_t *msg) | ||
|  | { | ||
|  |     iot_printf("%s glb %p msg %lu\n", __FUNCTION__, glb, msg->id); | ||
|  | 
 | ||
|  |     switch (msg->id) { | ||
|  |     case MAC_MSG_ID_SCH_TX: | ||
|  |         break; | ||
|  |     default: | ||
|  |         IOT_ASSERT(0); | ||
|  |         break; | ||
|  |     } | ||
|  | } | ||
|  | 
 | ||
|  | static void mac_handle_msg_pm_cancel(mac_global_t *glb, mac_msg_t *msg) | ||
|  | { | ||
|  |     iot_printf("%s glb %p msg %lu\n", __FUNCTION__, glb, msg->id); | ||
|  | 
 | ||
|  |     switch (msg->id) { | ||
|  |     case MAC_MSG_ID_PM_OFF: | ||
|  |     case MAC_MSG_ID_PWR_CHANGE: | ||
|  |         break; | ||
|  |     default: | ||
|  |         IOT_ASSERT(0); | ||
|  |         break; | ||
|  |     } | ||
|  | } | ||
|  | 
 | ||
|  | static void mac_handle_msg_phy_cancel(mac_global_t *glb, mac_msg_t *msg) | ||
|  | { | ||
|  |     iot_printf("%s glb %p msg %lu\n", __FUNCTION__, glb, msg->id); | ||
|  | 
 | ||
|  |     switch (msg->id) { | ||
|  |     case MAC_MSG_ID_CHANNEL_TEST_STOP: | ||
|  |         break; | ||
|  |     case MAC_MSG_ID_CHANNEL_ESTIMATED: | ||
|  |         break; | ||
|  |     default: | ||
|  |         IOT_ASSERT(0); | ||
|  |         break; | ||
|  |     } | ||
|  | } | ||
|  | 
 | ||
|  | static void mac_handle_msg_cli_cancel(mac_global_t *glb, mac_msg_t *msg) | ||
|  | { | ||
|  |     iot_printf("%s glb %p msg %lu\n", __FUNCTION__, glb, msg->id); | ||
|  | 
 | ||
|  |     switch (msg->id) { | ||
|  |     case MAC_MSG_ID_CHANNEL_DUMP_TEST: | ||
|  |         break; | ||
|  |     default: | ||
|  |         IOT_ASSERT(0); | ||
|  |         break; | ||
|  |     } | ||
|  | } | ||
|  | 
 | ||
|  | 
 | ||
|  | /* handle msg canceled case. message can be canceled due to various reasons.
 | ||
|  |  * each message may have different cancelation operation required. | ||
|  |  */ | ||
|  | void mac_handle_msg_cancel(mac_global_t *glb, mac_msg_t *msg) | ||
|  | { | ||
|  |     switch (msg->type) { | ||
|  |     case MAC_MSG_TYPE_CVG: | ||
|  |         mac_handle_msg_cvg_cancel(glb, msg); | ||
|  |         break; | ||
|  |     case MAC_MSG_TYPE_MAC: | ||
|  |         mac_handle_msg_mac_cancel(glb, msg); | ||
|  |         break; | ||
|  |     case MAC_MSG_TYPE_DSR: | ||
|  |         mac_handle_msg_dsr_cancel(glb, msg); | ||
|  |         break; | ||
|  |     case MAC_MSG_TYPE_TIMER: | ||
|  |         mac_handle_msg_timer_cancel(glb, msg); | ||
|  |         break; | ||
|  |     case MAC_MSG_TYPE_SCH: | ||
|  |         mac_handle_msg_sch_cancel(glb, msg); | ||
|  |         break; | ||
|  |     case MAC_MSG_TYPE_PM: | ||
|  |         mac_handle_msg_pm_cancel(glb, msg); | ||
|  |         break; | ||
|  |     case MAC_MSG_TYPE_PHY: | ||
|  |         mac_handle_msg_phy_cancel(glb, msg); | ||
|  |         break; | ||
|  |     case MAC_MSG_TYPE_CLI: | ||
|  |         mac_handle_msg_cli_cancel(glb, msg); | ||
|  |         break; | ||
|  |     default: | ||
|  |         IOT_ASSERT(0); | ||
|  |         break; | ||
|  |     } | ||
|  | 
 | ||
|  |     mac_free_msg(msg); | ||
|  | } | ||
|  | 
 | ||
|  | extern uint8_t mac_log_print_en; | ||
|  | extern void mac_tx_csma_dump(); | ||
|  | 
 | ||
|  | static void mac_main_task(void* arg) | ||
|  | { | ||
|  |     uint8_t i, j, tmp; | ||
|  |     uint32_t dsr_event; | ||
|  |     mac_global_t *glb = arg; | ||
|  |     iot_msg_entry_t *entry; | ||
|  |     mac_msg_t *msg; | ||
|  |     mac_dsr_func_t dsr; | ||
|  |     mac_msg_queue_t *pq; | ||
|  |     uint8_t quota_disbled_q_cnt = 0; | ||
|  |     uint8_t quota_enabled_q_cnt = 0; | ||
|  |     uint8_t quota_exhausted_q_cnt = 0; | ||
|  |     mac_msg_queue_t *quota_disbled_q[MAC_MSG_QUEUE_MAX_PRIO]; | ||
|  |     mac_msg_queue_t *quota_enabled_q[MAC_MSG_QUEUE_MAX_PRIO]; | ||
|  |     mac_msg_queue_t *quota_exhausted_q[MAC_MSG_QUEUE_MAX_PRIO]; | ||
|  | 
 | ||
|  |     iot_printf("%s glb %p\n", __FUNCTION__, glb); | ||
|  | 
 | ||
|  |     /* check if quota enabled and disabled queue exist */ | ||
|  |     for (i = 0; i < MAC_MSG_QUEUE_MAX_PRIO; i++) { | ||
|  |         pq = &glb->msg_q[i]; | ||
|  |         if (pq->quota_en) { | ||
|  |             quota_enabled_q[quota_enabled_q_cnt] = pq; | ||
|  |             quota_enabled_q_cnt++; | ||
|  |         } else { | ||
|  |             quota_disbled_q[quota_disbled_q_cnt] = pq; | ||
|  |             quota_disbled_q_cnt++; | ||
|  |         } | ||
|  |     } | ||
|  | 
 | ||
|  |     for (;;) { | ||
|  |         /* waiting for messages from various modules and dsr events from isr.
 | ||
|  |          * always handle dsr event firstly. | ||
|  |          */ | ||
|  |         dsr_event = os_wait_task_event_with_v(MAX_TIME); | ||
|  | 
 | ||
|  | handle_dsr: | ||
|  |         i = 0; | ||
|  |         while (dsr_event) { | ||
|  |             tmp = dsr_event & 0xFF; | ||
|  |             while (tmp) { | ||
|  |                 j = iot_bitops_fls(tmp) - 1; | ||
|  |                 tmp &= ~(0x1 << j); | ||
|  |                 dsr = glb->dsr_table.entry[i + j].dsr; | ||
|  |                 if (dsr) { | ||
|  |                     dsr(); | ||
|  |                 } | ||
|  |             } | ||
|  |             dsr_event >>= 8; | ||
|  |             i += 8; | ||
|  |         } | ||
|  | 
 | ||
|  | handle_msg: | ||
|  |         /* check quota disabled queue */ | ||
|  |         if (quota_disbled_q_cnt) { | ||
|  |             /* check message queues based on priority */ | ||
|  |             for (i = 0; i < quota_disbled_q_cnt; i++) { | ||
|  |                 pq = quota_disbled_q[i]; | ||
|  |                 entry = iot_msg_queue_get(&pq->q); | ||
|  |                 if (entry) { | ||
|  |                     /* get message and handle it */ | ||
|  |                     msg = container_of(entry, mac_msg_t, link); | ||
|  |                     mac_handle_msg(glb, msg); | ||
|  |                     /* check if any dsr event pending */ | ||
|  |                     dsr_event = os_wait_task_event_with_v(0); | ||
|  |                     if (dsr_event) | ||
|  |                         goto handle_dsr; | ||
|  |                     /* always search from highest priority queue with quota
 | ||
|  |                      * disabled. | ||
|  |                      */ | ||
|  |                     goto handle_msg; | ||
|  |                 } | ||
|  |             } | ||
|  |         } | ||
|  | 
 | ||
|  |         /* check quota enabled queue */ | ||
|  |         if (quota_enabled_q_cnt) { | ||
|  |             quota_exhausted_q_cnt = 0; | ||
|  |             /* check message queues based on priority */ | ||
|  |             for (i = 0; i < quota_enabled_q_cnt; i++) { | ||
|  |                 pq = quota_enabled_q[i]; | ||
|  |                 /* check if quota available for this queue */ | ||
|  |                 if (pq->curr_quota == 0) { | ||
|  |                     quota_exhausted_q[quota_exhausted_q_cnt] = pq; | ||
|  |                     quota_exhausted_q_cnt++; | ||
|  |                     continue; | ||
|  |                 } | ||
|  |                 entry = iot_msg_queue_get(&pq->q); | ||
|  |                 if (entry) { | ||
|  |                     /* get message and handle it */ | ||
|  |                     msg = container_of(entry, mac_msg_t, link); | ||
|  |                     mac_handle_msg(glb, msg); | ||
|  |                     pq->curr_quota--; | ||
|  |                     /* check if any dsr event pending */ | ||
|  |                     dsr_event = os_wait_task_event_with_v(0); | ||
|  |                     if (dsr_event) | ||
|  |                         goto handle_dsr; | ||
|  |                     /* always search from highest priority queue with quota
 | ||
|  |                      * disabled. | ||
|  |                      */ | ||
|  |                     goto handle_msg; | ||
|  |                 } | ||
|  |             } | ||
|  | 
 | ||
|  |             if (quota_exhausted_q_cnt == quota_enabled_q_cnt) { | ||
|  |                 /* no quota available queue exist, re-assign quota */ | ||
|  |                 for (i = 0; i < quota_enabled_q_cnt; i++) { | ||
|  |                     pq = quota_enabled_q[i]; | ||
|  |                     pq->curr_quota = pq->quota; | ||
|  |                 } | ||
|  |                 /* always search from highest priority queue with quota
 | ||
|  |                  * disabled. | ||
|  |                  */ | ||
|  |                 goto handle_msg; | ||
|  |             } else { | ||
|  |                 /* check if any quota exhausted queue exist */ | ||
|  |                 for (i = 0; i < quota_exhausted_q_cnt; i++) { | ||
|  |                     pq = quota_exhausted_q[i]; | ||
|  |                     entry = iot_msg_queue_get(&pq->q); | ||
|  |                     if (entry) { | ||
|  |                         /* get message and handle it */ | ||
|  |                         msg = container_of(entry, mac_msg_t, link); | ||
|  |                         mac_handle_msg(glb, msg); | ||
|  |                         /* check if any dsr event pending */ | ||
|  |                         dsr_event = os_wait_task_event_with_v(0); | ||
|  |                         if (dsr_event) | ||
|  |                             goto handle_dsr; | ||
|  |                         /* always search from highest priority queue with
 | ||
|  |                          * quota disabled. | ||
|  |                          */ | ||
|  |                         goto handle_msg; | ||
|  |                     } | ||
|  |                 } | ||
|  |             } | ||
|  |         } | ||
|  |         if (mac_log_print_en) { | ||
|  |             mac_tx_csma_dump(); | ||
|  |             mac_log_print_en = 0; | ||
|  |         } | ||
|  |     } | ||
|  | } | ||
|  | 
 | ||
|  | uint32_t mac_start_task(mac_global_t *glb) | ||
|  | { | ||
|  |     uint8_t i; | ||
|  |     uint32_t ret = 0; | ||
|  |     os_task_h handle; | ||
|  | 
 | ||
|  |     /* initialize mac message queue */ | ||
|  |     for (i = 0; i < MAC_MSG_QUEUE_MAX_PRIO; i++) { | ||
|  |         ret = iot_msg_queue_init(&glb->msg_q[i].q); | ||
|  |         if (g_mac_msg_q_quota[i]) { | ||
|  |             /* enable quota for this queue */ | ||
|  |             glb->msg_q[i].quota_en = 1; | ||
|  |             glb->msg_q[i].quota = g_mac_msg_q_quota[i]; | ||
|  |             glb->msg_q[i].curr_quota = glb->msg_q[i].quota; | ||
|  |         } else { | ||
|  |             /* disable quota for this queue */ | ||
|  |             glb->msg_q[i].quota_en = 0; | ||
|  |             glb->msg_q[i].quota = 0; | ||
|  |             glb->msg_q[i].curr_quota = 0; | ||
|  |         } | ||
|  |         if (ret) { | ||
|  |             for (; i > 0; i--) { | ||
|  |                 iot_msg_queue_deinit(&glb->msg_q[i - 1].q); | ||
|  |             } | ||
|  |             goto out; | ||
|  |         } | ||
|  |     } | ||
|  | 
 | ||
|  |     /* start mac main task */ | ||
|  |     handle = os_create_task_ext(mac_main_task, glb, PLC_MAC_TASK_PRIO, | ||
|  |         PLC_MAC_STACK_SIZE, __FUNCTION__); | ||
|  | 
 | ||
|  |     iot_printf("%s glb %p\n", __FUNCTION__, glb); | ||
|  | 
 | ||
|  |     if (handle == NULL) { | ||
|  |         ret = ERR_NOMEM; | ||
|  |         goto err_task; | ||
|  |     } else { | ||
|  |         glb->task_h = handle; | ||
|  |     } | ||
|  | 
 | ||
|  |     goto out; | ||
|  | 
 | ||
|  | err_task: | ||
|  |     for (i = 0; i < MAC_MSG_QUEUE_MAX_PRIO; i++) | ||
|  |         iot_msg_queue_deinit(&glb->msg_q[i].q); | ||
|  | out: | ||
|  |     return ret; | ||
|  | } | ||
|  | 
 | ||
|  | void mac_stop_task(mac_global_t *glb) | ||
|  | { | ||
|  |     iot_msg_entry_t *entry; | ||
|  |     mac_msg_t *msg; | ||
|  |     iot_msg_queue_t *pq; | ||
|  |     uint8_t i; | ||
|  | 
 | ||
|  |     if (glb->task_h) { | ||
|  |         /* delete mac main task */ | ||
|  |         os_delete_task(glb->task_h); | ||
|  |         glb->task_h = NULL; | ||
|  | 
 | ||
|  |         for (i = 0; i < MAC_MSG_QUEUE_MAX_PRIO; i++) { | ||
|  |             pq = &glb->msg_q[i].q; | ||
|  |             entry = iot_msg_queue_get(pq); | ||
|  |             while (entry) { | ||
|  |                 /* get messages */ | ||
|  |                 msg = container_of(entry, mac_msg_t, link); | ||
|  |                 mac_handle_msg_cancel(glb, msg); | ||
|  |                 entry = iot_msg_queue_get(pq); | ||
|  |             } | ||
|  | 
 | ||
|  |             /* deinit the mac message queue */ | ||
|  |             iot_msg_queue_deinit(pq); | ||
|  |         } | ||
|  |     } | ||
|  | 
 | ||
|  |     iot_printf("%s glb %p\n", __FUNCTION__, glb); | ||
|  | } | ||
|  | 
 | ||
|  | void mac_boost_task_prio() | ||
|  | { | ||
|  |     os_set_task_prio_ext(p_mac_glb->task_h, PLC_TASK_HIGHEST_PRIO); | ||
|  | } | ||
|  | 
 | ||
|  | void mac_restore_task_prio() | ||
|  | { | ||
|  |     os_set_task_prio_ext(p_mac_glb->task_h, PLC_MAC_TASK_PRIO); | ||
|  | } |