如何在 PM 服务器 Minix 中发送消息
How to send messages in PM server Minix
所以我正在尝试在 PM 服务器上创建一个新的系统调用。我的问题是,我怎样才能发送某种消息来发挥作用。
在 IPC 服务器中,我所要做的就是将我的系统调用添加到列表中,因为那里的所有函数都定义为 (*func)(message *)
(...)/servers/ipc/main.c
static struct {
int type;
int (*func)(message *);
int reply; /* whether the reply action is passed through */
} ipc_calls[] = {
(...)
{ IPC_MYNEWSIGNAL, do_something, 1 },
};
但在 table.c 中的 PM 函数定义为
(...)/servers/pm/table.c
int (* const call_vec[NR_PM_CALLS])(void) = {
(...)
CALL(PM_GETSYSINFO) = do_getsysinfo
}
如果我尝试传递带有签名的函数
int do_something(message *m)
我会得到错误:
Incompatible pointer types: initializing int (*const)(void) with int (message *)
如果我需要接收某种信息,在 PM 服务器上创建信号的正确方法是什么?
据我从问题中了解到,您想在系统调用处理程序中接收参数。让我们以 libc.
中的库函数 clock_settime
为例
int clock_settime(clockid_t clock_id, const struct timespec *ts)
{
message m;
memset(&m, 0, sizeof(m));
m.m_lc_pm_time.clk_id = clock_id;
m.m_lc_pm_time.now = 1; /* set time immediately. don't use adjtime() method. */
m.m_lc_pm_time.sec = ts->tv_sec;
m.m_lc_pm_time.nsec = ts->tv_nsec;
if (_syscall(PM_PROC_NR, PM_CLOCK_SETTIME, &m) < 0)
return -1;
return 0;
}
如您所见,它将 args 写入消息结构并传递给 _syscall。好的,现在看一下安装在 table.c
.
中的 PM_CLOCK_SETTIME
的系统调用处理程序
int do_gettime()
{
clock_t ticks, realtime, clock;
time_t boottime;
int s;
if ( (s=getuptime(&ticks, &realtime, &boottime)) != OK)
panic("do_time couldn't get uptime: %d", s);
switch (m_in.m_lc_pm_time.clk_id) {
case CLOCK_REALTIME:
clock = realtime;
break;
case CLOCK_MONOTONIC:
clock = ticks;
break;
default:
return EINVAL; /* invalid/unsupported clock_id */
}
mp->mp_reply.m_pm_lc_time.sec = boottime + (clock / system_hz);
mp->mp_reply.m_pm_lc_time.nsec =
(uint32_t) ((clock % system_hz) * 1000000000ULL / system_hz);
return(OK);
}
很明显,参数是一个名为 m_in
的全局变量。多一点搜索显示它来自 glo.h
/* The parameters of the call are kept here. */
EXTERN message m_in; /* the incoming message itself is kept here. */
我想 MINIX 会处理设置和访问全局变量,所以你不需要明确地写入它。
查看要点 7 将参数传递给系统调用 here. To understand how to compile the kernel correctly refer to post.
所以我正在尝试在 PM 服务器上创建一个新的系统调用。我的问题是,我怎样才能发送某种消息来发挥作用。
在 IPC 服务器中,我所要做的就是将我的系统调用添加到列表中,因为那里的所有函数都定义为 (*func)(message *)
(...)/servers/ipc/main.c
static struct {
int type;
int (*func)(message *);
int reply; /* whether the reply action is passed through */
} ipc_calls[] = {
(...)
{ IPC_MYNEWSIGNAL, do_something, 1 },
};
但在 table.c 中的 PM 函数定义为
(...)/servers/pm/table.c
int (* const call_vec[NR_PM_CALLS])(void) = {
(...)
CALL(PM_GETSYSINFO) = do_getsysinfo
}
如果我尝试传递带有签名的函数
int do_something(message *m)
我会得到错误:
Incompatible pointer types: initializing int (*const)(void) with int (message *)
如果我需要接收某种信息,在 PM 服务器上创建信号的正确方法是什么?
据我从问题中了解到,您想在系统调用处理程序中接收参数。让我们以 libc.
中的库函数clock_settime
为例
int clock_settime(clockid_t clock_id, const struct timespec *ts)
{
message m;
memset(&m, 0, sizeof(m));
m.m_lc_pm_time.clk_id = clock_id;
m.m_lc_pm_time.now = 1; /* set time immediately. don't use adjtime() method. */
m.m_lc_pm_time.sec = ts->tv_sec;
m.m_lc_pm_time.nsec = ts->tv_nsec;
if (_syscall(PM_PROC_NR, PM_CLOCK_SETTIME, &m) < 0)
return -1;
return 0;
}
如您所见,它将 args 写入消息结构并传递给 _syscall。好的,现在看一下安装在 table.c
.
PM_CLOCK_SETTIME
的系统调用处理程序
int do_gettime()
{
clock_t ticks, realtime, clock;
time_t boottime;
int s;
if ( (s=getuptime(&ticks, &realtime, &boottime)) != OK)
panic("do_time couldn't get uptime: %d", s);
switch (m_in.m_lc_pm_time.clk_id) {
case CLOCK_REALTIME:
clock = realtime;
break;
case CLOCK_MONOTONIC:
clock = ticks;
break;
default:
return EINVAL; /* invalid/unsupported clock_id */
}
mp->mp_reply.m_pm_lc_time.sec = boottime + (clock / system_hz);
mp->mp_reply.m_pm_lc_time.nsec =
(uint32_t) ((clock % system_hz) * 1000000000ULL / system_hz);
return(OK);
}
很明显,参数是一个名为 m_in
的全局变量。多一点搜索显示它来自 glo.h
/* The parameters of the call are kept here. */
EXTERN message m_in; /* the incoming message itself is kept here. */
我想 MINIX 会处理设置和访问全局变量,所以你不需要明确地写入它。
查看要点 7 将参数传递给系统调用 here. To understand how to compile the kernel correctly refer to