Add skeleton for perf_event_open.
This commit is contained in:
@ -20,7 +20,7 @@
|
||||
* syscall_name[] only, no handler exists.
|
||||
*/
|
||||
|
||||
SYSCALL_DELEGATED(0, read)
|
||||
SYSCALL_HANDLED(0, read)
|
||||
SYSCALL_DELEGATED(1, write)
|
||||
SYSCALL_DELEGATED(2, open)
|
||||
SYSCALL_HANDLED(3, close)
|
||||
@ -35,7 +35,7 @@ SYSCALL_HANDLED(12, brk)
|
||||
SYSCALL_HANDLED(13, rt_sigaction)
|
||||
SYSCALL_HANDLED(14, rt_sigprocmask)
|
||||
SYSCALL_HANDLED(15, rt_sigreturn)
|
||||
SYSCALL_DELEGATED(16, ioctl)
|
||||
SYSCALL_HANDLED(16, ioctl)
|
||||
SYSCALL_DELEGATED(17, pread64)
|
||||
SYSCALL_DELEGATED(18, pwrite64)
|
||||
SYSCALL_DELEGATED(20, writev)
|
||||
@ -133,6 +133,7 @@ SYSCALL_HANDLED(279, move_pages)
|
||||
SYSCALL_DELEGATED(281, epoll_pwait)
|
||||
SYSCALL_HANDLED(282, signalfd)
|
||||
SYSCALL_HANDLED(289, signalfd4)
|
||||
SYSCALL_HANDLED(298, perf_event_open)
|
||||
#ifdef DCFA_KMOD
|
||||
SYSCALL_HANDLED(303, mod_call)
|
||||
#endif
|
||||
|
||||
@ -2198,6 +2198,11 @@ return_execve2:
|
||||
do_syscall_return(fd, cpu, ret, 0, 0, 0, 0);
|
||||
break;
|
||||
|
||||
case __NR_perf_event_open:
|
||||
ret = open("/dev/null", O_RDONLY);
|
||||
do_syscall_return(fd, cpu, ret, 0, 0, 0, 0);
|
||||
break;
|
||||
|
||||
case __NR_rt_sigaction:
|
||||
act_sigaction(&w);
|
||||
do_syscall_return(fd, cpu, 0, 0, 0, 0, 0);
|
||||
|
||||
@ -312,18 +312,22 @@ struct vm_regions {
|
||||
|
||||
struct process_vm;
|
||||
|
||||
struct sigfd {
|
||||
struct sigfd *next;
|
||||
struct mckfd {
|
||||
struct mckfd *next;
|
||||
int fd;
|
||||
__sigset_t mask;
|
||||
long data;
|
||||
void *opt;
|
||||
long (*read_cb)(struct mckfd *, ihk_mc_user_context_t *);
|
||||
int (*ioctl_cb)(struct mckfd *, ihk_mc_user_context_t *);
|
||||
int (*close_cb)(struct mckfd *, ihk_mc_user_context_t *);
|
||||
};
|
||||
|
||||
#define SFD_CLOEXEC 02000000
|
||||
#define SFD_NONBLOCK 04000
|
||||
|
||||
struct sig_common {
|
||||
ihk_spinlock_t lock;
|
||||
ihk_atomic_t use;
|
||||
struct sigfd *sigfd;
|
||||
struct k_sigaction action[_NSIG];
|
||||
struct list_head sigpending;
|
||||
};
|
||||
@ -425,6 +429,8 @@ struct process {
|
||||
/* Store signal sent to parent when the process terminates. */
|
||||
int termsig;
|
||||
|
||||
ihk_spinlock_t mckfd_lock;
|
||||
struct mckfd *mckfd;
|
||||
};
|
||||
|
||||
void hold_thread(struct thread *ftn);
|
||||
|
||||
@ -96,6 +96,7 @@ init_process(struct process *proc, struct process *parent)
|
||||
INIT_LIST_HEAD(&proc->ptraced_children_list);
|
||||
mcs_rwlock_init(&proc->threads_lock);
|
||||
mcs_rwlock_init(&proc->children_lock);
|
||||
ihk_mc_spinlock_init(&proc->mckfd_lock);
|
||||
waitq_init(&proc->waitpid_q);
|
||||
ihk_atomic_set(&proc->refcount, 2);
|
||||
}
|
||||
|
||||
159
kernel/syscall.c
159
kernel/syscall.c
@ -2359,34 +2359,85 @@ do_sigaction(int sig, struct k_sigaction *act, struct k_sigaction *oact)
|
||||
return 0;
|
||||
}
|
||||
|
||||
SYSCALL_DECLARE(read)
|
||||
{
|
||||
int fd = ihk_mc_syscall_arg0(ctx);
|
||||
long rc;
|
||||
struct thread *thread = cpu_local_var(current);
|
||||
struct process *proc = thread->proc;
|
||||
struct mckfd *fdp;
|
||||
long irqstate;
|
||||
|
||||
irqstate = ihk_mc_spinlock_lock(&proc->mckfd_lock);
|
||||
for(fdp = proc->mckfd; fdp; fdp = fdp->next)
|
||||
if(fdp->fd == fd)
|
||||
break;
|
||||
ihk_mc_spinlock_unlock(&proc->mckfd_lock, irqstate);
|
||||
|
||||
if(fdp && fdp->read_cb){
|
||||
kprintf("read: found system fd %d\n", fd);
|
||||
rc = fdp->read_cb(fdp, ctx);
|
||||
}
|
||||
else{
|
||||
rc = syscall_generic_forwarding(__NR_read, ctx);
|
||||
}
|
||||
return rc;
|
||||
}
|
||||
|
||||
SYSCALL_DECLARE(ioctl)
|
||||
{
|
||||
int fd = ihk_mc_syscall_arg0(ctx);
|
||||
long rc;
|
||||
struct thread *thread = cpu_local_var(current);
|
||||
struct process *proc = thread->proc;
|
||||
struct mckfd *fdp;
|
||||
long irqstate;
|
||||
|
||||
irqstate = ihk_mc_spinlock_lock(&proc->mckfd_lock);
|
||||
for(fdp = proc->mckfd; fdp; fdp = fdp->next)
|
||||
if(fdp->fd == fd)
|
||||
break;
|
||||
ihk_mc_spinlock_unlock(&proc->mckfd_lock, irqstate);
|
||||
|
||||
if(fdp && fdp->ioctl_cb){
|
||||
kprintf("ioctl: found system fd %d\n", fd);
|
||||
rc = fdp->ioctl_cb(fdp, ctx);
|
||||
}
|
||||
else{
|
||||
rc = syscall_generic_forwarding(__NR_ioctl, ctx);
|
||||
}
|
||||
return rc;
|
||||
}
|
||||
|
||||
SYSCALL_DECLARE(close)
|
||||
{
|
||||
int fd = ihk_mc_syscall_arg0(ctx);
|
||||
int rc;
|
||||
long rc;
|
||||
struct thread *thread = cpu_local_var(current);
|
||||
struct sigfd *sfd;
|
||||
struct sigfd *sb;
|
||||
long irqstate;
|
||||
struct process *proc = thread->proc;
|
||||
struct mckfd *fdp;
|
||||
struct mckfd *fdq;
|
||||
long irqstate;
|
||||
|
||||
irqstate = ihk_mc_spinlock_lock(&thread->sigcommon->lock);
|
||||
for(sfd = thread->sigcommon->sigfd, sb = NULL; sfd; sb = sfd, sfd = sfd->next)
|
||||
if(sfd->fd == fd)
|
||||
irqstate = ihk_mc_spinlock_lock(&proc->mckfd_lock);
|
||||
for(fdp = proc->mckfd, fdq = NULL; fdp; fdq = fdp, fdp = fdp->next)
|
||||
if(fdp->fd == fd)
|
||||
break;
|
||||
if(sfd){
|
||||
struct syscall_request request IHK_DMA_ALIGN;
|
||||
if(sb)
|
||||
sb->next = sfd->next;
|
||||
|
||||
if(fdp){
|
||||
kprintf("close: found system fd %d pid=%d\n", fd, proc->pid);
|
||||
if(fdq)
|
||||
fdq->next = fdp->next;
|
||||
else
|
||||
thread->sigcommon->sigfd = sfd->next;
|
||||
ihk_mc_spinlock_unlock(&thread->sigcommon->lock, irqstate);
|
||||
request.number = __NR_signalfd4;
|
||||
request.args[0] = 1;
|
||||
request.args[1] = sfd->fd;
|
||||
kfree(sfd);
|
||||
rc = do_syscall(&request, ihk_mc_get_processor_id(), 0);
|
||||
proc->mckfd = fdp->next;
|
||||
ihk_mc_spinlock_unlock(&proc->mckfd_lock, irqstate);
|
||||
if(fdp->close_cb)
|
||||
fdp->close_cb(fdp, ctx);
|
||||
kfree(fdp);
|
||||
rc = syscall_generic_forwarding(__NR_close, ctx);
|
||||
}
|
||||
else{
|
||||
ihk_mc_spinlock_unlock(&thread->sigcommon->lock, irqstate);
|
||||
ihk_mc_spinlock_unlock(&proc->mckfd_lock, irqstate);
|
||||
rc = syscall_generic_forwarding(__NR_close, ctx);
|
||||
}
|
||||
return rc;
|
||||
@ -2487,7 +2538,8 @@ SYSCALL_DECLARE(signalfd4)
|
||||
{
|
||||
int fd = ihk_mc_syscall_arg0(ctx);
|
||||
struct thread *thread = cpu_local_var(current);
|
||||
struct sigfd *sfd;
|
||||
struct process *proc = thread->proc;
|
||||
struct mckfd *sfd;
|
||||
long irqstate;
|
||||
sigset_t *maskp = (sigset_t *)ihk_mc_syscall_arg1(ctx);;
|
||||
__sigset_t mask;
|
||||
@ -2501,10 +2553,9 @@ SYSCALL_DECLARE(signalfd4)
|
||||
if(flags & ~(SFD_NONBLOCK | SFD_CLOEXEC))
|
||||
return -EINVAL;
|
||||
|
||||
irqstate = ihk_mc_spinlock_lock(&thread->sigcommon->lock);
|
||||
if(fd == -1){
|
||||
struct syscall_request request IHK_DMA_ALIGN;
|
||||
ihk_mc_spinlock_unlock(&thread->sigcommon->lock, irqstate);
|
||||
|
||||
request.number = __NR_signalfd4;
|
||||
request.args[0] = 0;
|
||||
request.args[1] = flags;
|
||||
@ -2512,25 +2563,73 @@ SYSCALL_DECLARE(signalfd4)
|
||||
if(fd < 0){
|
||||
return fd;
|
||||
}
|
||||
sfd = kmalloc(sizeof(struct sigfd), IHK_MC_AP_NOWAIT);
|
||||
sfd = kmalloc(sizeof(struct mckfd), IHK_MC_AP_NOWAIT);
|
||||
if(!sfd)
|
||||
return -ENOMEM;
|
||||
sfd->fd = fd;
|
||||
irqstate = ihk_mc_spinlock_lock(&thread->sigcommon->lock);
|
||||
sfd->next = thread->sigcommon->sigfd;
|
||||
thread->sigcommon->sigfd = sfd;
|
||||
irqstate = ihk_mc_spinlock_lock(&proc->mckfd_lock);
|
||||
sfd->next = proc->mckfd;
|
||||
proc->mckfd = sfd;
|
||||
}
|
||||
else{
|
||||
for(sfd = thread->sigcommon->sigfd; sfd; sfd = sfd->next)
|
||||
irqstate = ihk_mc_spinlock_lock(&proc->mckfd_lock);
|
||||
for(sfd = proc->mckfd; sfd; sfd = sfd->next)
|
||||
if(sfd->fd == fd)
|
||||
break;
|
||||
if(!sfd){
|
||||
ihk_mc_spinlock_unlock(&thread->sigcommon->lock, irqstate);
|
||||
ihk_mc_spinlock_unlock(&proc->mckfd_lock, irqstate);
|
||||
return -EINVAL;
|
||||
}
|
||||
}
|
||||
memcpy(&sfd->mask, &mask, sizeof mask);
|
||||
ihk_mc_spinlock_unlock(&thread->sigcommon->lock, irqstate);
|
||||
memcpy(&sfd->data, &mask, sizeof mask);
|
||||
ihk_mc_spinlock_unlock(&proc->mckfd_lock, irqstate);
|
||||
return sfd->fd;
|
||||
}
|
||||
|
||||
static long
|
||||
perf_event_read(struct mckfd *sfd, ihk_mc_user_context_t *ctx)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int
|
||||
perf_event_ioctl(struct mckfd *sfd, ihk_mc_user_context_t *ctx)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
static int
|
||||
perf_event_close(struct mckfd *sfd, ihk_mc_user_context_t *ctx)
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
|
||||
SYSCALL_DECLARE(perf_event_open)
|
||||
{
|
||||
struct syscall_request request IHK_DMA_ALIGN;
|
||||
struct thread *thread = cpu_local_var(current);
|
||||
struct process *proc = thread->proc;
|
||||
struct mckfd *sfd;
|
||||
int fd;
|
||||
long irqstate;
|
||||
|
||||
request.number = __NR_perf_event_open;
|
||||
request.args[0] = 0;
|
||||
fd = do_syscall(&request, ihk_mc_get_processor_id(), 0);
|
||||
if(fd < 0){
|
||||
return fd;
|
||||
}
|
||||
sfd = kmalloc(sizeof(struct mckfd), IHK_MC_AP_NOWAIT);
|
||||
if(!sfd)
|
||||
return -ENOMEM;
|
||||
sfd->fd = fd;
|
||||
sfd->read_cb = perf_event_read;
|
||||
sfd->ioctl_cb = perf_event_ioctl;
|
||||
sfd->close_cb = perf_event_close;
|
||||
irqstate = ihk_mc_spinlock_lock(&proc->mckfd_lock);
|
||||
sfd->next = proc->mckfd;
|
||||
proc->mckfd = sfd;
|
||||
ihk_mc_spinlock_unlock(&proc->mckfd_lock, irqstate);
|
||||
return sfd->fd;
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user