mirror of
https://gitlab.com/sortix/sortix.git
synced 2023-02-13 20:55:38 -05:00
Add getsockopt(2) and setsockopt(2).
This commit is contained in:
parent
708bcb4735
commit
a24ecf4b83
12 changed files with 174 additions and 14 deletions
|
@ -628,4 +628,16 @@ ssize_t Descriptor::send(ioctx_t* ctx, const uint8_t* buf, size_t count, int fla
|
|||
return vnode->send(ctx, buf, count, flags);
|
||||
}
|
||||
|
||||
int Descriptor::getsockopt(ioctx_t* ctx, int level, int option_name,
|
||||
void* option_value, size_t* option_size_ptr)
|
||||
{
|
||||
return vnode->getsockopt(ctx, level, option_name, option_value, option_size_ptr);
|
||||
}
|
||||
|
||||
int Descriptor::setsockopt(ioctx_t* ctx, int level, int option_name,
|
||||
const void* option_value, size_t option_size)
|
||||
{
|
||||
return vnode->setsockopt(ctx, level, option_name, option_value, option_size);
|
||||
}
|
||||
|
||||
} // namespace Sortix
|
||||
|
|
|
@ -232,6 +232,10 @@ public:
|
|||
virtual ssize_t recv(ioctx_t* ctx, uint8_t* buf, size_t count, int flags);
|
||||
virtual ssize_t send(ioctx_t* ctx, const uint8_t* buf, size_t count,
|
||||
int flags);
|
||||
virtual int getsockopt(ioctx_t* ctx, int level, int option_name,
|
||||
void* option_value, size_t* option_size_ptr);
|
||||
virtual int setsockopt(ioctx_t* ctx, int level, int option_name,
|
||||
const void* option_value, size_t option_size);
|
||||
|
||||
private:
|
||||
bool SendMessage(Channel* channel, size_t type, void* ptr, size_t size,
|
||||
|
@ -1294,6 +1298,56 @@ ssize_t Unode::send(ioctx_t* /*ctx*/, const uint8_t* /*buf*/, size_t /*count*/,
|
|||
return errno = ENOTSOCK, -1;
|
||||
}
|
||||
|
||||
int Unode::getsockopt(ioctx_t* ctx, int level, int option_name,
|
||||
void* option_value, size_t* option_size_ptr)
|
||||
{
|
||||
size_t option_size;
|
||||
if ( !ctx->copy_from_src(&option_size, option_size_ptr, sizeof(option_size)) )
|
||||
return -1;
|
||||
Channel* channel = server->Connect();
|
||||
if ( !channel )
|
||||
return -1;
|
||||
int ret = -1;
|
||||
struct fsm_req_getsockopt msg;
|
||||
struct fsm_resp_getsockopt resp;
|
||||
msg.ino = ino;
|
||||
msg.level = level;
|
||||
msg.option_name = option_name;
|
||||
msg.max_option_size = option_size;
|
||||
if ( SendMessage(channel, FSM_REQ_GETSOCKOPT, &msg, sizeof(msg)) &&
|
||||
RecvMessage(channel, FSM_RESP_GETSOCKOPT, &resp, sizeof(resp)) )
|
||||
{
|
||||
if ( resp.option_size < option_size )
|
||||
option_size = resp.option_size;
|
||||
if ( channel->KernelRecv(ctx, option_value, option_size) )
|
||||
ret = 0;
|
||||
if ( !ctx->copy_to_dest(option_size_ptr, &option_size, sizeof(option_size)) )
|
||||
ret = -1;
|
||||
}
|
||||
channel->KernelClose();
|
||||
return ret;
|
||||
}
|
||||
|
||||
int Unode::setsockopt(ioctx_t* ctx, int level, int option_name,
|
||||
const void* option_value, size_t option_size)
|
||||
{
|
||||
Channel* channel = server->Connect();
|
||||
if ( !channel )
|
||||
return -1;
|
||||
int ret = -1;
|
||||
struct fsm_req_setsockopt msg;
|
||||
msg.ino = ino;
|
||||
msg.level = level;
|
||||
msg.option_name = option_name;
|
||||
msg.option_size = option_size;
|
||||
if ( SendMessage(channel, FSM_REQ_SETSOCKOPT, &msg, sizeof(msg)) &&
|
||||
channel->KernelSend(ctx, option_value, option_size) &&
|
||||
RecvMessage(channel, FSM_RESP_SUCCESS, NULL, 0) )
|
||||
ret = 0;
|
||||
channel->KernelClose();
|
||||
return ret;
|
||||
}
|
||||
|
||||
//
|
||||
// Initialization.
|
||||
//
|
||||
|
|
|
@ -96,6 +96,10 @@ public:
|
|||
int listen(ioctx_t* ctx, int backlog);
|
||||
ssize_t recv(ioctx_t* ctx, uint8_t* buf, size_t count, int flags);
|
||||
ssize_t send(ioctx_t* ctx, const uint8_t* buf, size_t count, int flags);
|
||||
int getsockopt(ioctx_t* ctx, int level, int option_name,
|
||||
void* option_value, size_t* option_size_ptr);
|
||||
int setsockopt(ioctx_t* ctx, int level, int option_name,
|
||||
const void* option_value, size_t option_size);
|
||||
|
||||
private:
|
||||
Ref<Descriptor> open_elem(ioctx_t* ctx, const char* filename, int flags,
|
||||
|
|
|
@ -106,6 +106,10 @@ public:
|
|||
virtual ssize_t recv(ioctx_t* ctx, uint8_t* buf, size_t count, int flags) = 0;
|
||||
virtual ssize_t send(ioctx_t* ctx, const uint8_t* buf, size_t count,
|
||||
int flags) = 0;
|
||||
virtual int getsockopt(ioctx_t* ctx, int level, int option_name,
|
||||
void* option_value, size_t* option_size_ptr) = 0;
|
||||
virtual int setsockopt(ioctx_t* ctx, int level, int option_name,
|
||||
const void* option_value, size_t option_size) = 0;
|
||||
|
||||
};
|
||||
|
||||
|
@ -186,6 +190,10 @@ public:
|
|||
virtual ssize_t recv(ioctx_t* ctx, uint8_t* buf, size_t count, int flags);
|
||||
virtual ssize_t send(ioctx_t* ctx, const uint8_t* buf, size_t count,
|
||||
int flags);
|
||||
virtual int getsockopt(ioctx_t* ctx, int level, int option_name,
|
||||
void* option_value, size_t* option_size_ptr);
|
||||
virtual int setsockopt(ioctx_t* ctx, int level, int option_name,
|
||||
const void* option_value, size_t option_size);
|
||||
|
||||
};
|
||||
|
||||
|
|
|
@ -96,6 +96,10 @@ public:
|
|||
int listen(ioctx_t* ctx, int backlog);
|
||||
ssize_t recv(ioctx_t* ctx, uint8_t* buf, size_t count, int flags);
|
||||
ssize_t send(ioctx_t* ctx, const uint8_t* buf, size_t count, int flags);
|
||||
int getsockopt(ioctx_t* ctx, int level, int option_name,
|
||||
void* option_value, size_t* option_size_ptr);
|
||||
int setsockopt(ioctx_t* ctx, int level, int option_name,
|
||||
const void* option_value, size_t option_size);
|
||||
|
||||
public /*TODO: private*/:
|
||||
Ref<Inode> inode;
|
||||
|
|
|
@ -165,6 +165,8 @@
|
|||
#define SYSCALL_SIGSUSPEND 137
|
||||
#define SYSCALL_SENDMSG 138
|
||||
#define SYSCALL_RECVMSG 139
|
||||
#define SYSCALL_MAX_NUM 140 /* index of highest constant + 1 */
|
||||
#define SYSCALL_GETSOCKOPT 140
|
||||
#define SYSCALL_SETSOCKOPT 141
|
||||
#define SYSCALL_MAX_NUM 142 /* index of highest constant + 1 */
|
||||
|
||||
#endif
|
||||
|
|
|
@ -384,4 +384,16 @@ ssize_t AbstractInode::send(ioctx_t* /*ctx*/, const uint8_t* /*buf*/,
|
|||
return errno = ENOTSOCK, -1;
|
||||
}
|
||||
|
||||
int AbstractInode::getsockopt(ioctx_t* /*ctx*/, int /*level*/, int /*option_name*/,
|
||||
void* /*option_value*/, size_t* /*option_size_ptr*/)
|
||||
{
|
||||
return errno = ENOTSOCK, -1;
|
||||
}
|
||||
|
||||
int AbstractInode::setsockopt(ioctx_t* /*ctx*/, int /*level*/, int /*option_name*/,
|
||||
const void* /*option_value*/, size_t /*option_size*/)
|
||||
{
|
||||
return errno = ENOTSOCK, -1;
|
||||
}
|
||||
|
||||
} // namespace Sortix
|
||||
|
|
|
@ -1010,6 +1010,28 @@ static ssize_t sys_recvmsg(int fd, struct msghdr* user_msg, int flags)
|
|||
return result;
|
||||
}
|
||||
|
||||
static int sys_getsockopt(int fd, int level, int option_name,
|
||||
void* option_value, size_t* option_size_ptr)
|
||||
{
|
||||
Ref<Descriptor> desc = CurrentProcess()->GetDescriptor(fd);
|
||||
if ( !desc )
|
||||
return -1;
|
||||
|
||||
ioctx_t ctx; SetupUserIOCtx(&ctx);
|
||||
return desc->getsockopt(&ctx, level, option_name, option_value, option_size_ptr);
|
||||
}
|
||||
|
||||
static int sys_setsockopt(int fd, int level, int option_name,
|
||||
const void* option_value, size_t option_size)
|
||||
{
|
||||
Ref<Descriptor> desc = CurrentProcess()->GetDescriptor(fd);
|
||||
if ( !desc )
|
||||
return -1;
|
||||
|
||||
ioctx_t ctx; SetupUserIOCtx(&ctx);
|
||||
return desc->setsockopt(&ctx, level, option_name, option_value, option_size);
|
||||
}
|
||||
|
||||
void Init()
|
||||
{
|
||||
Syscall::Register(SYSCALL_ACCEPT4, (void*) sys_accept4);
|
||||
|
@ -1036,6 +1058,7 @@ void Init()
|
|||
Syscall::Register(SYSCALL_FSYNC, (void*) sys_fsync);
|
||||
Syscall::Register(SYSCALL_FTRUNCATE, (void*) sys_ftruncate);
|
||||
Syscall::Register(SYSCALL_FUTIMENS, (void*) sys_futimens);
|
||||
Syscall::Register(SYSCALL_GETSOCKOPT, (void*) sys_getsockopt);
|
||||
Syscall::Register(SYSCALL_GETTERMMODE, (void*) sys_gettermmode);
|
||||
Syscall::Register(SYSCALL_IOCTL, (void*) sys_ioctl);
|
||||
Syscall::Register(SYSCALL_ISATTY, (void*) sys_isatty);
|
||||
|
@ -1058,6 +1081,7 @@ void Init()
|
|||
Syscall::Register(SYSCALL_RENAMEAT, (void*) sys_renameat);
|
||||
Syscall::Register(SYSCALL_SENDMSG, (void*) sys_sendmsg);
|
||||
Syscall::Register(SYSCALL_SEND, (void*) sys_send);
|
||||
Syscall::Register(SYSCALL_SETSOCKOPT, (void*) sys_setsockopt);
|
||||
Syscall::Register(SYSCALL_SETTERMMODE, (void*) sys_settermmode);
|
||||
Syscall::Register(SYSCALL_SYMLINKAT, (void*) sys_symlinkat);
|
||||
Syscall::Register(SYSCALL_TCGETPGRP, (void*) sys_tcgetpgrp);
|
||||
|
|
|
@ -294,4 +294,16 @@ ssize_t Vnode::send(ioctx_t* ctx, const uint8_t* buf, size_t count, int flags)
|
|||
return inode->send(ctx, buf, count, flags);
|
||||
}
|
||||
|
||||
int Vnode::getsockopt(ioctx_t* ctx, int level, int option_name,
|
||||
void* option_value, size_t* option_size_ptr)
|
||||
{
|
||||
return inode->getsockopt(ctx, level, option_name, option_value, option_size_ptr);
|
||||
}
|
||||
|
||||
int Vnode::setsockopt(ioctx_t* ctx, int level, int option_name,
|
||||
const void* option_value, size_t option_size)
|
||||
{
|
||||
return inode->setsockopt(ctx, level, option_name, option_value, option_size);
|
||||
}
|
||||
|
||||
} // namespace Sortix
|
||||
|
|
|
@ -368,7 +368,33 @@ struct fsm_resp_statvfs
|
|||
struct statvfs stvfs;
|
||||
};
|
||||
|
||||
#define FSM_MSG_NUM 45
|
||||
#define FSM_REQ_SETSOCKOPT 46
|
||||
struct fsm_req_setsockopt
|
||||
{
|
||||
ino_t ino;
|
||||
int level;
|
||||
int option_name;
|
||||
size_t option_size;
|
||||
/*uint8_t option[option_size];*/
|
||||
};
|
||||
|
||||
#define FSM_REQ_GETSOCKOPT 47
|
||||
struct fsm_req_getsockopt
|
||||
{
|
||||
ino_t ino;
|
||||
int level;
|
||||
int option_name;
|
||||
size_t max_option_size;
|
||||
};
|
||||
|
||||
#define FSM_RESP_GETSOCKOPT 48
|
||||
struct fsm_resp_getsockopt
|
||||
{
|
||||
size_t option_size;
|
||||
/*uint8_t option[option_size];*/
|
||||
};
|
||||
|
||||
#define FSM_MSG_NUM 49
|
||||
|
||||
#if defined(__cplusplus)
|
||||
} /* extern "C" */
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
/*******************************************************************************
|
||||
|
||||
Copyright(C) Jonas 'Sortie' Termansen 2013.
|
||||
Copyright(C) Jonas 'Sortie' Termansen 2013, 2014.
|
||||
|
||||
This file is part of the Sortix C Library.
|
||||
|
||||
|
@ -23,12 +23,13 @@
|
|||
*******************************************************************************/
|
||||
|
||||
#include <sys/socket.h>
|
||||
#include <sys/syscall.h>
|
||||
|
||||
#include <errno.h>
|
||||
#include <stdio.h>
|
||||
DEFN_SYSCALL5(int, sys_getsockopt, SYSCALL_GETSOCKOPT, int, int, int, const void*, size_t*);
|
||||
|
||||
extern "C" int getsockopt(int, int, int, void* restrict, socklen_t* restrict)
|
||||
extern "C"
|
||||
int getsockopt(int fd, int level, int option_name, void* restrict option_value,
|
||||
socklen_t* restrict option_size)
|
||||
{
|
||||
fprintf(stderr, "%s is not implemented yet.\n", __func__);
|
||||
return errno = ENOSYS, -1;
|
||||
return sys_getsockopt(fd, level, option_name, option_value, option_size);
|
||||
}
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
/*******************************************************************************
|
||||
|
||||
Copyright(C) Jonas 'Sortie' Termansen 2013.
|
||||
Copyright(C) Jonas 'Sortie' Termansen 2013, 2014.
|
||||
|
||||
This file is part of the Sortix C Library.
|
||||
|
||||
|
@ -23,12 +23,13 @@
|
|||
*******************************************************************************/
|
||||
|
||||
#include <sys/socket.h>
|
||||
#include <sys/syscall.h>
|
||||
|
||||
#include <errno.h>
|
||||
#include <stdio.h>
|
||||
DEFN_SYSCALL5(int, sys_setsockopt, SYSCALL_SETSOCKOPT, int, int, int, const void*, size_t);
|
||||
|
||||
extern "C" int setsockopt(int, int, int, const void*, socklen_t)
|
||||
extern "C"
|
||||
int setsockopt(int fd, int level, int option_name, const void* option_value,
|
||||
socklen_t option_size)
|
||||
{
|
||||
fprintf(stderr, "%s is not implemented yet.\n", __func__);
|
||||
return errno = ENOSYS, -1;
|
||||
return sys_setsockopt(fd, level, option_name, option_value, option_size);
|
||||
}
|
||||
|
|
Loading…
Add table
Reference in a new issue