ssize_t BT_read(struct file *filp, char __user *buf, size_t count, loff_t *f_pos) { static int chip_reset_count; INT32 retval = 0; down(&rd_mtx); BT_DBG_FUNC("%s: count %zd pos %lld\n", __func__, count, *f_pos); if (rstflag) { if (rstflag == 1) { /* Reset start */ retval = -88; if ((chip_reset_count%500) == 0) BT_INFO_FUNC("%s: detect whole chip reset start, %d\n", __func__, chip_reset_count); chip_reset_count++; } else if (rstflag == 2) { /* Reset end */ retval = -99; BT_INFO_FUNC("%s: detect whole chip reset end\n", __func__); chip_reset_count = 0; } goto OUT; } if (count > BT_BUFFER_SIZE) { count = BT_BUFFER_SIZE; BT_ERR_FUNC("%s: count > BT_BUFFER_SIZE\n", __func__); } retval = mtk_wcn_stp_receive_data(i_buf, count, BT_TASK_INDX); while (retval == 0) { /* Got nothing, wait for STP's signal */ /* * If nonblocking mode, return directly. * O_NONBLOCK is specified during open() */ if (filp->f_flags & O_NONBLOCK) { BT_DBG_FUNC("Non-blocking BT_read\n"); retval = -EAGAIN; goto OUT; } BT_DBG_FUNC("%s: wait_event 1\n", __func__); wait_event(BT_wq, flag != 0); BT_DBG_FUNC("%s: wait_event 2\n", __func__); flag = 0; retval = mtk_wcn_stp_receive_data(i_buf, count, BT_TASK_INDX); BT_DBG_FUNC("%s: mtk_wcn_stp_receive_data returns %d\n", __func__, retval); } /* Got something from STP driver */ if (copy_to_user(buf, i_buf, retval)) { retval = -EFAULT; goto OUT; } OUT: up(&rd_mtx); BT_DBG_FUNC("%s: retval = %d\n", __func__, retval); return retval; }
ssize_t BT_read(struct file *filp, char __user *buf, size_t count, loff_t *f_pos) { int retval = 0; down(&rd_mtx); BT_DBG_FUNC("BT_read(): count %d pos %lld\n", count, *f_pos); if(retflag) { if (retflag == 1) //reset start { retval = -88; BT_INFO_FUNC("MT662x reset Read: start\n"); } else if (retflag == 2) // reset end { retval = -99; BT_INFO_FUNC("MT662x reset Read: end\n"); } goto OUT; } if(count > MTKSTP_BUFFER_SIZE) { count = MTKSTP_BUFFER_SIZE; } retval = mtk_wcn_stp_receive_data(i_buf, count, BT_TASK_INDX); while(retval == 0) // got nothing, wait for STP's signal { /*If nonblocking mode, return directly O_NONBLOCK is specified during open() */ if (filp->f_flags & O_NONBLOCK){ BT_DBG_FUNC("Non-blocking BT_read() \n"); retval = -EAGAIN; goto OUT; } BT_DBG_FUNC("BT_read(): wait_event 1\n"); wait_event(BT_wq, flag != 0); BT_DBG_FUNC("BT_read(): wait_event 2\n"); flag = 0; retval = mtk_wcn_stp_receive_data(i_buf, count, BT_TASK_INDX); BT_DBG_FUNC("BT_read(): mtk_wcn_stp_receive_data() = %d\n", retval); } // we got something from STP driver if (copy_to_user(buf, i_buf, retval)) { retval = -EFAULT; goto OUT; } OUT: up(&rd_mtx); BT_DBG_FUNC("BT_read(): retval = %d\n", retval); return (retval); }
INT32 wmt_idc_msg_to_lte_handing(VOID) { UINT32 readlen = 0; local_para_struct *p_lps = NULL; UINT8 *p_data = NULL; UINT8 opcode = 0; UINT16 msg_len = 0; UINT32 handle_len = 0; #if CFG_WMT_LTE_ENABLE_MSGID_MAPPING MTK_WCN_BOOL unknow_msgid = MTK_WCN_BOOL_FALSE; #endif readlen = mtk_wcn_stp_receive_data(&gWmtIdcInfo.buffer[0], LTE_IDC_BUFFER_MAX_SIZE, COEX_TASK_INDX); if (readlen == 0) { osal_sleep_ms(5); readlen = mtk_wcn_stp_receive_data(&gWmtIdcInfo.buffer[0], LTE_IDC_BUFFER_MAX_SIZE, COEX_TASK_INDX); } if (readlen > 0) { WMT_DBG_FUNC("read data len from fw(%d)\n", readlen); wmt_idc_dump_debug_msg("WMT->LTE from STP buffer", &gWmtIdcInfo.buffer[0], readlen); p_data = &gWmtIdcInfo.buffer[0]; while (handle_len < readlen) { p_data += 2; /*omit direction & opcode 2 bytes */ osal_memcpy(&msg_len, p_data, 2); msg_len -= 1; /*flag byte */ WMT_DBG_FUNC("current raw data len(%d) from connsys firmware\n", msg_len); p_data += 2; /*length: 2 bytes */ /*how to handle flag(msg type) need to Scott comment */ /************************************************/ if (*p_data == WMT_IDC_RX_OPCODE_DEBUG_MONITOR) /*do not need transfer to LTE */ { p_data += 1; /*flag : 1 byte */ /*need to handle these debug message */ wmt_idc_dump_debug_msg("WIFI DEBUG MONITOR", p_data, msg_len); } else /*need to transfer to LTE */ { p_lps = (local_para_struct *) osal_malloc(osal_sizeof(local_para_struct) + osal_sizeof(UINT8) * msg_len); if (NULL == p_lps) { WMT_ERR_FUNC("allocate local_para_struct memory fail\n"); return -1; } p_lps->msg_len = msg_len + osal_sizeof(local_para_struct); opcode = *p_data; WMT_DBG_FUNC("current opcode(%d) to LTE\n", opcode); p_data += 1; /*flag : 1 byte */ osal_memcpy(p_lps->data, p_data, msg_len); gWmtIdcInfo.iit.local_para_ptr = p_lps; #if CFG_WMT_LTE_ENABLE_MSGID_MAPPING switch (opcode) { case WMT_IDC_RX_OPCODE_BTWF_DEF_PARA: gWmtIdcInfo.iit.msg_id = IPC_MSG_ID_EL1_WIFIBT_OPER_DEFAULT_PARAM_IND; break; case WMT_IDC_RX_OPCODE_BTWF_CHAN_RAN: gWmtIdcInfo.iit.msg_id = IPC_MSG_ID_EL1_WIFIBT_OPER_FREQ_IND; break; case WMT_IDC_RX_OPCODE_LTE_FREQ_IDX_TABLE: gWmtIdcInfo.iit.msg_id = IPC_MSG_ID_EL1_WIFIBT_FREQ_IDX_TABLE_IND; break; case WMT_IDC_RX_OPCODE_BTWF_PROFILE_IND: gWmtIdcInfo.iit.msg_id = IPC_MSG_ID_EL1_WIFIBT_PROFILE_IND; break; case WMT_IDC_RX_OPCODE_UART_PIN_SEL: gWmtIdcInfo.iit.msg_id = IPC_MSG_ID_EL1_PIN_TYPE_IND; break; /* case WMT_IDC_RX_OPCODE_TDM_REQ: */ /* gWmtIdcInfo.iit.msg_id = IPC_MSG_ID_EL1_WIFIBT_OPER_FREQ_IND; */ /* break; */ default: unknow_msgid = MTK_WCN_BOOL_TRUE; WMT_ERR_FUNC("unknow opcode(%d) from connsys firmware\n", opcode); break; } if (MTK_WCN_BOOL_FALSE == unknow_msgid) { /*handling flag value in wmt cmd */ mtk_conn_md_bridge_send_msg(&gWmtIdcInfo.iit); } #else if (opcode >= LTE_MSG_ID_OFFSET) { gWmtIdcInfo.iit.msg_id = opcode + IPC_EL1_MSG_ID_BEGIN - LTE_MSG_ID_OFFSET + 1; /*handling flag value in wmt cmd */ mtk_conn_md_bridge_send_msg(&gWmtIdcInfo.iit); WMT_INFO_FUNC("CONN->LTE: (0x%x->0x%x)\n", opcode, gWmtIdcInfo.iit.msg_id); } else { WMT_ERR_FUNC("opcode(%d)from connsys fw is out of range,drop it!\n", opcode); } #endif osal_free(p_lps); } p_data += msg_len; /*point to next package header */ handle_len += (msg_len + 5); } } else { WMT_ERR_FUNC("there is no coex data in stp buffer\n"); } osal_memset(&gWmtIdcInfo.buffer[0], 0, LTE_IDC_BUFFER_MAX_SIZE); return 0; }
INT32 wmt_ctrl_rx(P_WMT_CTRL_DATA pWmtCtrlData/*UINT8 *pBuff, UINT32 buffLen, UINT32 *readSize*/) { P_DEV_WMT pDev = &gDevWmt; /* single instance */ INT32 readLen; LONG waitRet = -1; UINT8 *pBuff = (UINT8 *)pWmtCtrlData->au4CtrlData[0]; UINT32 buffLen = pWmtCtrlData->au4CtrlData[1]; UINT32 *readSize = (UINT32 *)pWmtCtrlData->au4CtrlData[2]; if (readSize) { *readSize = 0; } /* sanity check */ if (!buffLen ) { WMT_WARN_FUNC("buffLen = 0\n"); osal_assert(buffLen); return 0; } #if 0 if (!pDev) { WMT_WARN_FUNC("gpDevWmt = NULL\n"); osal_assert(pDev); return -1; } #endif if (!osal_test_bit(WMT_STAT_STP_OPEN, &pDev->state)) { WMT_WARN_FUNC("state(0x%lx) \n", pDev->state); osal_assert(osal_test_bit(WMT_STAT_STP_OPEN, &pDev->state)); return -2; } /* sanity ok, proceeding rx operation */ /* read_len = mtk_wcn_stp_receive_data(data, size, WMT_TASK_INDX); */ readLen = mtk_wcn_stp_receive_data(pBuff, buffLen, WMT_TASK_INDX); while (readLen == 0) { // got nothing, wait for STP's signal WMT_LOUD_FUNC("before wmt_dev_rx_timeout\n"); //iRet = wait_event_interruptible(pdev->rWmtRxWq, osal_test_bit(WMT_STAT_RX, &pdev->state)); //waitRet = wait_event_interruptible_timeout(pDev->rWmtRxWq, osal_test_bit(WMT_STAT_RX, &pdev->state), msecs_to_jiffies(WMT_LIB_RX_TIMEOUT)); pDev->rWmtRxWq.timeoutValue = WMT_LIB_RX_TIMEOUT; //waitRet = osal_wait_for_event_bit_timeout(&pDev->rWmtRxWq, &pDev->state, WMT_STAT_RX); waitRet = wmt_dev_rx_timeout(&pDev->rWmtRxWq); WMT_LOUD_FUNC("wmt_dev_rx_timeout returned\n"); if (0 == waitRet) { WMT_ERR_FUNC("wmt_dev_rx_timeout: timeout,jiffies(%lu),timeoutvalue(%d) \n", jiffies,pDev->rWmtRxWq.timeoutValue); return -1; } else if (waitRet < 0) { WMT_WARN_FUNC("wmt_dev_rx_timeout: interrupted by signal (%ld)\n", waitRet); return waitRet; } WMT_DBG_FUNC("wmt_dev_rx_timeout, iRet(%ld)\n", waitRet); /* read_len = mtk_wcn_stp_receive_data(data, size, WMT_TASK_INDX); */ readLen = mtk_wcn_stp_receive_data(pBuff, buffLen, WMT_TASK_INDX); if (0 == readLen) { WMT_WARN_FUNC("wmt_ctrl_rx be signaled, but no rx data(%ld)\n", waitRet); } WMT_DBG_FUNC("readLen(%d) \n", readLen); } if (readSize) { *readSize = readLen ; } return 0; }
ssize_t GPS_read(struct file *filp, char __user *buf, size_t count, loff_t *f_pos) { long val = 0; int retval; down(&rd_mtx); /* printk("GPS_read(): count %d pos %lld\n", count, *f_pos);*/ if(count > MTKSTP_BUFFER_SIZE) { count = MTKSTP_BUFFER_SIZE; } #if GPS_DEBUG_TRACE_GPIO mtk_wcn_stp_debug_gpio_assert(IDX_GPS_RX, DBG_TIE_LOW); #endif retval = mtk_wcn_stp_receive_data(i_buf, count, GPS_TASK_INDX); #if GPS_DEBUG_TRACE_GPIO mtk_wcn_stp_debug_gpio_assert(IDX_GPS_RX, DBG_TIE_HIGH); #endif while(retval == 0) // got nothing, wait for STP's signal { /*wait_event(GPS_wq, flag != 0);*/ /* George: let signal wake up */ val = wait_event_interruptible(GPS_wq, flag != 0); flag = 0; #if GPS_DEBUG_TRACE_GPIO mtk_wcn_stp_debug_gpio_assert(IDX_GPS_RX, DBG_TIE_LOW); #endif retval = mtk_wcn_stp_receive_data(i_buf, count, GPS_TASK_INDX); #if GPS_DEBUG_TRACE_GPIO mtk_wcn_stp_debug_gpio_assert(IDX_GPS_RX, DBG_TIE_HIGH); #endif /* if we are signaled */ if (val) { if (-ERESTARTSYS == val) { GPS_INFO_FUNC("signaled by -ERESTARTSYS(%ld) \n ", val); } else { GPS_INFO_FUNC("signaled by %ld \n ", val); } break; } } #if GPS_DEBUG_DUMP { unsigned char *buf_ptr = &i_buf[0]; int k=0; printk("--[GPS-READ]--"); for(k=0; k < 10 ; k++){ if(k%16 == 0) printk("\n"); printk("0x%02x ", i_buf[k]); } printk("--\n"); } #endif if (retval) { // we got something from STP driver if (copy_to_user(buf, i_buf, retval)) { retval = -EFAULT; goto OUT; } else { /* success */ } } else { // we got nothing from STP driver, being signaled retval = val; } OUT: up(&rd_mtx); /* printk("GPS_read(): retval = %d\n", retval);*/ return (retval); }
fm_s32 fm_event_parser(fm_s32(*rds_parser) (struct rds_rx_t *, fm_s32)) { fm_s32 len; fm_s32 i = 0; fm_u8 opcode = 0; fm_u16 length = 0; fm_u8 ch; fm_u8 rx_buf[RX_BUF_SIZE + 10] = { 0 }; /* the 10 bytes are protect gaps */ static volatile fm_task_parser_state state = FM_TASK_RX_PARSER_PKT_TYPE; struct fm_trace_t trace; struct task_struct *task = current; len = mtk_wcn_stp_receive_data(rx_buf, RX_BUF_SIZE, FM_TASK_INDX); WCN_DBG(FM_DBG | LINK, "[len=%d],[CMD=0x%02x 0x%02x 0x%02x 0x%02x]\n", len, rx_buf[0], rx_buf[1], rx_buf[2], rx_buf[3]); while (i < len) { ch = rx_buf[i]; switch (state) { case FM_TASK_RX_PARSER_PKT_TYPE: if (ch == FM_TASK_EVENT_PKT_TYPE) { if ((i + 5) < RX_BUF_SIZE) { WCN_DBG(FM_DBG | LINK, "0x%02x 0x%02x 0x%02x 0x%02x 0x%02x 0x%02x\n", rx_buf[i], rx_buf[i + 1], rx_buf[i + 2], rx_buf[i + 3], rx_buf[i + 4], rx_buf[i + 5]); } else { WCN_DBG(FM_DBG | LINK, "0x%02x 0x%02x\n", rx_buf[i], rx_buf[i + 1]); } state = FM_TASK_RX_PARSER_OPCODE; } else { WCN_DBG(FM_ALT | LINK, "event pkt type error (rx_buf[%d] = 0x%02x)\n", i, ch); } i++; break; case FM_TASK_RX_PARSER_OPCODE: i++; opcode = ch; state = FM_TASK_RX_PARSER_PKT_LEN_1; break; case FM_TASK_RX_PARSER_PKT_LEN_1: i++; length = ch; state = FM_TASK_RX_PARSER_PKT_LEN_2; break; case FM_TASK_RX_PARSER_PKT_LEN_2: i++; length |= (fm_u16) (ch << 0x8); #ifdef FM_TRACE_ENABLE trace.type = FM_TASK_EVENT_PKT_TYPE; trace.opcode = opcode; trace.len = length; trace.tid = (fm_s32) task->pid; fm_memset(trace.pkt, 0, FM_TRACE_PKT_SIZE); fm_memcpy(trace.pkt, &rx_buf[i], (length > FM_TRACE_PKT_SIZE) ? FM_TRACE_PKT_SIZE : length); if (fm_true == FM_TRACE_FULL(cmd_fifo)) { FM_TRACE_OUT(cmd_fifo, NULL); } FM_TRACE_IN(cmd_fifo, &trace); #endif if (length > 0) { state = FM_TASK_RX_PARSER_PKT_PAYLOAD; } else if (opcode == CSPI_WRITE_OPCODE) { state = FM_TASK_RX_PARSER_PKT_TYPE; FM_EVENT_SEND(link_event->ln_event, FLAG_CSPI_WRITE); } else { state = FM_TASK_RX_PARSER_PKT_TYPE; FM_EVENT_SEND(link_event->ln_event, (1 << opcode)); } break; case FM_TASK_RX_PARSER_PKT_PAYLOAD: switch (opcode) { case FM_TUNE_OPCODE: if ((length == 1) && (rx_buf[i] == 1)) { FM_EVENT_SEND(link_event->ln_event, FLAG_TUNE_DONE); } break; case FM_SOFT_MUTE_TUNE_OPCODE: if (length >= 2) { fm_memcpy(link_event->result.cqi, &rx_buf[i], (length > FM_CQI_BUF_SIZE) ? FM_CQI_BUF_SIZE : length); FM_EVENT_SEND(link_event->ln_event, FLAG_SM_TUNE); } break; case FM_SEEK_OPCODE: if ((i + 1) < RX_BUF_SIZE) { link_event->result.seek_result = rx_buf[i] + (rx_buf[i + 1] << 8); /* 8760 means 87.60Mhz */ } FM_EVENT_SEND(link_event->ln_event, FLAG_SEEK_DONE); break; case FM_SCAN_OPCODE: /* check if the result data is long enough */ if ((RX_BUF_SIZE - i) < (sizeof(fm_u16) * FM_SCANTBL_SIZE)) { WCN_DBG(FM_ALT | LINK, "FM_SCAN_OPCODE err, [tblsize=%d],[bufsize=%d]\n", (unsigned int)(sizeof(fm_u16) * FM_SCANTBL_SIZE), (unsigned int)(RX_BUF_SIZE - i)); FM_EVENT_SEND(link_event->ln_event, FLAG_SCAN_DONE); return 0; } else if ((length >= FM_CQI_BUF_SIZE) && ((RX_BUF_SIZE - i) >= FM_CQI_BUF_SIZE)) { fm_memcpy(link_event->result.cqi, &rx_buf[i], FM_CQI_BUF_SIZE); FM_EVENT_SEND(link_event->ln_event, FLAG_CQI_DONE); } else { fm_memcpy(link_event->result.scan_result, &rx_buf[i], sizeof(fm_u16) * FM_SCANTBL_SIZE); FM_EVENT_SEND(link_event->ln_event, FLAG_SCAN_DONE); } break; case FSPI_READ_OPCODE: if ((i + 1) < RX_BUF_SIZE) { link_event->result.fspi_rd = (rx_buf[i] + (rx_buf[i + 1] << 8)); } FM_EVENT_SEND(link_event->ln_event, (1 << opcode)); break; case CSPI_READ_OPCODE: { if ((i + 1) < RX_BUF_SIZE) { link_event->result.cspi_rd = (rx_buf[i] + (rx_buf[i + 1] << 8) + (rx_buf[i + 2] << 16) + (rx_buf[i + 3] << 24)); } FM_EVENT_SEND(link_event->ln_event, FLAG_CSPI_READ); break; } case FM_HOST_READ_OPCODE: { if ((i + 1) < RX_BUF_SIZE) { link_event->result.cspi_rd = (rx_buf[i] + (rx_buf[i + 1] << 8) + (rx_buf[i + 2] << 16) + (rx_buf[i + 3] << 24)); } FM_EVENT_SEND(link_event->ln_event, (1 << opcode)); break; } case RDS_RX_DATA_OPCODE: /* check if the rds data is long enough */ if ((RX_BUF_SIZE - i) < length) { WCN_DBG(FM_ALT | LINK, "RDS RX err, [rxlen=%d],[bufsize=%d]\n", (fm_s32) length, (RX_BUF_SIZE - i)); FM_EVENT_SEND(link_event->ln_event, (1 << opcode)); break; } /* copy rds data to rds buf */ fm_memcpy(&link_event->result.rds_rx_result, &rx_buf[i], length); /*Handle the RDS data that we get */ if (rds_parser) { rds_parser(&link_event->result.rds_rx_result, length); } else { WCN_DBG(FM_WAR | LINK, "no method to parse RDS data\n"); } FM_EVENT_SEND(link_event->ln_event, (1 << opcode)); break; default: FM_EVENT_SEND(link_event->ln_event, (1 << opcode)); break; } state = FM_TASK_RX_PARSER_PKT_TYPE; i += length; break; default: break; } } return 0; }