SOCKETPAIR(2): Port to RTEMS

This commit is contained in:
Sebastian Huber 2015-11-16 09:51:44 +01:00
parent 5aa22c60af
commit d1558f38f7
4 changed files with 86 additions and 2 deletions

View File

@ -815,12 +815,13 @@ done1:
return (error); return (error);
} }
#ifndef __rtems__
int int
kern_socketpair(struct thread *td, int domain, int type, int protocol, kern_socketpair(struct thread *td, int domain, int type, int protocol,
int *rsv) int *rsv)
{ {
#ifndef __rtems__
struct filedesc *fdp = td->td_proc->p_fd; struct filedesc *fdp = td->td_proc->p_fd;
#endif /* __rtems__ */
struct file *fp1, *fp2; struct file *fp1, *fp2;
struct socket *so1, *so2; struct socket *so1, *so2;
int fd, error, oflag, fflag; int fd, error, oflag, fflag;
@ -829,10 +830,12 @@ kern_socketpair(struct thread *td, int domain, int type, int protocol,
oflag = 0; oflag = 0;
fflag = 0; fflag = 0;
#ifndef __rtems__
if ((type & SOCK_CLOEXEC) != 0) { if ((type & SOCK_CLOEXEC) != 0) {
type &= ~SOCK_CLOEXEC; type &= ~SOCK_CLOEXEC;
oflag |= O_CLOEXEC; oflag |= O_CLOEXEC;
} }
#endif /* __rtems__ */
if ((type & SOCK_NONBLOCK) != 0) { if ((type & SOCK_NONBLOCK) != 0) {
type &= ~SOCK_NONBLOCK; type &= ~SOCK_NONBLOCK;
fflag |= FNONBLOCK; fflag |= FNONBLOCK;
@ -898,22 +901,53 @@ free1:
return (error); return (error);
} }
#ifdef __rtems__
static
#endif /* __rtems__ */
int int
sys_socketpair(struct thread *td, struct socketpair_args *uap) sys_socketpair(struct thread *td, struct socketpair_args *uap)
{ {
#ifndef __rtems__
int error, sv[2]; int error, sv[2];
#else /* __rtems__ */
int error;
int *sv = uap->rsv;
#endif /* __rtems__ */
error = kern_socketpair(td, uap->domain, uap->type, error = kern_socketpair(td, uap->domain, uap->type,
uap->protocol, sv); uap->protocol, sv);
if (error) if (error)
return (error); return (error);
#ifndef __rtems__
error = copyout(sv, uap->rsv, 2 * sizeof(int)); error = copyout(sv, uap->rsv, 2 * sizeof(int));
if (error) { if (error) {
(void)kern_close(td, sv[0]); (void)kern_close(td, sv[0]);
(void)kern_close(td, sv[1]); (void)kern_close(td, sv[1]);
} }
#endif /* __rtems__ */
return (error); return (error);
} }
#ifdef __rtems__
int
socketpair(int domain, int type, int protocol, int *socket_vector)
{
struct thread *td = rtems_bsd_get_curthread_or_null();
struct socketpair_args ua = {
.domain = domain,
.type = type,
.protocol = protocol,
.rsv = socket_vector
};
int error;
if (td != NULL) {
error = sys_socketpair(td, &ua);
} else {
error = ENOMEM;
}
return rtems_bsd_error_to_status_and_errno(error);
}
#endif /* __rtems__ */ #endif /* __rtems__ */
#ifdef __rtems__ #ifdef __rtems__

View File

@ -481,13 +481,13 @@ struct shutdown_args {
char s_l_[PADL_(int)]; int s; char s_r_[PADR_(int)]; char s_l_[PADL_(int)]; int s; char s_r_[PADR_(int)];
char how_l_[PADL_(int)]; int how; char how_r_[PADR_(int)]; char how_l_[PADL_(int)]; int how; char how_r_[PADR_(int)];
}; };
#ifndef __rtems__
struct socketpair_args { struct socketpair_args {
char domain_l_[PADL_(int)]; int domain; char domain_r_[PADR_(int)]; char domain_l_[PADL_(int)]; int domain; char domain_r_[PADR_(int)];
char type_l_[PADL_(int)]; int type; char type_r_[PADR_(int)]; char type_l_[PADL_(int)]; int type; char type_r_[PADR_(int)];
char protocol_l_[PADL_(int)]; int protocol; char protocol_r_[PADR_(int)]; char protocol_l_[PADL_(int)]; int protocol; char protocol_r_[PADR_(int)];
char rsv_l_[PADL_(int *)]; int * rsv; char rsv_r_[PADR_(int *)]; char rsv_l_[PADL_(int *)]; int * rsv; char rsv_r_[PADR_(int *)];
}; };
#ifndef __rtems__
struct mkdir_args { struct mkdir_args {
char path_l_[PADL_(char *)]; char * path; char path_r_[PADR_(char *)]; char path_l_[PADL_(char *)]; char * path; char path_r_[PADR_(char *)];
char mode_l_[PADL_(int)]; int mode; char mode_r_[PADR_(int)]; char mode_l_[PADL_(int)]; int mode; char mode_r_[PADR_(int)];

View File

@ -98,6 +98,8 @@ int shutdown(int, int);
int socket(int, int, int); int socket(int, int, int);
int socketpair(int, int, int, int *);
int sysctl(const int *, u_int, void *, size_t *, const void *, size_t); int sysctl(const int *, u_int, void *, size_t *, const void *, size_t);
int sysctlbyname(const char *, void *, size_t *, const void *, size_t); int sysctlbyname(const char *, void *, size_t *, const void *, size_t);

View File

@ -1359,6 +1359,53 @@ test_socket_poll(void)
assert(rtems_resource_snapshot_check(&snapshot)); assert(rtems_resource_snapshot_check(&snapshot));
} }
static void
no_mem_socket_pair(int fd)
{
int sd[2];
int rv;
errno = 0;
rv = socketpair(PF_UNIX, SOCK_DGRAM, 0, &sd[0]);
assert(rv == -1);
assert(errno == ENOMEM);
}
static void
test_socket_pair(void)
{
rtems_resource_snapshot snapshot;
int sd[2];
int rv;
char in[] = { 'x' };
char out[] = { 'o' };
ssize_t n;
puts("test socket pair");
rtems_resource_snapshot_take(&snapshot);
rv = socketpair(PF_UNIX, SOCK_DGRAM, 0, &sd[0]);
assert(rv == 0);
n = write(sd[0], &out[0], sizeof(out));
assert(n == (ssize_t)sizeof(out));
n = read(sd[1], &in[0], sizeof(in));
assert(n == (ssize_t)sizeof(in));
assert(memcmp(&in[0], &out[0], sizeof(in)) == 0);
rv = close(sd[0]);
assert(rv == 0);
rv = close(sd[1]);
assert(rv == 0);
do_no_mem_test(no_mem_socket_pair, -1);
assert(rtems_resource_snapshot_check(&snapshot));
}
static void static void
test_kqueue_unsupported_ops(void) test_kqueue_unsupported_ops(void)
@ -1754,6 +1801,7 @@ test_main(void)
test_socket_recv_and_recvfrom_and_recvmsg(); test_socket_recv_and_recvfrom_and_recvmsg();
test_socket_select(); test_socket_select();
test_socket_poll(); test_socket_poll();
test_socket_pair();
test_kqueue_unsupported_ops(); test_kqueue_unsupported_ops();
test_kqueue_fstat(); test_kqueue_fstat();