drivers: modem: modem_socket: Fix blocking modem_socket_poll
Before this commit, if a socket had received data before calling the poll function, then the poll was waiting for either new data or a timeout. With this fix, polled socket are check for pending data before the semaphore wait. Signed-off-by: Xavier Chapron <xavier.chapron@stimio.fr>
This commit is contained in:
parent
8771fbdaac
commit
7d67991a91
1 changed files with 33 additions and 9 deletions
|
@ -267,37 +267,61 @@ int modem_socket_poll(struct modem_socket_config *cfg,
|
||||||
return -EINVAL;
|
return -EINVAL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
k_sem_reset(&cfg->sem_poll);
|
||||||
|
|
||||||
for (i = 0; i < nfds; i++) {
|
for (i = 0; i < nfds; i++) {
|
||||||
sock = modem_socket_from_fd(cfg, fds[i].fd);
|
sock = modem_socket_from_fd(cfg, fds[i].fd);
|
||||||
if (sock) {
|
if (sock) {
|
||||||
/*
|
/*
|
||||||
* Handle user check for POLLOUT events:
|
* Handle user check for POLLOUT events:
|
||||||
* we consider the socket to always be writeable.
|
* we consider the socket to always be writable.
|
||||||
*/
|
*/
|
||||||
if (fds[i].events & ZSOCK_POLLOUT) {
|
if (fds[i].events & ZSOCK_POLLOUT) {
|
||||||
fds[i].revents |= ZSOCK_POLLOUT;
|
|
||||||
found_count++;
|
found_count++;
|
||||||
|
break;
|
||||||
} else if (fds[i].events & ZSOCK_POLLIN) {
|
} else if (fds[i].events & ZSOCK_POLLIN) {
|
||||||
sock->is_polled = true;
|
sock->is_polled = true;
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Handle check done after data reception on
|
||||||
|
* the socket. In this case that was received
|
||||||
|
* but as the socket wasn't polled, no sem_poll
|
||||||
|
* semaphore was given at that time. Therefore
|
||||||
|
* if there is a polled socket with data,
|
||||||
|
* increment found_count to escape the
|
||||||
|
* k_sem_take().
|
||||||
|
*/
|
||||||
|
if (sock->packet_sizes[0] > 0U) {
|
||||||
|
found_count++;
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/* exit early if we've found rdy sockets */
|
/* Avoid waiting on semaphore if we have already found an event */
|
||||||
if (found_count) {
|
ret = 0;
|
||||||
errno = 0;
|
if (!found_count) {
|
||||||
return found_count;
|
ret = k_sem_take(&cfg->sem_poll, K_MSEC(msecs));
|
||||||
}
|
}
|
||||||
|
/* Reset counter as we reiterate on all polled sockets */
|
||||||
|
found_count = 0;
|
||||||
|
|
||||||
ret = k_sem_take(&cfg->sem_poll, K_MSEC(msecs));
|
|
||||||
for (i = 0; i < nfds; i++) {
|
for (i = 0; i < nfds; i++) {
|
||||||
sock = modem_socket_from_fd(cfg, fds[i].fd);
|
sock = modem_socket_from_fd(cfg, fds[i].fd);
|
||||||
if (!sock) {
|
if (!sock) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ((fds[i].events & ZSOCK_POLLIN) &&
|
/*
|
||||||
(sock->packet_sizes[0] > 0U)) {
|
* Handle user check for ZSOCK_POLLOUT events:
|
||||||
|
* we consider the socket to always be writable.
|
||||||
|
*/
|
||||||
|
if (fds[i].events & ZSOCK_POLLOUT) {
|
||||||
|
fds[i].revents |= ZSOCK_POLLOUT;
|
||||||
|
found_count++;
|
||||||
|
} else if ((fds[i].events & ZSOCK_POLLIN) &&
|
||||||
|
(sock->packet_sizes[0] > 0U)) {
|
||||||
fds[i].revents |= ZSOCK_POLLIN;
|
fds[i].revents |= ZSOCK_POLLIN;
|
||||||
found_count++;
|
found_count++;
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue