mirror of
https://gitlab.rtems.org/rtems/rtos/rtems.git
synced 2025-12-25 22:07:15 +00:00
Patch from Ian Lance Taylor <ian@airs.com>:
RTEMS permits using the SO_SNDTIMEO and SO_RCVTIMEO socket options to
set a timeout for most socket I/O operations. However, in RTEMS
4.0.0, those options do not affect connect or accept. I don't know of
any way to put a timeout on those calls in RTEMS 4.0.0; can anybody
point to one.
Since it is frequently useful to have a timeout on accept, and
sometimes useful to have a timeout on connect shorter than the BSD
system default of 75 seconds, the following patch causes SO_RCVTIMEO
to affect connect and accept.
This commit is contained in:
@@ -41,7 +41,7 @@ struct mdproc {
|
||||
* Other RTEMS/BSD glue
|
||||
*/
|
||||
struct socket;
|
||||
extern void soconnsleep (struct socket *so);
|
||||
extern int soconnsleep (struct socket *so);
|
||||
extern void soconnwakeup (struct socket *so);
|
||||
#define splnet() 0
|
||||
#define splimp() 0
|
||||
|
||||
@@ -380,11 +380,12 @@ wakeup (void *p)
|
||||
/*
|
||||
* Wait for a connection/disconnection event.
|
||||
*/
|
||||
void
|
||||
int
|
||||
soconnsleep (struct socket *so)
|
||||
{
|
||||
rtems_event_set events;
|
||||
rtems_id tid;
|
||||
rtems_status_code sc;
|
||||
|
||||
/*
|
||||
* Soak up any pending events.
|
||||
@@ -404,12 +405,18 @@ soconnsleep (struct socket *so)
|
||||
/*
|
||||
* Wait for the wakeup event.
|
||||
*/
|
||||
rtems_bsdnet_event_receive (SOSLEEP_EVENT, RTEMS_EVENT_ANY | RTEMS_WAIT, RTEMS_NO_TIMEOUT, &events);
|
||||
sc = rtems_bsdnet_event_receive (SOSLEEP_EVENT, RTEMS_EVENT_ANY | RTEMS_WAIT, so->so_rcv.sb_timeo, &events);
|
||||
|
||||
/*
|
||||
* Relinquish ownership of the socket.
|
||||
*/
|
||||
so->so_pgid = 0;
|
||||
|
||||
switch (sc) {
|
||||
case RTEMS_SUCCESSFUL: return 0;
|
||||
case RTEMS_TIMEOUT: return EWOULDBLOCK;
|
||||
default: return ENXIO;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
|
||||
@@ -211,7 +211,7 @@ connect (int s, struct sockaddr *name, int namelen)
|
||||
return -1;
|
||||
}
|
||||
while ((so->so_state & SS_ISCONNECTING) && so->so_error == 0) {
|
||||
soconnsleep (so);
|
||||
so->so_error = soconnsleep (so);
|
||||
}
|
||||
if (error == 0) {
|
||||
error = so->so_error;
|
||||
@@ -271,7 +271,7 @@ accept (int s, struct sockaddr *name, int *namelen)
|
||||
head->so_error = ECONNABORTED;
|
||||
break;
|
||||
}
|
||||
soconnsleep (head);
|
||||
head->so_error = soconnsleep (head);
|
||||
}
|
||||
if (head->so_error) {
|
||||
errno = head->so_error;
|
||||
|
||||
@@ -41,7 +41,7 @@ struct mdproc {
|
||||
* Other RTEMS/BSD glue
|
||||
*/
|
||||
struct socket;
|
||||
extern void soconnsleep (struct socket *so);
|
||||
extern int soconnsleep (struct socket *so);
|
||||
extern void soconnwakeup (struct socket *so);
|
||||
#define splnet() 0
|
||||
#define splimp() 0
|
||||
|
||||
@@ -380,11 +380,12 @@ wakeup (void *p)
|
||||
/*
|
||||
* Wait for a connection/disconnection event.
|
||||
*/
|
||||
void
|
||||
int
|
||||
soconnsleep (struct socket *so)
|
||||
{
|
||||
rtems_event_set events;
|
||||
rtems_id tid;
|
||||
rtems_status_code sc;
|
||||
|
||||
/*
|
||||
* Soak up any pending events.
|
||||
@@ -404,12 +405,18 @@ soconnsleep (struct socket *so)
|
||||
/*
|
||||
* Wait for the wakeup event.
|
||||
*/
|
||||
rtems_bsdnet_event_receive (SOSLEEP_EVENT, RTEMS_EVENT_ANY | RTEMS_WAIT, RTEMS_NO_TIMEOUT, &events);
|
||||
sc = rtems_bsdnet_event_receive (SOSLEEP_EVENT, RTEMS_EVENT_ANY | RTEMS_WAIT, so->so_rcv.sb_timeo, &events);
|
||||
|
||||
/*
|
||||
* Relinquish ownership of the socket.
|
||||
*/
|
||||
so->so_pgid = 0;
|
||||
|
||||
switch (sc) {
|
||||
case RTEMS_SUCCESSFUL: return 0;
|
||||
case RTEMS_TIMEOUT: return EWOULDBLOCK;
|
||||
default: return ENXIO;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
|
||||
@@ -211,7 +211,7 @@ connect (int s, struct sockaddr *name, int namelen)
|
||||
return -1;
|
||||
}
|
||||
while ((so->so_state & SS_ISCONNECTING) && so->so_error == 0) {
|
||||
soconnsleep (so);
|
||||
so->so_error = soconnsleep (so);
|
||||
}
|
||||
if (error == 0) {
|
||||
error = so->so_error;
|
||||
@@ -271,7 +271,7 @@ accept (int s, struct sockaddr *name, int *namelen)
|
||||
head->so_error = ECONNABORTED;
|
||||
break;
|
||||
}
|
||||
soconnsleep (head);
|
||||
head->so_error = soconnsleep (head);
|
||||
}
|
||||
if (head->so_error) {
|
||||
errno = head->so_error;
|
||||
|
||||
@@ -41,7 +41,7 @@ struct mdproc {
|
||||
* Other RTEMS/BSD glue
|
||||
*/
|
||||
struct socket;
|
||||
extern void soconnsleep (struct socket *so);
|
||||
extern int soconnsleep (struct socket *so);
|
||||
extern void soconnwakeup (struct socket *so);
|
||||
#define splnet() 0
|
||||
#define splimp() 0
|
||||
|
||||
@@ -380,11 +380,12 @@ wakeup (void *p)
|
||||
/*
|
||||
* Wait for a connection/disconnection event.
|
||||
*/
|
||||
void
|
||||
int
|
||||
soconnsleep (struct socket *so)
|
||||
{
|
||||
rtems_event_set events;
|
||||
rtems_id tid;
|
||||
rtems_status_code sc;
|
||||
|
||||
/*
|
||||
* Soak up any pending events.
|
||||
@@ -404,12 +405,18 @@ soconnsleep (struct socket *so)
|
||||
/*
|
||||
* Wait for the wakeup event.
|
||||
*/
|
||||
rtems_bsdnet_event_receive (SOSLEEP_EVENT, RTEMS_EVENT_ANY | RTEMS_WAIT, RTEMS_NO_TIMEOUT, &events);
|
||||
sc = rtems_bsdnet_event_receive (SOSLEEP_EVENT, RTEMS_EVENT_ANY | RTEMS_WAIT, so->so_rcv.sb_timeo, &events);
|
||||
|
||||
/*
|
||||
* Relinquish ownership of the socket.
|
||||
*/
|
||||
so->so_pgid = 0;
|
||||
|
||||
switch (sc) {
|
||||
case RTEMS_SUCCESSFUL: return 0;
|
||||
case RTEMS_TIMEOUT: return EWOULDBLOCK;
|
||||
default: return ENXIO;
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
|
||||
@@ -211,7 +211,7 @@ connect (int s, struct sockaddr *name, int namelen)
|
||||
return -1;
|
||||
}
|
||||
while ((so->so_state & SS_ISCONNECTING) && so->so_error == 0) {
|
||||
soconnsleep (so);
|
||||
so->so_error = soconnsleep (so);
|
||||
}
|
||||
if (error == 0) {
|
||||
error = so->so_error;
|
||||
@@ -271,7 +271,7 @@ accept (int s, struct sockaddr *name, int *namelen)
|
||||
head->so_error = ECONNABORTED;
|
||||
break;
|
||||
}
|
||||
soconnsleep (head);
|
||||
head->so_error = soconnsleep (head);
|
||||
}
|
||||
if (head->so_error) {
|
||||
errno = head->so_error;
|
||||
|
||||
Reference in New Issue
Block a user