vm/ipc: only report signals when it matters to ipc
. ipc wants to know about processes that get signals, so that it can break blocking ipc operations . doing it for every single signal is wasteful and causes the annoying 'no slot for signals' message . this fix tells vm on a per-process basis it (ipc) wants to be notified, i.e. only when it does any ipc calls . move ipc config to separate config file while we're at it
This commit is contained in:
parent
862fb8354d
commit
d477a9ed82
@ -1074,6 +1074,7 @@ struct
|
|||||||
{ "GETREF", VM_GETREF },
|
{ "GETREF", VM_GETREF },
|
||||||
{ "RS_SET_PRIV", VM_RS_SET_PRIV },
|
{ "RS_SET_PRIV", VM_RS_SET_PRIV },
|
||||||
{ "QUERY_EXIT", VM_QUERY_EXIT },
|
{ "QUERY_EXIT", VM_QUERY_EXIT },
|
||||||
|
{ "WATCH_EXIT", VM_WATCH_EXIT },
|
||||||
{ "NOTIFY_SIG", VM_NOTIFY_SIG },
|
{ "NOTIFY_SIG", VM_NOTIFY_SIG },
|
||||||
{ "INFO", VM_INFO },
|
{ "INFO", VM_INFO },
|
||||||
{ "RS_UPDATE", VM_RS_UPDATE },
|
{ "RS_UPDATE", VM_RS_UPDATE },
|
||||||
|
@ -1071,8 +1071,11 @@
|
|||||||
# define VM_RS_MEM_PIN 0 /* pin memory */
|
# define VM_RS_MEM_PIN 0 /* pin memory */
|
||||||
# define VM_RS_MEM_MAKE_VM 1 /* make VM instance */
|
# define VM_RS_MEM_MAKE_VM 1 /* make VM instance */
|
||||||
|
|
||||||
|
#define VM_WATCH_EXIT (VM_RQ_BASE+43)
|
||||||
|
# define VM_WE_EP m1_i1
|
||||||
|
|
||||||
/* Total. */
|
/* Total. */
|
||||||
#define NR_VM_CALLS 43
|
#define NR_VM_CALLS 44
|
||||||
#define VM_CALL_MASK_SIZE BITMAP_CHUNKS(NR_VM_CALLS)
|
#define VM_CALL_MASK_SIZE BITMAP_CHUNKS(NR_VM_CALLS)
|
||||||
|
|
||||||
/* not handled as a normal VM call, thus at the end of the reserved rage */
|
/* not handled as a normal VM call, thus at the end of the reserved rage */
|
||||||
|
@ -26,7 +26,8 @@ _PROTOTYPE( int vm_notify_sig, (endpoint_t ep, endpoint_t ipc_ep));
|
|||||||
_PROTOTYPE( int vm_set_priv, (int procnr, void *buf));
|
_PROTOTYPE( int vm_set_priv, (int procnr, void *buf));
|
||||||
_PROTOTYPE( int vm_update, (endpoint_t src_e, endpoint_t dst_e));
|
_PROTOTYPE( int vm_update, (endpoint_t src_e, endpoint_t dst_e));
|
||||||
_PROTOTYPE( int vm_memctl, (endpoint_t ep, int req));
|
_PROTOTYPE( int vm_memctl, (endpoint_t ep, int req));
|
||||||
_PROTOTYPE( int vm_query_exit, (int *endpt));
|
_PROTOTYPE( int vm_query_exit, (endpoint_t *endpt));
|
||||||
|
_PROTOTYPE( int vm_watch_exit, (endpoint_t ep));
|
||||||
_PROTOTYPE( int vm_forgetblock, (u64_t id));
|
_PROTOTYPE( int vm_forgetblock, (u64_t id));
|
||||||
_PROTOTYPE( void vm_forgetblocks, (void));
|
_PROTOTYPE( void vm_forgetblocks, (void));
|
||||||
_PROTOTYPE( int vm_yield_block_get_block, (u64_t yieldid, u64_t getid,
|
_PROTOTYPE( int vm_yield_block_get_block, (u64_t yieldid, u64_t getid,
|
||||||
|
@ -520,25 +520,6 @@ service amddev
|
|||||||
uid 0;
|
uid 0;
|
||||||
};
|
};
|
||||||
|
|
||||||
service ipc
|
|
||||||
{
|
|
||||||
system
|
|
||||||
UMAP # 14
|
|
||||||
VIRCOPY # 15
|
|
||||||
;
|
|
||||||
uid 0;
|
|
||||||
ipc
|
|
||||||
SYSTEM USER pm rs log tty ds vm
|
|
||||||
;
|
|
||||||
vm
|
|
||||||
REMAP
|
|
||||||
SHM_UNMAP
|
|
||||||
GETPHYS
|
|
||||||
GETREF
|
|
||||||
QUERY_EXIT
|
|
||||||
;
|
|
||||||
};
|
|
||||||
|
|
||||||
service osscore
|
service osscore
|
||||||
{
|
{
|
||||||
system
|
system
|
||||||
|
@ -22,3 +22,14 @@ PUBLIC int vm_query_exit(int *endpt)
|
|||||||
*endpt = m.VM_QUERY_RET_PT;
|
*endpt = m.VM_QUERY_RET_PT;
|
||||||
return (m.VM_QUERY_IS_MORE ? 1 : 0);
|
return (m.VM_QUERY_IS_MORE ? 1 : 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
PUBLIC int vm_watch_exit(endpoint_t ep)
|
||||||
|
{
|
||||||
|
message m;
|
||||||
|
int r;
|
||||||
|
|
||||||
|
memset(&m, 0, sizeof(m));
|
||||||
|
m.VM_WE_EP = ep;
|
||||||
|
return _syscall(VM_PROC_NR, VM_WATCH_EXIT, &m);
|
||||||
|
}
|
||||||
|
|
||||||
|
@ -8,5 +8,8 @@ LDADD+= -lsys
|
|||||||
MAN=
|
MAN=
|
||||||
|
|
||||||
BINDIR?= /usr/sbin
|
BINDIR?= /usr/sbin
|
||||||
|
FILES=ipc.conf
|
||||||
|
FILESNAME=ipc
|
||||||
|
FILESDIR= /etc/system.conf.d
|
||||||
|
|
||||||
.include <minix.service.mk>
|
.include <minix.service.mk>
|
||||||
|
19
servers/ipc/ipc.conf
Normal file
19
servers/ipc/ipc.conf
Normal file
@ -0,0 +1,19 @@
|
|||||||
|
service ipc
|
||||||
|
{
|
||||||
|
system
|
||||||
|
UMAP # 14
|
||||||
|
VIRCOPY # 15
|
||||||
|
;
|
||||||
|
uid 0;
|
||||||
|
ipc
|
||||||
|
SYSTEM USER pm rs log tty ds vm
|
||||||
|
;
|
||||||
|
vm
|
||||||
|
REMAP
|
||||||
|
SHM_UNMAP
|
||||||
|
GETPHYS
|
||||||
|
GETREF
|
||||||
|
QUERY_EXIT
|
||||||
|
WATCH_EXIT
|
||||||
|
;
|
||||||
|
};
|
@ -64,6 +64,14 @@ PUBLIC int main(int argc, char *argv[])
|
|||||||
|
|
||||||
/* dispatch messages */
|
/* dispatch messages */
|
||||||
for (i = 0; i < SIZE(ipc_calls); i++) {
|
for (i = 0; i < SIZE(ipc_calls); i++) {
|
||||||
|
/* If any process does an IPC call,
|
||||||
|
* we have to know about it exiting.
|
||||||
|
* Tell VM to watch it for us.
|
||||||
|
*/
|
||||||
|
if(vm_watch_exit(m.m_source) != OK) {
|
||||||
|
printf("IPC: watch failed on %d\n", m.m_source);
|
||||||
|
}
|
||||||
|
|
||||||
if (ipc_calls[i].type == call_type) {
|
if (ipc_calls[i].type == call_type) {
|
||||||
int result;
|
int result;
|
||||||
|
|
||||||
|
@ -365,6 +365,7 @@ PRIVATE int sef_cb_init_fresh(int type, sef_init_info_t *info)
|
|||||||
CALLMAP(VM_GETREF, do_get_refcount);
|
CALLMAP(VM_GETREF, do_get_refcount);
|
||||||
CALLMAP(VM_INFO, do_info);
|
CALLMAP(VM_INFO, do_info);
|
||||||
CALLMAP(VM_QUERY_EXIT, do_query_exit);
|
CALLMAP(VM_QUERY_EXIT, do_query_exit);
|
||||||
|
CALLMAP(VM_WATCH_EXIT, do_watch_exit);
|
||||||
CALLMAP(VM_FORGETBLOCKS, do_forgetblocks);
|
CALLMAP(VM_FORGETBLOCKS, do_forgetblocks);
|
||||||
CALLMAP(VM_FORGETBLOCK, do_forgetblock);
|
CALLMAP(VM_FORGETBLOCK, do_forgetblock);
|
||||||
CALLMAP(VM_YIELDBLOCKGETBLOCK, do_yieldblockgetblock);
|
CALLMAP(VM_YIELDBLOCKGETBLOCK, do_yieldblockgetblock);
|
||||||
|
@ -207,5 +207,6 @@ _PROTOTYPE(int do_rs_memctl, (message *m));
|
|||||||
|
|
||||||
/* queryexit.c */
|
/* queryexit.c */
|
||||||
_PROTOTYPE(int do_query_exit, (message *m));
|
_PROTOTYPE(int do_query_exit, (message *m));
|
||||||
|
_PROTOTYPE(int do_watch_exit, (message *m));
|
||||||
_PROTOTYPE(int do_notify_sig, (message *m));
|
_PROTOTYPE(int do_notify_sig, (message *m));
|
||||||
_PROTOTYPE(void init_query_exit, (void));
|
_PROTOTYPE(void init_query_exit, (void));
|
||||||
|
@ -67,10 +67,19 @@ PUBLIC int do_query_exit(message *m)
|
|||||||
*===========================================================================*/
|
*===========================================================================*/
|
||||||
PUBLIC int do_notify_sig(message *m)
|
PUBLIC int do_notify_sig(message *m)
|
||||||
{
|
{
|
||||||
int i, avails = 0;
|
int i, avails = 0, p;
|
||||||
endpoint_t ep = m->VM_NOTIFY_SIG_ENDPOINT;
|
endpoint_t ep = m->VM_NOTIFY_SIG_ENDPOINT;
|
||||||
endpoint_t ipc_ep = m->VM_NOTIFY_SIG_IPC;
|
endpoint_t ipc_ep = m->VM_NOTIFY_SIG_IPC;
|
||||||
int r;
|
int r;
|
||||||
|
struct vmproc *vmp;
|
||||||
|
int pslot;
|
||||||
|
|
||||||
|
if(vm_isokendpt(ep, &pslot) != OK) return ESRCH;
|
||||||
|
vmp = &vmproc[pslot];
|
||||||
|
|
||||||
|
/* Only record the event if we've been asked to report it. */
|
||||||
|
if(!(vmp->vm_flags & VMF_WATCHEXIT))
|
||||||
|
return OK;
|
||||||
|
|
||||||
for (i = 0; i < NR_PROCS; i++) {
|
for (i = 0; i < NR_PROCS; i++) {
|
||||||
/* its signal is already here */
|
/* its signal is already here */
|
||||||
@ -80,7 +89,7 @@ PUBLIC int do_notify_sig(message *m)
|
|||||||
avails++;
|
avails++;
|
||||||
}
|
}
|
||||||
if (!avails) {
|
if (!avails) {
|
||||||
/* no slot for signals, impossible */
|
/* no slot for signals, unlikely */
|
||||||
printf("VM: no slot for signals!\n");
|
printf("VM: no slot for signals!\n");
|
||||||
return ENOMEM;
|
return ENOMEM;
|
||||||
}
|
}
|
||||||
@ -106,6 +115,21 @@ out:
|
|||||||
return OK;
|
return OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*===========================================================================*
|
||||||
|
* do_watch_exit *
|
||||||
|
*===========================================================================*/
|
||||||
|
PUBLIC int do_watch_exit(message *m)
|
||||||
|
{
|
||||||
|
endpoint_t e = m->VM_WE_EP;
|
||||||
|
struct vmproc *vmp;
|
||||||
|
int p;
|
||||||
|
if(vm_isokendpt(e, &p) != OK) return ESRCH;
|
||||||
|
vmp = &vmproc[p];
|
||||||
|
vmp->vm_flags |= VMF_WATCHEXIT;
|
||||||
|
|
||||||
|
return OK;
|
||||||
|
}
|
||||||
|
|
||||||
/*===========================================================================*
|
/*===========================================================================*
|
||||||
* init_query_exit *
|
* init_query_exit *
|
||||||
*===========================================================================*/
|
*===========================================================================*/
|
||||||
|
@ -65,5 +65,6 @@ struct vmproc {
|
|||||||
#define VMF_HAS_DMA 0x010 /* Process directly or indirectly granted
|
#define VMF_HAS_DMA 0x010 /* Process directly or indirectly granted
|
||||||
* DMA buffers.
|
* DMA buffers.
|
||||||
*/
|
*/
|
||||||
|
#define VMF_WATCHEXIT 0x020 /* Store in queryexit table */
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
Loading…
x
Reference in New Issue
Block a user