1433d6423SLionel Sambuc
2433d6423SLionel Sambuc #define _SYSTEM 1
3433d6423SLionel Sambuc
4433d6423SLionel Sambuc #include <minix/callnr.h>
5433d6423SLionel Sambuc #include <minix/com.h>
6433d6423SLionel Sambuc #include <minix/config.h>
7433d6423SLionel Sambuc #include <minix/const.h>
8433d6423SLionel Sambuc #include <minix/ds.h>
9433d6423SLionel Sambuc #include <minix/endpoint.h>
10433d6423SLionel Sambuc #include <minix/minlib.h>
11433d6423SLionel Sambuc #include <minix/type.h>
12433d6423SLionel Sambuc #include <minix/ipc.h>
13433d6423SLionel Sambuc #include <minix/sysutil.h>
14433d6423SLionel Sambuc #include <minix/syslib.h>
15433d6423SLionel Sambuc #include <minix/bitmap.h>
16433d6423SLionel Sambuc
17433d6423SLionel Sambuc #include <errno.h>
18433d6423SLionel Sambuc #include <assert.h>
19433d6423SLionel Sambuc
20433d6423SLionel Sambuc #include "glo.h"
21433d6423SLionel Sambuc #include "proto.h"
22433d6423SLionel Sambuc #include "util.h"
23433d6423SLionel Sambuc #include "sanitycheck.h"
24433d6423SLionel Sambuc
reset_vm_rusage(struct vmproc * vmp)25433d6423SLionel Sambuc static void reset_vm_rusage(struct vmproc *vmp)
26433d6423SLionel Sambuc {
27433d6423SLionel Sambuc vmp->vm_total = 0;
28433d6423SLionel Sambuc vmp->vm_total_max = 0;
29433d6423SLionel Sambuc vmp->vm_minor_page_fault = 0;
30433d6423SLionel Sambuc vmp->vm_major_page_fault = 0;
31433d6423SLionel Sambuc }
32433d6423SLionel Sambuc
free_proc(struct vmproc * vmp)33433d6423SLionel Sambuc void free_proc(struct vmproc *vmp)
34433d6423SLionel Sambuc {
35433d6423SLionel Sambuc map_free_proc(vmp);
36433d6423SLionel Sambuc pt_free(&vmp->vm_pt);
37433d6423SLionel Sambuc region_init(&vmp->vm_regions_avl);
38433d6423SLionel Sambuc #if VMSTATS
39433d6423SLionel Sambuc vmp->vm_bytecopies = 0;
40433d6423SLionel Sambuc #endif
41433d6423SLionel Sambuc vmp->vm_region_top = 0;
42433d6423SLionel Sambuc reset_vm_rusage(vmp);
43433d6423SLionel Sambuc }
44433d6423SLionel Sambuc
clear_proc(struct vmproc * vmp)45433d6423SLionel Sambuc void clear_proc(struct vmproc *vmp)
46433d6423SLionel Sambuc {
47433d6423SLionel Sambuc region_init(&vmp->vm_regions_avl);
48433d6423SLionel Sambuc acl_clear(vmp);
49433d6423SLionel Sambuc vmp->vm_flags = 0; /* Clear INUSE, so slot is free. */
50433d6423SLionel Sambuc #if VMSTATS
51433d6423SLionel Sambuc vmp->vm_bytecopies = 0;
52433d6423SLionel Sambuc #endif
53433d6423SLionel Sambuc vmp->vm_region_top = 0;
54433d6423SLionel Sambuc reset_vm_rusage(vmp);
55433d6423SLionel Sambuc }
56433d6423SLionel Sambuc
57433d6423SLionel Sambuc /*===========================================================================*
58433d6423SLionel Sambuc * do_exit *
59433d6423SLionel Sambuc *===========================================================================*/
do_exit(message * msg)60433d6423SLionel Sambuc int do_exit(message *msg)
61433d6423SLionel Sambuc {
62433d6423SLionel Sambuc int proc;
63433d6423SLionel Sambuc struct vmproc *vmp;
64433d6423SLionel Sambuc
65433d6423SLionel Sambuc SANITYCHECK(SCL_FUNCTIONS);
66433d6423SLionel Sambuc
67433d6423SLionel Sambuc if(vm_isokendpt(msg->VME_ENDPOINT, &proc) != OK) {
68433d6423SLionel Sambuc printf("VM: bogus endpoint VM_EXIT %d\n", msg->VME_ENDPOINT);
69433d6423SLionel Sambuc return EINVAL;
70433d6423SLionel Sambuc }
71433d6423SLionel Sambuc vmp = &vmproc[proc];
72433d6423SLionel Sambuc
73433d6423SLionel Sambuc if(!(vmp->vm_flags & VMF_EXITING)) {
74433d6423SLionel Sambuc printf("VM: unannounced VM_EXIT %d\n", msg->VME_ENDPOINT);
75433d6423SLionel Sambuc return EINVAL;
76433d6423SLionel Sambuc }
77*63483e02SCristiano Giuffrida if(vmp->vm_flags & VMF_VM_INSTANCE) {
78*63483e02SCristiano Giuffrida vmp->vm_flags &= ~VMF_VM_INSTANCE;
79*63483e02SCristiano Giuffrida num_vm_instances--;
80*63483e02SCristiano Giuffrida }
81433d6423SLionel Sambuc
82433d6423SLionel Sambuc {
83433d6423SLionel Sambuc /* Free pagetable and pages allocated by pt code. */
84433d6423SLionel Sambuc SANITYCHECK(SCL_DETAIL);
85433d6423SLionel Sambuc free_proc(vmp);
86433d6423SLionel Sambuc SANITYCHECK(SCL_DETAIL);
87433d6423SLionel Sambuc }
88433d6423SLionel Sambuc SANITYCHECK(SCL_DETAIL);
89433d6423SLionel Sambuc
90433d6423SLionel Sambuc /* Reset process slot fields. */
91433d6423SLionel Sambuc clear_proc(vmp);
92433d6423SLionel Sambuc
93433d6423SLionel Sambuc SANITYCHECK(SCL_FUNCTIONS);
94433d6423SLionel Sambuc return OK;
95433d6423SLionel Sambuc }
96433d6423SLionel Sambuc
97433d6423SLionel Sambuc /*===========================================================================*
98433d6423SLionel Sambuc * do_willexit *
99433d6423SLionel Sambuc *===========================================================================*/
do_willexit(message * msg)100433d6423SLionel Sambuc int do_willexit(message *msg)
101433d6423SLionel Sambuc {
102433d6423SLionel Sambuc int proc;
103433d6423SLionel Sambuc struct vmproc *vmp;
104433d6423SLionel Sambuc
105433d6423SLionel Sambuc if(vm_isokendpt(msg->VMWE_ENDPOINT, &proc) != OK) {
106433d6423SLionel Sambuc printf("VM: bogus endpoint VM_EXITING %d\n",
107433d6423SLionel Sambuc msg->VMWE_ENDPOINT);
108433d6423SLionel Sambuc return EINVAL;
109433d6423SLionel Sambuc }
110433d6423SLionel Sambuc vmp = &vmproc[proc];
111433d6423SLionel Sambuc
112433d6423SLionel Sambuc vmp->vm_flags |= VMF_EXITING;
113433d6423SLionel Sambuc
114433d6423SLionel Sambuc return OK;
115433d6423SLionel Sambuc }
116433d6423SLionel Sambuc
do_procctl(message * msg,int transid)117433d6423SLionel Sambuc int do_procctl(message *msg, int transid)
118433d6423SLionel Sambuc {
119433d6423SLionel Sambuc endpoint_t proc;
120433d6423SLionel Sambuc struct vmproc *vmp;
121433d6423SLionel Sambuc
122433d6423SLionel Sambuc if(vm_isokendpt(msg->VMPCTL_WHO, &proc) != OK) {
123433d6423SLionel Sambuc printf("VM: bogus endpoint VM_PROCCTL %ld\n",
124433d6423SLionel Sambuc msg->VMPCTL_WHO);
125433d6423SLionel Sambuc return EINVAL;
126433d6423SLionel Sambuc }
127433d6423SLionel Sambuc vmp = &vmproc[proc];
128433d6423SLionel Sambuc
129433d6423SLionel Sambuc switch(msg->VMPCTL_PARAM) {
130433d6423SLionel Sambuc case VMPPARAM_CLEAR:
131433d6423SLionel Sambuc if(msg->m_source != RS_PROC_NR
132433d6423SLionel Sambuc && msg->m_source != VFS_PROC_NR)
133433d6423SLionel Sambuc return EPERM;
134433d6423SLionel Sambuc free_proc(vmp);
135433d6423SLionel Sambuc if(pt_new(&vmp->vm_pt) != OK)
136433d6423SLionel Sambuc panic("VMPPARAM_CLEAR: pt_new failed");
137433d6423SLionel Sambuc pt_bind(&vmp->vm_pt, vmp);
138433d6423SLionel Sambuc return OK;
139433d6423SLionel Sambuc case VMPPARAM_HANDLEMEM:
140433d6423SLionel Sambuc {
141433d6423SLionel Sambuc if(msg->m_source != VFS_PROC_NR)
142433d6423SLionel Sambuc return EPERM;
143433d6423SLionel Sambuc
144433d6423SLionel Sambuc handle_memory_start(vmp, msg->VMPCTL_M1,
145433d6423SLionel Sambuc msg->VMPCTL_LEN, msg->VMPCTL_FLAGS,
146433d6423SLionel Sambuc VFS_PROC_NR, VFS_PROC_NR, transid, 1);
147433d6423SLionel Sambuc
148433d6423SLionel Sambuc return SUSPEND;
149433d6423SLionel Sambuc }
150433d6423SLionel Sambuc default:
151433d6423SLionel Sambuc return EINVAL;
152433d6423SLionel Sambuc }
153433d6423SLionel Sambuc
154433d6423SLionel Sambuc return OK;
155433d6423SLionel Sambuc }
156433d6423SLionel Sambuc
157