dma_buf = mmap(0, ATA_DMA_BUF_SIZE, PROT_READ|PROT_WRITE,
MAP_PREALLOC | MAP_CONTIG | MAP_ANON, -1, 0);
prdt = mmap(0, PRDT_BYTES,
- PROT_READ|PROT_WRITE, MAP_CONTIG | MAP_ANON, -1, 0);
+ PROT_READ|PROT_WRITE,
+ MAP_PREALLOC | MAP_CONTIG | MAP_ANON, -1, 0);
if(dma_buf == MAP_FAILED || prdt == MAP_FAILED) {
disable_dma = 1;
printf("at_wini%d: no dma\n", w_instance);
/* Save proc_ptr, because it may be changed by debug statements. */
saved_proc = proc_ptr;
- CHECK_RUNQUEUES;
-
ep = &ex_data[vec_nr];
if (vec_nr == 2) { /* spurious NMI on some machines */
int verifyrange = 0;
extern u32_t newpde, overwritepde, linlincopies,
- physzero, invlpgs, vmcheckranges, straightpdes;
+ physzero, invlpgs, straightpdes;
#define PROCPDEPTR(pr, pi) ((u32_t *) ((u8_t *) vm_pagedirs +\
I386_PAGE_SIZE * pr->p_nr + \
u32_t i386_invlpg_addr = 0;
-#define WANT_FREEPDES 4
+#define WANT_FREEPDES 100
#define NOPDE -1
#define PDEMASK(n) (1L << (n))
PRIVATE int nfreepdes = 0, freepdes[WANT_FREEPDES], inusepde = NOPDE;
return 1;
}
-int vm_checkrange_verbose = 0;
-
extern u32_t vmreqs;
/*===========================================================================*
NOREC_RETURN(deliver, r);
}
-/*===========================================================================*
- * vm_checkrange *
- *===========================================================================*/
-PUBLIC int vm_checkrange(struct proc *caller, struct proc *target,
- vir_bytes vir, vir_bytes bytes, int wrfl, int checkonly)
-{
- u32_t flags, po, v;
- int r;
-
- NOREC_ENTER(vmcheckrange);
-
- vmcheckranges++;
-
- if(!HASPT(target))
- NOREC_RETURN(vmcheckrange, OK);
-
- /* If caller has had a reply to this request, return it. */
- if(!verifyrange && RTS_ISSET(caller, VMREQUEST)) {
- if(caller->p_vmrequest.who == target->p_endpoint) {
- vmassert(caller->p_vmrequest.vmresult != VMSUSPEND);
- RTS_LOCK_UNSET(caller, VMREQUEST);
-#if 1
- kprintf("SYSTEM: vm_checkrange: returning vmresult %d\n",
- caller->p_vmrequest.vmresult);
-#endif
- NOREC_RETURN(vmcheckrange, caller->p_vmrequest.vmresult);
- } else {
-#if 1
- kprintf("SYSTEM: vm_checkrange: caller has a request for %d, "
- "but our target is %d\n",
- caller->p_vmrequest.who, target->p_endpoint);
-#endif
- }
- }
-
- po = vir % I386_PAGE_SIZE;
- if(po > 0) {
- vir -= po;
- bytes += po;
- }
-
- vmassert(target);
- vmassert(bytes > 0);
-
- for(v = vir; v < vir + bytes; v+= I386_PAGE_SIZE) {
- u32_t phys;
- int r;
-
- /* If page exists and it's writable if desired, we're OK
- * for this page.
- */
- if((r=vm_lookup(target, v, &phys, &flags)) == OK &&
- !(wrfl && !(flags & I386_VM_WRITE))) {
- continue;
- }
-
- if(verifyrange) {
- int wrok;
- wrok = !(wrfl && !(flags & I386_VM_WRITE));
- printf("checkrange failed; lookup: %d; write ok: %d\n",
- r, wrok);
- }
-
- if(!checkonly) {
- vmassert(k_reenter == -1);
- vm_suspend(caller, target, vir, bytes, wrfl,
- VMSTYPE_KERNELCALL);
- }
-
- NOREC_RETURN(vmcheckrange, VMSUSPEND);
- }
-
- NOREC_RETURN(vmcheckrange, OK);
-}
-
char *flagstr(u32_t e, int dir)
{
static char str[80];
o = lin % I386_PAGE_SIZE;
lin -= o;
limit = (limit + o) & I386_VM_ADDR_MASK;
-#if 0
+#if 1
for(i386_invlpg_addr = lin; i386_invlpg_addr <= limit;
i386_invlpg_addr += I386_PAGE_SIZE) {
invlpgs++;
level0(i386_invlpg_level0);
}
#else
- vm_cr3= ptproc->p_seg.p_cr3;
- vmassert(vm_cr3);
- level0(set_cr3);
+ level0(reload_cr3);
#endif
}
* address space), SEG (hardware segment), VIRT (in-datasegment
* address if known).
*/
-#define CREATEPDE(PROC, PTR, LINADDR, REMAIN, BYTES) { \
+#define CREATEPDE(PROC, PTR, LINADDR, REMAIN, BYTES, PDE) { \
int proc_pde_index; \
FIXME("CREATEPDE: check if invlpg is necessary"); \
proc_pde_index = I386_VM_PDE(LINADDR); \
+ PDE = NOPDE; \
if((PROC) && (((PROC) == ptproc) || iskernelp(PROC))) { \
PTR = LINADDR; \
straightpdes++; \
} else { \
- int use_pde = NOPDE; \
int fp; \
int mustinvl; \
u32_t pdeval, *pdevalptr, mask; \
int k = freepdes[fp]; \
if(inusepde == k) \
continue; \
- use_pde = k; \
+ PDE = k; \
mask = PDEMASK(k); \
vmassert(mask); \
if(dirtypde & mask) \
continue; \
break; \
} \
- vmassert(use_pde != NOPDE); \
+ vmassert(PDE != NOPDE); \
vmassert(mask); \
if(dirtypde & mask) { \
mustinvl = 1; \
overwritepde++; \
} else { \
mustinvl = 0; \
- dirtypde |= mask; \
newpde++; \
} \
- inusepde = use_pde; \
- *PROCPDEPTR(ptproc, use_pde) = pdeval; \
+ inusepde = PDE; \
+ *PROCPDEPTR(ptproc, PDE) = pdeval; \
offset = LINADDR & I386_VM_OFFSET_MASK_4MB; \
- PTR = I386_BIG_PAGE_SIZE*use_pde + offset; \
+ PTR = I386_BIG_PAGE_SIZE*PDE + offset; \
REMAIN = MIN(REMAIN, I386_BIG_PAGE_SIZE - offset); \
- if(1 || mustinvl) { \
+ if(mustinvl) { \
invlpg_range(PTR, REMAIN); \
} \
} \
}
+#define DONEPDE(PDE) { \
+ if(PDE != NOPDE) { \
+ dirtypde |= PDEMASK(PDE); \
+ *PROCPDEPTR(ptproc, PDE) = 0; \
+ } \
+}
+
+
/*===========================================================================*
* lin_lin_copy *
while(bytes > 0) {
phys_bytes srcptr, dstptr;
vir_bytes chunk = bytes;
+ int srcpde, dstpde;
/* Set up 4MB ranges. */
inusepde = NOPDE;
- CREATEPDE(srcproc, srcptr, srclinaddr, chunk, bytes);
- CREATEPDE(dstproc, dstptr, dstlinaddr, chunk, bytes);
+ CREATEPDE(srcproc, srcptr, srclinaddr, chunk, bytes, srcpde);
+ CREATEPDE(dstproc, dstptr, dstlinaddr, chunk, bytes, dstpde);
/* Copy pages. */
vmassert(intr_disabled());
vmassert(catch_pagefaults);
catch_pagefaults = 0;
+ DONEPDE(srcpde);
+ DONEPDE(dstpde);
+
if(addr) {
if(addr >= srcptr && addr < (srcptr + chunk)) {
NOREC_RETURN(linlincopy, EFAULT_SRC);
* We can do this 4MB at a time.
*/
while(bytes > 0) {
+ int pde;
vir_bytes chunk = bytes;
phys_bytes ptr;
inusepde = NOPDE;
- CREATEPDE(((struct proc *) NULL), ptr, ph, chunk, bytes);
+ CREATEPDE(((struct proc *) NULL), ptr, ph, chunk, bytes, pde);
/* We can memset as many bytes as we have remaining,
* or as many as remain in the 4MB chunk we mapped in.
*/
phys_memset(ptr, p, chunk);
+ DONEPDE(pde);
bytes -= chunk;
ph += chunk;
}
return virtual_copy(&src, &dst, bytes);
}
+/*===========================================================================*
+ * data_copy_vmcheck *
+ *===========================================================================*/
+PUBLIC int data_copy_vmcheck(
+ endpoint_t from_proc, vir_bytes from_addr,
+ endpoint_t to_proc, vir_bytes to_addr,
+ size_t bytes)
+{
+ struct vir_addr src, dst;
+
+ src.segment = dst.segment = D;
+ src.offset = from_addr;
+ dst.offset = to_addr;
+ src.proc_nr_e = from_proc;
+ dst.proc_nr_e = to_proc;
+
+ return virtual_copy_vmcheck(&src, &dst, bytes);
+}
+
/*===========================================================================*
* arch_pre_exec *
*===========================================================================*/
.define _pagefault_count
.define _cr3_test
.define _cr3_reload
+.define _reload_cr3
.define _write_cr3 ! write cr3
.define errexception
mov (loadedcr3), eax
mov eax, (_proc_ptr)
mov (_ptproc), eax
-! mov (_dirtypde), 0
+ mov (_dirtypde), 0
0:
lea eax, P_STACKTOP(esp) ! arrange for next interrupt
mov (_tss+TSS3_S_SP0), eax ! to save state in process table
mov ebp, esp
mov eax, 8(ebp)
inc (_cr3_test)
-! cmp eax, (loadedcr3)
-! jz 0f
+ cmp eax, (loadedcr3)
+ jz 0f
inc (_cr3_reload)
mov cr3, eax
mov (loadedcr3), eax
-! mov (_dirtypde), 0
+ mov (_dirtypde), 0
0:
pop ebp
ret
+!*===========================================================================*
+!* reload_cr3 *
+!*===========================================================================*
+! PUBLIC void reload_cr3(void);
+_reload_cr3:
+ push ebp
+ mov ebp, esp
+ inc (_cr3_reload)
+ mov (_dirtypde), 0
+ mov eax, cr3
+ mov cr3, eax
+ pop ebp
+ ret
+
!*===========================================================================*
!* level0_call *
!*===========================================================================*
_PROTOTYPE( int _memcpy_k, (void *dst, void *src, size_t n) );
_PROTOTYPE( int _memcpy_k_fault, (void) );
_PROTOTYPE( u32_t read_cr3, (void) );
+_PROTOTYPE( void reload_cr3, (void) );
/* protect.c */
_PROTOTYPE( void prot_init, (void) );
case '2':
ser_dump_queues();
break;
+#if DEBUG_TRACE
#define TOGGLECASE(ch, flag) \
case ch: { \
if(verboseflags & flag) { \
}
TOGGLECASE('8', VF_SCHEDULING)
TOGGLECASE('9', VF_PICKPROC)
+#endif
}
do_serial_debug--;
if(u) { unlock; }
return;
}
- if(pp->p_ready && pp->p_rts_flags) {
- printf("HUH? p_ready but rts flags!\n");
- }
-
- if(!pp->p_ready && !pp->p_rts_flags) {
- printf("HUH? not p_ready but no rts flags!\n");
- }
-
COL
- kprintf("%d: %s %d prio %d/%d time %d/%d cr3 0x%lx rts %s misc %s ready %d",
+ kprintf("%d: %s %d prio %d/%d time %d/%d cr3 0x%lx rts %s misc %s",
proc_nr(pp), pp->p_name, pp->p_endpoint,
pp->p_priority, pp->p_max_priority, pp->p_user_time,
pp->p_sys_time, pp->p_seg.p_cr3,
- rtsflagstr(pp->p_rts_flags), miscflagstr(pp->p_misc_flags),
- pp->p_ready);
+ rtsflagstr(pp->p_rts_flags), miscflagstr(pp->p_misc_flags));
if(pp->p_rts_flags & SENDING) {
dep = pp->p_sendto_e;
COL
proc_stacktrace(pp);
- if(pp->p_rts_flags & VMREQUEST) {
- COL
- printf("vmrequest set with: %s\n", pp->p_vmrequest.stacktrace);
- }
-
if(depproc)
printslot(depproc, level+1);
}
{
struct proc *pp;
- CHECK_RUNQUEUES;
-
for (pp= BEG_PROC_ADDR; pp < END_PROC_ADDR; pp++)
{
if (pp->p_rts_flags & SLOT_FREE)
#define DEBUG_TIME_LOCKS 1
/* Runtime sanity checking. */
-#define DEBUG_VMASSERT 1
-#define DEBUG_SCHED_CHECK 1
-#define DEBUG_STACK_CHECK 1
-#define DEBUG_TRACE 1
+#define DEBUG_VMASSERT 0
+#define DEBUG_SCHED_CHECK 0
+#define DEBUG_STACK_CHECK 0
+#define DEBUG_TRACE 0
#if DEBUG_TRACE
vir_bytes bytes, int vmcheck) );
_PROTOTYPE( int data_copy, (endpoint_t from, vir_bytes from_addr,
endpoint_t to, vir_bytes to_addr, size_t bytes));
+_PROTOTYPE( int data_copy_vmcheck, (endpoint_t from, vir_bytes from_addr,
+ endpoint_t to, vir_bytes to_addr, size_t bytes));
#define data_copy_to(d, p, v, n) data_copy(SYSTEM, (d), (p), (v), (n));
#define data_copy_from(d, p, v, n) data_copy((p), (v), SYSTEM, (d), (n));
_PROTOTYPE( void alloc_segments, (struct proc *rp) );
FORWARD _PROTOTYPE( struct proc *vmrestart_check, (message *));
u32_t cr3_test, cr3_reload, newpde, overwritepde,
- linlincopies, physzero, invlpgs, npagefaults, vmreqs, vmcheckranges, straightpdes;
+ linlincopies, physzero, invlpgs, npagefaults, vmreqs, straightpdes;
/*===========================================================================*
* sys_task *
dt = u - prevu;
if(dt >= 5*system_hz) {
#define PERSEC(n) ((n)*system_hz/dt)
- printf("%6d cr3 tests: %5lu cr3: %5lu straightpdes: %5lu newpde: %5lu overwritepde %5lu linlincopies: %5lu physzero: %5lu invlpgs: %5lu pagefaults: %5lu vmreq: %5lu vmcheckranges: %5lu\n",
+ printf("%6d cr3 tests: %5lu cr3: %5lu straightpdes: %5lu newpde: %5lu overwritepde %5lu linlincopies: %5lu physzero: %5lu invlpgs: %5lu pagefaults: %5lu vmreq: %5lu\n",
u/system_hz,
PERSEC(cr3_test), PERSEC(cr3_reload),
PERSEC(straightpdes), PERSEC(newpde),
PERSEC(overwritepde),
PERSEC(linlincopies), PERSEC(physzero),
PERSEC(invlpgs), PERSEC(npagefaults),
- PERSEC(vmreqs), PERSEC(vmcheckranges));
+ PERSEC(vmreqs));
cr3_reload = 0;
cr3_test = 0;
newpde = overwritepde = linlincopies =
physzero = invlpgs = straightpdes = 0;
npagefaults = 0;
- vmreqs = vmcheckranges = 0;
+ vmreqs = 0;
prevu = u;
}
}
*/
size_t length;
vir_bytes src_vir;
- int proc_nr, nr_e, nr;
+ int proc_nr, nr_e, nr, r;
struct proc *caller;
- phys_bytes ph;
int wipe_rnd_bin = -1;
caller = proc_addr(who_p);
src_vir = (vir_bytes) irq_hooks;
break;
}
- case GET_SCHEDINFO: {
- /* This is slightly complicated because we need two data structures
- * at once, otherwise the scheduling information may be incorrect.
- * Copy the queue heads and fall through to copy the process table.
- */
- if((ph=umap_local(caller, D, (vir_bytes) m_ptr->I_VAL_PTR2,length)) == 0)
- return EFAULT;
- length = sizeof(struct proc *) * NR_SCHED_QUEUES;
- CHECKRANGE_OR_SUSPEND(proc_addr(who_p), ph, length, 1);
- data_copy(SYSTEM, (vir_bytes) rdy_head,
- who_e, (vir_bytes) m_ptr->I_VAL_PTR2, length);
- /* fall through to GET_PROCTAB */
- }
case GET_PROCTAB: {
length = sizeof(struct proc) * (NR_PROCS + NR_TASKS);
src_vir = (vir_bytes) proc;
/* Try to make the actual copy for the requested data. */
if (m_ptr->I_VAL_LEN > 0 && length > m_ptr->I_VAL_LEN) return (E2BIG);
- if((ph=umap_local(caller, D, (vir_bytes) m_ptr->I_VAL_PTR,length)) == 0)
- return EFAULT;
- CHECKRANGE_OR_SUSPEND(caller, ph, length, 1);
- if(data_copy(SYSTEM, src_vir, who_e, (vir_bytes) m_ptr->I_VAL_PTR, length) == OK) {
+ r = data_copy_vmcheck(SYSTEM, src_vir, who_e,
+ (vir_bytes) m_ptr->I_VAL_PTR, length);
+
+ if(r != OK) return r;
+
if(wipe_rnd_bin >= 0 && wipe_rnd_bin < RANDOM_SOURCES) {
krandom.bin[wipe_rnd_bin].r_size = 0;
krandom.bin[wipe_rnd_bin].r_next = 0;
}
- }
+
return(OK);
}
struct sigcontext sc, *scp;
struct sigframe fr, *frp;
int proc, r;
- phys_bytes ph;
if (!isokendpt(m_ptr->SIG_ENDPT, &proc)) return(EINVAL);
if (iskerneln(proc)) return(EPERM);
rp = proc_addr(proc);
- ph = umap_local(proc_addr(who_p), D, (vir_bytes) m_ptr->SIG_CTXT_PTR, sizeof(struct sigmsg));
- if(!ph) return EFAULT;
- CHECKRANGE_OR_SUSPEND(proc_addr(who_p), ph, sizeof(struct sigmsg), 1);
-
/* Get the sigmsg structure into our address space. */
- if((r=data_copy(who_e, (vir_bytes) m_ptr->SIG_CTXT_PTR,
+ if((r=data_copy_vmcheck(who_e, (vir_bytes) m_ptr->SIG_CTXT_PTR,
SYSTEM, (vir_bytes) &smsg, (phys_bytes) sizeof(struct sigmsg))) != OK)
return r;
sc.sc_flags = 0; /* unused at this time */
sc.sc_mask = smsg.sm_mask;
- ph = umap_local(rp, D, (vir_bytes) scp, sizeof(struct sigcontext));
- if(!ph) return EFAULT;
- CHECKRANGE_OR_SUSPEND(rp, ph, sizeof(struct sigcontext), 1);
/* Copy the sigcontext structure to the user's stack. */
- if((r=data_copy(SYSTEM, (vir_bytes) &sc, m_ptr->SIG_ENDPT, (vir_bytes) scp,
- (vir_bytes) sizeof(struct sigcontext))) != OK)
+ if((r=data_copy_vmcheck(SYSTEM, (vir_bytes) &sc, m_ptr->SIG_ENDPT,
+ (vir_bytes) scp, (vir_bytes) sizeof(struct sigcontext))) != OK)
return r;
/* Initialize the sigframe structure. */
fr.sf_signo = smsg.sm_signo;
fr.sf_retadr = (void (*)()) smsg.sm_sigreturn;
- ph = umap_local(rp, D, (vir_bytes) frp, sizeof(struct sigframe));
- if(!ph) return EFAULT;
- CHECKRANGE_OR_SUSPEND(rp, ph, sizeof(struct sigframe), 1);
/* Copy the sigframe structure to the user's stack. */
- if((r=data_copy(SYSTEM, (vir_bytes) &fr, m_ptr->SIG_ENDPT, (vir_bytes) frp,
+ if((r=data_copy_vmcheck(SYSTEM, (vir_bytes) &fr,
+ m_ptr->SIG_ENDPT, (vir_bytes) frp,
(vir_bytes) sizeof(struct sigframe))) != OK)
return r;
PUBLIC int do_sysctl(m_ptr)
register message *m_ptr; /* pointer to request message */
{
- phys_bytes ph;
vir_bytes len, buf;
static char mybuf[DIAG_BUFSIZE];
struct proc *caller, *target;
caller->p_endpoint, len);
return EINVAL;
}
- if((ph=umap_local(caller, D, buf, len)) == 0)
- return EFAULT;
- CHECKRANGE_OR_SUSPEND(caller, ph, len, 1);
- if((s=data_copy(who_e, buf, SYSTEM, (vir_bytes) mybuf, len)) != OK) {
+ if((s=data_copy_vmcheck(who_e, buf, SYSTEM, (vir_bytes) mybuf, len)) != OK) {
kprintf("do_sysctl: diag for %d: len %d: copy failed: %d\n",
caller->p_endpoint, len, s);
return s;
case LOCAL_SEG:
phys_addr = lin_addr = umap_local(targetpr, seg_index, offset, count);
if(!lin_addr) return EFAULT;
- CHECKRANGE_OR_SUSPEND(targetpr, lin_addr, count, 1);
naughty = 1;
break;
case REMOTE_SEG:
phys_addr = lin_addr = umap_remote(targetpr, seg_index, offset, count);
if(!lin_addr) return EFAULT;
- CHECKRANGE_OR_SUSPEND(targetpr, lin_addr, count, 1);
naughty = 1;
break;
case GRANT_SEG:
kprintf("SYSTEM:do_umap: umap_local failed\n");
return EFAULT;
}
- CHECKRANGE_OR_SUSPEND(targetpr, lin_addr, count, 1);
if(vm_lookup(targetpr, lin_addr, &phys_addr, NULL) != OK) {
kprintf("SYSTEM:do_umap: vm_lookup failed\n");
return EFAULT;
#ifndef _VM_H
#define _VM_H 1
-#define CHECKRANGE_OR_SUSPEND(pr, start, length, wr) { int mr; \
- FIXME("CHECKRANGE_OR_SUSPEND exists"); \
- if(vm_running && (mr=vm_checkrange(proc_addr(who_p), pr, start, length, wr, 0)) != OK) { \
- return mr; \
- } }
-
-#define CHECKRANGE(pr, start, length, wr) \
- vm_checkrange(proc_addr(who_p), pr, start, length, wr, 1)
-
/* Pseudo error codes */
#define VMSUSPEND -996
#define EFAULT_SRC -995
{ F5, monparams_dmp, "Boot monitor parameters" },
{ F6, irqtab_dmp, "IRQ hooks and policies" },
{ F7, kmessages_dmp, "Kernel messages" },
- { F9, sched_dmp, "Scheduling queues" },
{ F10, kenv_dmp, "Kernel parameters" },
{ F11, timing_dmp, "Timing details (if enabled)" },
{ SF1, mproc_dmp, "Process manager process table" },
printf("\n");
}
-/*===========================================================================*
- * sched_dmp *
- *===========================================================================*/
-PUBLIC void sched_dmp()
-{
- struct proc *rdy_head[NR_SCHED_QUEUES];
- struct kinfo kinfo;
- register struct proc *rp;
- vir_bytes ptr_diff;
- int r;
-
- /* First obtain a scheduling information. */
- if ((r = sys_getschedinfo(proc, rdy_head)) != OK) {
- report("IS","warning: couldn't get copy of process table", r);
- return;
- }
- /* Then obtain kernel addresses to correct pointer information. */
- if ((r = sys_getkinfo(&kinfo)) != OK) {
- report("IS","warning: couldn't get kernel addresses", r);
- return;
- }
-
- /* Update all pointers. Nasty pointer algorithmic ... */
- ptr_diff = (vir_bytes) proc - (vir_bytes) kinfo.proc_addr;
- for (r=0;r<NR_SCHED_QUEUES; r++)
- if (rdy_head[r] != NIL_PROC)
- rdy_head[r] =
- (struct proc *)((vir_bytes) rdy_head[r] + ptr_diff);
- for (rp=BEG_PROC_ADDR; rp < END_PROC_ADDR; rp++)
- if (rp->p_nextready != NIL_PROC)
- rp->p_nextready =
- (struct proc *)((vir_bytes) rp->p_nextready + ptr_diff);
-
- /* Now show scheduling queues. */
- printf("Dumping scheduling queues.\n");
-
- for (r=0;r<NR_SCHED_QUEUES; r++) {
- rp = rdy_head[r];
- if (!rp) continue;
- printf("%2d: ", r);
- while (rp != NIL_PROC) {
- printf("%3d ", rp->p_nr);
- rp = rp->p_nextready;
- }
- printf("\n");
- }
- printf("\n");
-}
/*===========================================================================*
* kenv_dmp *
#define VM_PAGE_SIZE I386_PAGE_SIZE
/* Where do processes start in linear (i.e. page table) memory? */
-#define VM_PROCSTART (I386_BIG_PAGE_SIZE*10)
+#define VM_PROCSTART (I386_BIG_PAGE_SIZE*100)
#define CLICKSPERPAGE (I386_PAGE_SIZE/CLICK_SIZE)