Hello,
I'm working with C6748, NDK 2.20.05.33, BIOS 5.41.11.38, nsp_1_00_00_09.
My application uses sockets API via the NDK to provide TCP communication.
There are two task threads runinng:
AppTask - generates some data and calls the send_data(...) function.
send_data(...) - posts the data buffer into the mailbox, which the TX_Task is pending on.
TX_Task - pends on the mailbox to get the data and sends it through the connected TCP socket.
The approximate code looks like the following:
#define TX_TIMEOUT (10u) // in millisecs as well as in system ticks.
static SOCKET MySocket;
static MBX_Handle TX_MBX;
typedef struct
{
unsigned char[TX_BUFFER_SIZE] Buffer;
unsigned int Length;
}MBX_TX_Obj;
void AppTask(void)
{
unsigned char[TX_BUFFER_SIZE] data;
unsigned int length = TX_BUFFER_SIZE;
while(Running)
{
// Generate some data
if(send_data((void*)&data[0], length) == FALSE)
break;
// Update some data fields
// TSK_Sleep(TX_TIMEOUT); // Optional !!!!
}
if(Running == TRUE)
{
// Error occurred while trying to send data!!!!
}
}
void TX_Task(void)
{
static MBX_TX_Obj TX_Object;
int wBytes, sockError;
while(Connected)
{
MBX_pend(TX_MBX, &TX_Object, SYS_FOREVER);
wBytes = send(MySocket, (void*)&TX_Object.Buffer[0], TX_Object.Length, NULL);
if(wBytes < 0 || wBytes < TX_Object.Length)
{
sockError = fdError();
fdClose(MySocket);
// Handle the socket error
break;
}
}
}
Bool send_data(void* Data, Length)
{
static MBX_TX_Obj TX_Object;
TX_Object.Buffer = (unsigned char*)Data;
TX_Object.Length = Length;
if(MBX_post(TX_MBX, &TX_Object, TX_TIMEOUT) == FALSE)
{
/// Generate and fire an error event !!!!
return FALSE;
}
return TRUE;
}
Where:
- The priority of TX_Task is higher than of the AppTask, which allows the TX_Task to dequeue the data in time, and not wait till the mailbox has been filled by the AppTask.
- Assume the socket the mailbox handles are initialized elsewhere with appropriate options.
- Assume that the socket is connected to some host before the TX_Task and AppTask threads start executing.
- Assume that sequences of generating and updating data in the AppTask take zero time.
The timeout for the mailbox has to be in system clock ticks, as it is mentioned in the user guides.My system configuration for clock manager is set to generate a clock interrupt for every 1000 microseconds, which is the default setting. As far as understand, this means the input value of ticks in the MBX_post call has to be equal to the value of milliseconds, which I want my send_data(...) function to wait for appearance of an available slot in the mailbox. I have checked this issue by converting the milliseconds value into ticks via DSP/BIOS clock module APIs:
Ticks = Time * CLK_countspms()) / CLK_getprd();
It returns the same value of Time, as expected.
The issue here is that, send(..) socket API blocks till the TCP handles the appropriate data arriving, while the AppTask continues executing and pushes data objects into the mailbox till it is full. In this situation, the MBX_post(...) in the send_data(...) function must wait the TX_TIMEOUT time for available slot in the mailbox, which I do expect. But in some way, it doesn't wait the whole time, and returns FALSE.
On other hand, if I input a zero timeout in the MBX_post, and perform a TSK_Sleep(TX_TIMEOUT) instead, after each call to send_data(...), everything works perfectly, even when the TX_TIMEOUT is minimum (1).
The question is:
-Why the MBX_post returns FALSE before the TX_TIMEOUT expires
- How do I handle this mailbox issue without calling the AppTask to sleep after each call to send_data(..)?
Thank you, Anatoly.