lwip_fcntl() returns access modes

This commit is contained in:
Joan Lledó 2017-03-29 12:45:17 +02:00 committed by goldsimon
parent 33e3ee0790
commit 172dab1289
3 changed files with 33 additions and 3 deletions

View File

@ -3149,13 +3149,15 @@ lwip_ioctl(int s, long cmd, void *argp)
/** A minimal implementation of fcntl.
* Currently only the commands F_GETFL and F_SETFL are implemented.
* Only the flag O_NONBLOCK is implemented.
* The flag O_NONBLOCK and access modes are supported for F_GETFL, only
* the flag O_NONBLOCK is implemented for F_SETFL.
*/
int
lwip_fcntl(int s, int cmd, int val)
{
struct lwip_sock *sock = get_socket(s);
int ret = -1;
int op_mode = 0;
if (!sock) {
return -1;
@ -3165,6 +3167,25 @@ lwip_fcntl(int s, int cmd, int val)
case F_GETFL:
ret = netconn_is_nonblocking(sock->conn) ? O_NONBLOCK : 0;
sock_set_errno(sock, 0);
if (NETCONNTYPE_GROUP(netconn_type(sock->conn)) == NETCONN_TCP) {
#if LWIP_TCPIP_CORE_LOCKING
LOCK_TCPIP_CORE();
LWIP_ASSERT("sock->conn->pcb.tcp != NULL", sock->conn->pcb.tcp != NULL);
if(!(sock->conn->pcb.tcp->flags & TF_RXCLOSED)) {
op_mode |= O_RDONLY;
}
if (!(sock->conn->pcb.tcp->flags & TF_FIN)) {
op_mode |= O_WRONLY;
}
UNLOCK_TCPIP_CORE();
#endif /* !LWIP_TCPIP_CORE_LOCKING */
} else {
op_mode |= O_RDWR;
}
ret |= (op_mode == (O_RDONLY|O_WRONLY)) ? O_RDWR : op_mode;
break;
case F_SETFL:
if ((val & ~O_NONBLOCK) == 0) {

View File

@ -374,6 +374,15 @@ typedef struct ip_mreq {
#ifndef O_NDELAY
#define O_NDELAY 1 /* same as O_NONBLOCK, for compatibility */
#endif
#ifndef O_RDONLY
#define O_RDONLY 2
#endif
#ifndef O_WRONLY
#define O_WRONLY 4
#endif
#ifndef O_RDWR
#define O_RDWR (O_RDONLY|O_WRONLY)
#endif
#ifndef SHUT_RD
#define SHUT_RD 0

View File

@ -254,8 +254,8 @@ static void test_sockets_msgapi_tcp(int domain)
/* set s2 to non-blocking, not inherited from listener */
opt = lwip_fcntl(s2, F_GETFL, 0);
fail_unless(opt == 0);
opt |= O_NONBLOCK;
fail_unless(opt == 6);
opt = O_NONBLOCK;
ret = lwip_fcntl(s2, F_SETFL, opt);
fail_unless(ret == 0);