我创建了一个系统调用来返回特定进程的标记变量(我在内核中添加的)。当我做错误时:函数‘sys_kill’的隐式声明。是否有人知道导致这种情况的原因,或者我是否可以使用其他函数来查看进程是否正在运行以返回标记?
#include <linux/kernel.h>
#include <linux/init.h>
#include <linux/sched.h>
#include <linux/syscalls.h>
#include <linux/signal.h>
#include "header.h"
asmlinkage int sys_get_thing(int pid){ //gets the process ID
struct task_struct *p; //pointer to the struct
p = find_task_by_vpid(pid); //p = process found by PID
if(sys_kill(p->pid, 0) == 0){ //syskill sends a 0 signal to all processes matching passed PID - checks if running
return p->tag; //the 0 signal found has the tag we are looking for
}
else{
return -1; //if nothing is found return -1
}
}发布于 2020-03-10 20:23:38
内核中的调用是在signal.c中实现的kill_something_info。这里有一个实例syscall的定义:https://elixir.bootlin.com/linux/v4.10.14/source/kernel/signal.c#L2860
发布于 2020-03-11 12:04:56
sys_kill不存在于使用syscall包装器(那些定义CONFIG_ARCH_HAS_SYSCALL_WRAPPER的体系结构)的体系结构中。即使确实存在,也应该注意到"include/linux/syscalls.h“中的建议:
* Please note that these prototypes here are only provided for information
* purposes, for static analysis, and for linking from the syscall table.
* These functions should not be called elsewhere from kernel code.此外,对于使用syscall包装的体系结构,asmlinkage int sys_get_tag(int pid)函数定义将是无效的。为了在所有架构上工作,而且由于它只有一个参数,所以应该将其编写为SYSCALL_DEFINE1(get_tag, int, pid)。
不需要从内核空间向任务发送信号来确定它是否存在。找到的任何任务都是存在的,尽管已找到的任务可能被标记为死掉,并且这些任务可能应该被OP的系统调用忽略。这可以通过检查p->state & TASK_DEAD来完成。
对find_task_by_vpid的调用应该受到rcu_read_lock()的保护,除非任务结构的引用在匹配的rcu_read_unlock()之前由get_task_struct(task)递增,否则找到的任务结构不再有效。有一个find_get_task_by_vpid函数,它将find_task_by_vpid和get_task_struct的效果与适当的RCU锁定结合起来。
syscall不应该返回-1,而是应该返回一个适当的被否定的errno值。这将导致userspace set返回-1并设置errno变量。如果找不到进程,则适当的errno值是ESRCH,因此如果找不到进程,syscall的内核实现应该返回-ESRCH。
以下是syscall的两个可能实现。第一种方法直接使用RCU锁定:
SYSCALL_DEFINE1(get_tag, int, pid)
{
struct task_struct *p; // pointer to the struct
int rc = -ESRCH; // default return value when not found
rcu_read_lock();
p = find_task_by_vpid(pid); // p = process found by PID
if (p && !(p->state & TASK_DEAD)) // process exists and is not dead
rc = p->tag; // the tag we are looking for
rcu_read_unlock();
return rc;
}第二种方法使用find_get_task_vpid和put_task_struct,而不是显式的RCU锁定( RCU锁定和解锁是在对find_get_task_vpid的调用中完成的):
SYSCALL_DEFINE1(get_tag, int, pid)
{
struct task_struct *p; // pointer to the struct
int rc = -ESRCH; // default return value when not found
p = find_get_task_by_vpid(pid); // p = process found by PID
if (p) { // process exists ...
if (!(p->state & TASK_DEAD)) // ... and is not dead
rc = p->tag; // the tag we are looking for
put_task_struct(p);
}
return rc;
}https://stackoverflow.com/questions/60622581
复制相似问题