The purpose of the following portion of code is to poll on a socket fd-set and if data (ssl encrypted) is available, read it and decrypt it by openssl library. The underlying transport layer is TCP Stream, so data comes as stream (not packet).
Now, if more than one packets (lets assume 2 packets of length 85 bytes) are sent in quick succession from the peer, then TCP receive will return both the packets in same buffer with Number of Bytes received as 170. So, we have one buffer that carries 2 ssl encrypted packets (or n number of packets). For ssl decryption, we need to call BIO_write() to write the buffer into ssl_bio and then ssl_read() to retrieve the decrypted buffer. But though BIO_write() is writing 170 bytes into the bio, it seems like ssl_read() is only returning one decrypted packet (43 bytes). There is no error returned. How to know if there is still unprocessed bytes in the bio. Is there any way out or is there any bug in the code?
The code is working fine when single packets are received in tcp recv().
int iReadyFds = poll( PollFdSet, iFdCount, iTimeout);
for(iFdIndx = 0; iFdIndx < (iFdCount) && (iReadyFds>0); ++iFdIndx)
{
if((PollFdSet[iFdIndx].events == 0) ||
(PollFdSet[iFdIndx].fd == 0) ||
(PollFdSet[iFdIndx].revents != POLLIN)
)
{
continue;
}
/* we have data to read */
int iMsgLen = 0;
int iFd = PollFdSet[iFdIndx].fd;
/*This is TCP Receive. Returns 170 bytes*/
iRcvdBytes = recv( iSocketId, ( void* )pcInBuffer, PN_TCP_STREAM_MAX_RX_BUFF_SIZE, 0 );
/*Writing into SSL BIO, this will be retrieved by ssl_read*/
/*iNoOFBytes = 170*/
iNoOFBytes = BIO_write(m_pRead_bio, pcInBuffer, iRcvdBytes);
if(iNoOFBytes <= 0)
{
printf("Error");
return -1;
}
char* pcDecodedBuff = (char*)malloc(1024);
/*here it returns 43 bytes of decrypted buffer(1 packet). the other packet vanishes*/
iReadData = SSL_read(m_psSSL, pcDecodedBuff, 1024);
if ((iReadData == -1) || (iReadData == 0))
{
error = SSL_get_error(psPskTls->m_psSSL, iReadData);
if(error == SSL_ERROR_ZERO_RETURN
|| error == SSL_ERROR_NONE
|| error == SSL_ERROR_WANT_READ)
{
printf("Error");
}
}
iReadyFds--;
}