Dear TI:
功能说明:CC1312要实现通过串口读取数据并响应输出,使用readCallback函数来实现读取中断,在函数中执行UART_read(handle, recv_buf, wantedRxBytes);函数来获取下一次数据。
然后另一个线程实现RF射频来接受信息。
出现的问题:在串口读取一次之后,只能接受一次RF的信息,当下一次串口执行一次之后又可以接受一次信息,猜想是UART_read()函数阻塞了RF的进程。这种情况怎么办?怎么让两者互相独立?
Thanks。
This thread has been locked.
If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.
您好,尝试去使用信号量去试验,
RF部分代码逻辑如下:
while(1) {
// Wait to receive a packet
EasyLink_receiveAsync(echoRxDoneCb, 0);
/* Wait indefinitely for Rx */
Semaphore_pend(echoDoneSem, BIOS_WAIT_FOREVER);
}
此处的信号量实现等待RX信号,当接收完成后post信号量。
串口部分由原来的在readcallback函数中调用uart_read函数改成Semaphore_post(echoDoneSem);
static void readCallback(UART_Handle handle, void *recv_buf, size_t size)
{
uart = handle;
if(size == 8)
{
memset(mdcmd_buf, 0, MAX_BUF_SIZE);
memcpy(mdcmd_buf,recv_buf,size);
UART_control(handle,(UART_CMD_RESERVED + 2),NULL);//清除uart_read中的buffer
Modbus_flag = true;
memset(recv_buf, 0, MAX_BUF_SIZE);
Semaphore_post(echoDoneSem);
//UART_read(handle, recv_buf, wantedRxBytes);
}
else//同时收到多条指令或着不是正确指令时
{
UART_control(handle,(UART_CMD_RESERVED + 2),NULL);//清除uart_read中的buffer
memset(recv_buf, 0, MAX_BUF_SIZE);
Semaphore_post(echoDoneSem);
//UART_read(handle, recv_buf, wantedRxBytes);
}
MD_wdg_flag = true;
}
然后在UART执行逻辑中将UART_read函数放到while循环中,并用Semaphore_pend去阻塞。如下:
while(1)
{
UART_read(uart, recv_buf, wantedRxBytes);
Semaphore_pend(echoDoneSem, BIOS_WAIT_FOREVER);
if(Modbus_flag)
{
func_unpackage(&mdcmd_buf[0], 8); //执行Modbus指令
chargeBaudFun(); //波特率是否变更
Modbus_flag = false;
}
}
如此操作不知道是不是您之前的意思,我的想法是,在阻塞的时候当RF或者readcallback有响应时执行完释放echoDoneSem,然后继续等待RF和UART。
实验的结果是,RF和UART都不工作,不知道是不是信号量的使用逻辑不对。
请帮忙查看一下。
参考RF类似的示例逻辑:
static void rxTaskFunction(UArg arg0, UArg arg1)
{
/* Init UART */
const char startPrompt[] = "Opening UART and RF:\r\n";
const char packetRxPromt[] = "Packet received \r\n";
UART_Handle uart;
UART_Params uartParams;
UART_init();
/* Create a UART with data processing off. */
UART_Params_init(&uartParams);
uartParams.writeDataMode = UART_DATA_BINARY;
uartParams.readDataMode = UART_DATA_BINARY;
uartParams.readReturnMode = UART_RETURN_FULL;
uartParams.readEcho = UART_ECHO_OFF;
uartParams.baudRate = 115200;
uart = UART_open(Board_UART0, &uartParams);
if (uart == NULL) {
/* UART_open() failed */
while (1);
}
/* Init RF */
RF_Params rfParams;
RF_Params_init(&rfParams);
if( RFQueue_defineQueue(&dataQueue,
rxDataEntryBuffer,
sizeof(rxDataEntryBuffer),
NUM_DATA_ENTRIES,
MAX_LENGTH + NUM_APPENDED_BYTES))
{
/* Failed to allocate space for all data entries */
while(1);
}
/* Modify CMD_PROP_RX command for application needs */
RF_cmdPropRx.pQueue = &dataQueue; /* Set the Data Entity queue for received data */
RF_cmdPropRx.rxConf.bAutoFlushIgnored = 1; /* Discard ignored packets from Rx queue */
RF_cmdPropRx.rxConf.bAutoFlushCrcErr = 1; /* Discard packets with CRC error from Rx queue */
RF_cmdPropRx.maxPktLen = MAX_LENGTH; /* Implement packet length filtering to avoid PROP_ERROR_RXBUF */
RF_cmdPropRx.pktConf.bRepeatOk = 1;
RF_cmdPropRx.pktConf.bRepeatNok = 1;
/* Request access to the radio */
rfHandle = RF_open(&rfObject, &RF_prop, (RF_RadioSetup*)&RF_cmdPropRadioDivSetup, &rfParams);
/* Set the frequency */
RF_postCmd(rfHandle, (RF_Op*)&RF_cmdFs, RF_PriorityNormal, NULL, 0);
/* Write to the UART before starting RX */
UART_write(uart, startPrompt, sizeof(startPrompt));
/* Enter RX mode and stay forever in RX */
RF_EventMask terminationReason = RF_postCmd(rfHandle, (RF_Op*)&RF_cmdPropRx,
RF_PriorityNormal, &callback,
RF_EventRxEntryDone);
while(1)
{
/* Waiting for packet */
Semaphore_pend(semHandle, BIOS_WAIT_FOREVER);
/* Writing packet to UART */
UART_write(uart, &packet, packetLength);
};
}
void callback(RF_Handle h, RF_CmdHandle ch, RF_EventMask e)
{
if (e & RF_EventRxEntryDone)
{
/* Toggle pin to indicate RX */
PIN_setOutputValue(pinHandle, Board_PIN_LED2,!PIN_getOutputValue(Board_PIN_LED2));
/* Get current unhandled data entry */
currentDataEntry = RFQueue_getDataEntry();
/* Handle the packet data, located at ¤tDataEntry->data:
* - Length is the first byte with the current configuration
* - Data starts from the second byte */
packetLength = *(uint8_t*)(¤tDataEntry->data);
packetDataPointer = (uint8_t*)(¤tDataEntry->data + 1);
/* Copy the payload + the status byte to the packet variable */
memcpy(packet, packetDataPointer, (packetLength + 1));
RFQueue_nextEntry();
/* Packet received */
Semaphore_post(semHandle);
}
}
/*
* ======== main ========
*/
int main(void)
{
Semaphore_Params semParams;
/* Construct a Semaphore object to be use as a resource lock, inital count 1 */
Semaphore_Params_init(&semParams);
Semaphore_construct(&semStruct, 0, &semParams);
/* Obtain instance handle */
semHandle = Semaphore_handle(&semStruct);
/* Call driver init functions. */
Board_initGeneral();
/* Open LED pins */
ledPinHandle = PIN_open(&ledPinState, pinTable);
Assert_isTrue(ledPinHandle != NULL, NULL);
/* Initialize task */
RxTask_init(ledPinHandle);
/* Start BIOS */
BIOS_start();
return (0);
}