Basic VM and other minor improvements.

Not complete, probably not fully debugged or optimized.
This commit is contained in:
Ben Gras 2008-11-19 12:26:10 +00:00
parent c888305e21
commit c078ec0331
273 changed files with 10814 additions and 4305 deletions

View file

@ -27,7 +27,7 @@ usage:
# 'make install' target.
#
# etcfiles has to be done first.
world: includes depend libraries cmds install postinstall
world: includes depend cmds install postinstall
includes:
cd include && $(MAKE) install gcc

View file

@ -18,6 +18,7 @@ char version[]= "2.20";
#include <string.h>
#include <errno.h>
#include <ibm/partition.h>
#include <ibm/bios.h>
#include <minix/config.h>
#include <minix/type.h>
#include <minix/com.h>
@ -28,6 +29,7 @@ char version[]= "2.20";
#if BIOS
#include <kernel/const.h>
#include <kernel/type.h>
#include <sys/video.h>
#endif
#if UNIX
#include <stdio.h>
@ -46,6 +48,10 @@ char version[]= "2.20";
#define arraylimit(a) ((a) + arraysize(a))
#define between(a, c, z) ((unsigned) ((c) - (a)) <= ((z) - (a)))
u16_t vid_port; /* Video i/o port. */
u32_t vid_mem_base; /* Video memory base address. */
u32_t vid_mem_size; /* Video memory size. */
int fsok= -1; /* File system state. Initially unknown. */
static int block_size;
@ -590,6 +596,19 @@ void initialize(void)
bootdev.name[5] += bootdev.secondary;
}
/* Find out about the video hardware. */
raw_copy(mon2abs(&vid_port), VDU_CRT_BASE_ADDR, sizeof(vid_port));
if(vid_port == C_6845) {
vid_mem_base = COLOR_BASE;
vid_mem_size = COLOR_SIZE;
} else {
vid_mem_base = MONO_BASE;
vid_mem_size = MONO_SIZE;
}
if(get_video() >= 3)
vid_mem_size = EGA_SIZE;
#else /* DOS */
/* Take the monitor out of the memory map if we have memory to spare,
* note that only half our PSP is needed at the new place, the first
@ -1959,3 +1978,4 @@ void main(int argc, char **argv)
/*
* $PchId: boot.c,v 1.14 2002/02/27 19:46:14 philip Exp $
*/

View file

@ -18,6 +18,8 @@
#include <minix/const.h>
#include <minix/type.h>
#include <minix/syslib.h>
#include <minix/tty.h>
#include <sys/video.h>
#include <kernel/const.h>
#include <kernel/type.h>
#include <ibm/partition.h>
@ -27,6 +29,10 @@
static int block_size = 0;
extern u16_t vid_port; /* Video i/o port. */
extern u32_t vid_mem_base; /* Video memory base address. */
extern u32_t vid_mem_size; /* Video memory size. */
#define click_shift clck_shft /* 7 char clash with click_size. */
/* Some kernels have extra features: */
@ -376,6 +382,42 @@ int get_segment(u32_t *vsec, long *size, u32_t *addr, u32_t limit)
return 1;
}
static void restore_screen(void)
{
struct boot_tty_info boot_tty_info;
u32_t info_location;
#define LINES 25
#define CHARS 80
static u16_t consolescreen[LINES][CHARS];
/* Try and find out what the main console was displaying
* by looking into video memory.
*/
info_location = vid_mem_base+vid_mem_size-sizeof(boot_tty_info);
raw_copy(mon2abs(&boot_tty_info), info_location,
sizeof(boot_tty_info));
if(boot_tty_info.magic == TTYMAGIC) {
if(boot_tty_info.flags & (BTIF_CONSORIGIN|BTIF_CONSCURSOR) ==
(BTIF_CONSORIGIN|BTIF_CONSCURSOR)) {
int line;
raw_copy(mon2abs(consolescreen),
vid_mem_base + boot_tty_info.consorigin,
sizeof(consolescreen));
clear_screen();
for(line = 0; line < LINES; line++) {
int ch;
for(ch = 0; ch < CHARS; ch++) {
u16_t newch = consolescreen[line][ch] & BYTE;
if(newch < ' ') newch = ' ';
putch(newch);
}
}
}
}
}
void exec_image(char *image)
/* Get a Minix image into core, patch it up and execute. */
{
@ -607,8 +649,13 @@ void exec_image(char *image)
/* Read leftover character, if any. */
scan_keyboard();
/* Restore screen contents. */
restore_screen();
}
ino_t latest_version(char *version, struct stat *stp)
/* Recursively read the current directory, selecting the newest image on
* the way up. (One can't use r_stat while reading a directory.)

View file

@ -61,7 +61,7 @@ static char dirbuf[_MAX_BLOCK_SIZE]; /* Scratch/Directory block. */
static block_t a_indir, a_dindir; /* Addresses of the indirects. */
static off_t dirpos; /* Reading pos in a dir. */
#define fsbuf(b) (* (struct buf *) (b))
#define fsbuf(b) (* (union fsdata_u *) (b))
#define zone_shift (super.s_log_zone_size) /* zone to block ratio */
@ -110,6 +110,7 @@ void r_stat(Ino_t inum, struct stat *stp)
block_t block;
block_t ino_block;
ino_t ino_offset;
union fsdata_u *blockbuf;
/* Calculate start of i-list */
block = START_BLOCK + super.s_imap_blocks + super.s_zmap_blocks;
@ -120,13 +121,14 @@ void r_stat(Ino_t inum, struct stat *stp)
block += ino_block;
/* Fetch the block */
readblock(block, scratch, block_size);
blockbuf = (union fsdata_u *) scratch;
readblock(block, blockbuf, block_size);
if (super.s_magic == SUPER_V2 || super.s_magic == SUPER_V3) {
d2_inode *dip;
int i;
dip= &fsbuf(scratch).b_v2_ino[ino_offset];
dip= &blockbuf->b__v2_ino[ino_offset];
curfil.i_mode= dip->d2_mode;
curfil.i_nlinks= dip->d2_nlinks;
@ -142,7 +144,7 @@ void r_stat(Ino_t inum, struct stat *stp)
d1_inode *dip;
int i;
dip= &fsbuf(scratch).b_v1_ino[ino_offset];
dip= &blockbuf->b__v1_ino[ino_offset];
curfil.i_mode= dip->d1_mode;
curfil.i_nlinks= dip->d1_nlinks;
@ -263,8 +265,8 @@ off_t r_vir2abs(off_t virblk)
i = zone / (zone_t) nr_indirects;
ind_zone = (super.s_magic == SUPER_V2 || super.s_magic == SUPER_V3)
? fsbuf(dindir).b_v2_ind[i]
: fsbuf(dindir).b_v1_ind[i];
? fsbuf(dindir).b__v2_ind[i]
: fsbuf(dindir).b__v1_ind[i];
zone %= (zone_t) nr_indirects;
}
if (ind_zone == 0) return 0;
@ -276,8 +278,8 @@ off_t r_vir2abs(off_t virblk)
a_indir= z;
}
zone = (super.s_magic == SUPER_V2 || super.s_magic == SUPER_V3)
? fsbuf(indir).b_v2_ind[(int) zone]
: fsbuf(indir).b_v1_ind[(int) zone];
? fsbuf(indir).b__v2_ind[(int) zone]
: fsbuf(indir).b__v1_ind[(int) zone];
/* Calculate absolute datablock number */
z = ((block_t) zone << zone_shift) + zone_index;

View file

@ -4,7 +4,7 @@ MAKE = exec make -$(MAKEFLAGS)
BZIP2=bzip2-1.0.3
FLEX=flex-2.5.4
SMALLPROGRAMS=`arch` aal advent ash autil awk byacc cawf cron de dhcpd dis88 elle elvis ftp101 ftpd200 ibm indent m4 make mdb mined patch pax profile ps reboot rlogind scripts sh simple syslogd talk talkd telnet telnetd urlget yap zoneinfo
SMALLPROGRAMS=`arch` aal advent ash autil awk byacc cawf cron de dhcpd dis88 elle elvis ftp101 ftpd200 ibm indent m4 make mined patch pax profile ps reboot rlogind scripts sh simple syslogd talk talkd telnet telnetd urlget yap
usage:
@echo "Usage: make all # Compile all commands" >&2

View file

@ -55,16 +55,16 @@ sh: $(OBJS)
install: /usr/bin/ash /usr/bin/sh /bin/sh /bin/bigsh
/usr/bin/ash: sh
install -cs -o bin $? $@
install -cs -o bin $< $@
/usr/bin/sh: /usr/bin/ash
install -l $? $@
install -l $< $@
/bin/sh: /usr/bin/ash
install -lcs $? $@
install -lcs $< $@
/bin/bigsh: /usr/bin/ash
install -S 6600k -lcs $? $@
install -S 6600k -lcs $< $@
clean:
rm -f $(CLEANFILES) sh core
@ -75,7 +75,7 @@ token.def: mktokens
sh mktokens
arith.c: arith.y
$(YACC) -d $?
$(YACC) -d $<
mv y.tab.c $@
mv y.tab.h arith_y.h

View file

@ -22,8 +22,7 @@ ALL = \
postmort \
recwave \
repartition \
screendump \
sdump \
screendump
all: $(ALL)
@ -109,7 +108,6 @@ install: \
/usr/bin/recwave \
/usr/bin/repartition \
/usr/bin/screendump \
/usr/bin/sdump \
/bin/loadkeys \
/usr/bin/atnormalize: atnormalize

View file

@ -30,11 +30,11 @@ servers/inet/inet
servers/is/is
servers/pm/pm
servers/rs/rs
servers/vm/vm
servers/rs/service
drivers/at_wini/at_wini
drivers/bios_wini/bios_wini
drivers/cmos/cmos
drivers/dp8390/dp8390
drivers/dpeth/dpeth
drivers/floppy/floppy

View file

@ -84,6 +84,7 @@
#include "../../servers/pm/mproc.h"
#include "../../servers/vfs/fproc.h"
#include "../../servers/vfs/const.h"
#include "../../servers/mfs/const.h"
/*----- ps's local stuff below this line ------*/
@ -109,7 +110,9 @@ size_t n_ttyinfo; /* Number of tty info slots */
/* Number of tasks and processes and addresses of the main process tables. */
int nr_tasks, nr_procs;
#if 0
vir_bytes proc_addr, mproc_addr, fproc_addr;
#endif
extern int errno;
/* Process tables of the kernel, MM, and FS. */
@ -315,10 +318,14 @@ char *argv[];
if ((memfd = open(MEM_PATH, O_RDONLY)) == -1) err(MEM_PATH);
if (gettynames() == -1) err("Can't get tty names");
#if 0
getsysinfo(PM_PROC_NR, SI_PROC_ADDR, &mproc_addr);
getsysinfo(FS_PROC_NR, SI_PROC_ADDR, &fproc_addr);
#endif
getsysinfo(PM_PROC_NR, SI_KINFO, &kinfo);
#if 0
proc_addr = kinfo.proc_addr;
#endif
nr_tasks = kinfo.nr_tasks;
nr_procs = kinfo.nr_procs;
@ -329,6 +336,7 @@ char *argv[];
if (ps_proc == NULL || ps_mproc == NULL || ps_fproc == NULL)
err("Out of memory");
#if 0
/* Get kernel process table */
if (addrread(kmemfd, (phys_clicks) 0,
proc_addr, (char *) ps_proc,
@ -347,6 +355,17 @@ char *argv[];
nr_procs * sizeof(ps_fproc[0]))
!= nr_procs * sizeof(ps_fproc[0]))
err("Can't get fs proc table from /dev/mem");
#else
if(getsysinfo(PM_PROC_NR, SI_KPROC_TAB, ps_proc) < 0) {
fprintf(stderr, "getsysinfo() for SI_KPROC_TAB failed.\n");
exit(1);
}
if(getsysinfo(PM_PROC_NR, SI_PROC_TAB, ps_mproc) < 0) {
fprintf(stderr, "getsysinfo() for SI_PROC_TAB failed.\n");
exit(1);
}
#endif
/* We need to know where INIT hangs out. */
for (i = FS_PROC_NR; i < nr_procs; i++) {
@ -479,8 +498,13 @@ int endpoints;
bufp->ps_flags = ps_proc[p_ki].p_rts_flags;
if (p_nr >= low_user) {
#if 0
bufp->ps_dev = ps_fproc[p_nr].fp_tty;
bufp->ps_ftask = ps_fproc[p_nr].fp_task;
#else
bufp->ps_dev = 0;
bufp->ps_ftask = 0;
#endif
} else {
bufp->ps_dev = 0;
bufp->ps_ftask = 0;
@ -511,9 +535,11 @@ int endpoints;
bufp->ps_state = T_STATE; /* stopped (traced) */
else if (ps_proc[p_ki].p_rts_flags == 0)
bufp->ps_state = R_STATE; /* in run-queue */
#if 0
else if (ps_mproc[p_nr].mp_flags & (WAITING | PAUSED | SIGSUSPENDED) ||
ps_fproc[p_nr].fp_suspended == SUSPENDED)
bufp->ps_state = S_STATE; /* sleeping */
#endif
else
bufp->ps_state = W_STATE; /* a short wait */
} else { /* tasks are simple */

File diff suppressed because it is too large Load diff

View file

@ -479,3 +479,4 @@ char *argv[];
printf("\nwtmp begins %.16s \n", ctime(&wtmp_buffer[0].ut_time));
return(0);
}

View file

@ -56,17 +56,8 @@
#define BIN 2
#define BINGRP 2
#define BIT_MAP_SHIFT 13
#define N_BLOCKS MAX_BLOCK_NR
#define N_BLOCKS16 (128L * 1024)
#define INODE_MAX ((unsigned) 65535)
/* You can make a really large file system on a 16-bit system, but the array
* of bits that get_block()/putblock() needs gets a bit big, so we can only
* prefill MAX_INIT blocks. (16-bit fsck can't check a file system larger
* than N_BLOCKS16 anyway.)
*/
#define MAX_INIT (sizeof(char *) == 2 ? N_BLOCKS16 : N_BLOCKS)
#ifdef DOS
maybedefine O_RDONLY 4 /* O_RDONLY | BINARY_BIT */
@ -90,12 +81,12 @@ char *progname;
long current_time, bin_time;
char *zero, *lastp;
char umap[MAX_INIT / 8]; /* bit map tells if block read yet */
char *umap_array; /* bit map tells if block read yet */
int umap_array_elements = 0;
block_t zone_map; /* where is zone map? (depends on # inodes) */
int inodes_per_block;
int fs_version;
unsigned int block_size;
block_t max_nrblocks;
FILE *proto;
@ -167,14 +158,12 @@ char *argv[];
i = 0;
fs_version = 3;
inodes_per_block = 0;
max_nrblocks = N_BLOCKS;
block_size = 0;
while ((ch = getopt(argc, argv, "12b:di:lotB:")) != EOF)
switch (ch) {
case '1':
fs_version = 1;
inodes_per_block = V1_INODES_PER_BLOCK;
max_nrblocks = 0xFFFF;
break;
case '2':
fs_version = 2;
@ -262,12 +251,6 @@ char *argv[];
/* Read the line with the block and inode counts. */
getline(line, token);
blocks = atol(token[0]);
if (blocks > max_nrblocks) pexit("Block count too large");
if (sizeof(char *) == 2 && blocks > N_BLOCKS16) {
fprintf(stderr,
"%s: warning: FS is larger than the %dM that fsck can check!\n",
progname, (int) (N_BLOCKS16 / (1024L * 1024)));
}
inodes = atoi(token[1]);
/* Process mode line for root directory. */
@ -305,7 +288,6 @@ char *argv[];
}
if (blocks < 5) pexit("Block count too small");
if (blocks > max_nrblocks) pexit("Block count too large");
if (i < 1) pexit("Inode count too small");
if (i > INODE_MAX && fs_version < 3) pexit("Inode count too large");
inodes = (ino_t) i;
@ -320,6 +302,17 @@ char *argv[];
nrblocks = blocks;
nrinodes = inodes;
{
size_t bytes;
bytes = 1 + blocks/8;
if(!(umap_array = malloc(bytes))) {
fprintf(stderr, "mkfs: can't allocate block bitmap (%d bytes).\n",
bytes);
exit(1);
}
umap_array_elements = bytes;
}
/* Open special. */
special(argv[--optind]);
@ -336,7 +329,7 @@ char *argv[];
}
testb[0] = 0x3245;
testb[1] = 0x11FF;
testb[block_size-1] = 0x1F2F;
testb[block_size/2-1] = 0x1F2F;
if ((w=write(fd, (char *) testb, block_size)) != block_size) {
if(w < 0) perror("write");
printf("%d/%d\n", w, block_size);
@ -350,7 +343,7 @@ char *argv[];
testb[1] = 0;
nread = read(fd, (char *) testb, block_size);
if (nread != block_size || testb[0] != 0x3245 || testb[1] != 0x11FF ||
testb[block_size-1] != 0x1F2F) {
testb[block_size/2-1] != 0x1F2F) {
if(nread < 0) perror("read");
printf("nread = %d\n", nread);
printf("testb = 0x%x 0x%x 0x%x\n", testb[0], testb[1], testb[block_size-1]);
@ -370,24 +363,6 @@ printf("testb = 0x%x 0x%x 0x%x\n", testb[0], testb[1], testb[block_size-1]);
cache_init();
#if (MACHINE == ATARI)
if (isdev) {
char block0[BLOCK_SIZE];
get_block((block_t) 0, block0);
/* Need to read twice; first time gets an empty block */
get_block((block_t) 0, block0);
/* Zero parts of the boot block so the disk won't be
* recognized as a tos disk any more. */
block0[0] = block0[1] = 0; /* branch code to boot code */
strncpy(&block0[2], "MINIX ", (size_t) 6);
block0[16] = 0; /* number of FATS */
block0[17] = block0[18] = 0; /* number of dir entries */
block0[22] = block0[23] = 0; /* sectors/FAT */
bzero(&block0[30], 480);/* boot code */
put_block((block_t) 0, block0);
} else
#endif
put_block((block_t) 0, zero); /* Write a null boot block. */
zone_shift = 0; /* for future use */
@ -1229,12 +1204,14 @@ block_t n;
int w, s, mask, r;
if (sizeof(char *) == 2 && n >= MAX_INIT) pexit("can't initialize past 128M");
w = n / 8;
if(w >= umap_array_elements) {
pexit("umap array too small - this can't happen");
}
s = n % 8;
mask = 1 << s;
r = (umap[w] & mask ? 1 : 0);
umap[w] |= mask;
r = (umap_array[w] & mask ? 1 : 0);
umap_array[w] |= mask;
return(r);
}

View file

@ -40,6 +40,7 @@
char *Tclr_all;
#if 0
int print_memory(struct pm_mem_info *pmi)
{
int h;
@ -58,6 +59,7 @@ int print_memory(struct pm_mem_info *pmi)
return 1;
}
#endif
int print_load(double *loads, int nloads)
{
@ -209,10 +211,13 @@ void showtop(int r)
int nloads, i, p, lines = 0;
static struct proc prev_proc[PROCS], proc[PROCS];
struct winsize winsize;
static struct pm_mem_info pmi;
/*
static struct pm_mem_info pmi;
*/
static int prev_uptime, uptime;
static struct mproc mproc[NR_PROCS];
struct tms tms;
int mem = 0;
uptime = times(&tms);
@ -222,10 +227,13 @@ void showtop(int r)
exit(1);
}
#if 0
if(getsysinfo(PM_PROC_NR, SI_MEM_ALLOC, &pmi) < 0) {
fprintf(stderr, "getsysinfo() for SI_MEM_ALLOC failed.\n");
mem = 0;
exit(1);;
}
} else mem = 1;
#endif
if(getsysinfo(PM_PROC_NR, SI_KPROC_TAB, proc) < 0) {
fprintf(stderr, "getsysinfo() for SI_KPROC_TAB failed.\n");
@ -247,7 +255,9 @@ void showtop(int r)
lines += print_load(loads, NLOADS);
lines += print_proc_summary(proc);
lines += print_memory(&pmi);
#if 0
if(mem) { lines += print_memory(&pmi); }
#endif
if(winsize.ws_row > 0) r = winsize.ws_row;
@ -347,3 +357,4 @@ int main(int argc, char *argv[])
return 0;
}
int sys_hz() { return 50; }

View file

@ -22,7 +22,7 @@ all: $(TARGETS)
syslogd: syslogd.o
$(CC) $? $(LDFLAGS)
@install -S 8kw $@
@install $@
syslog_test: syslog_test.o syslog.o
$(CC) syslog_test.o syslog.o $(LDFLAGS)

View file

@ -5,8 +5,7 @@ DRIVER = amddev
CC = exec cc
CFLAGS = $(CPROFILE)
LDFLAGS = -i
#LIBS = -lsysutil -lsys -ltimers
LIBS = -lsysutil -lsys
LIBS = -lsys
OBJ = amddev.o

View file

@ -15,7 +15,7 @@ Driver for the AMD Device Exclusion Vector (DEV)
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <sys/vm.h>
#include <sys/vm_i386.h>
#include <minix/com.h>
#include <minix/const.h>
#include <minix/ipc.h>
@ -213,17 +213,13 @@ static void write_reg(int function, int index, u32_t value)
static void init_domain(int index)
{
int r;
size_t o, size, memsize;
phys_bytes busaddr;
size= 0x100000 / 8;
table= malloc(size + PAGE_SIZE);
table= alloc_contig(size, AC_ALIGN4K, &busaddr);
if (table == NULL)
panic("AMDDEV","malloc failed", NO_NUM);
o= (unsigned)table & (PAGE_SIZE-1);
if (o)
table += PAGE_SIZE-o;
if (index == 0)
{
memset(table, 0, size);
@ -237,9 +233,6 @@ static void init_domain(int index)
memset(table, 0x00, size);
}
r= sys_umap(SELF, D, (vir_bytes)table, size, &busaddr);
if (r != OK)
panic("AMDDEV","sys_umap failed", r);
printf("init_domain: busaddr = %p\n", busaddr);
write_reg(DEVF_BASE_HI, index, 0);
@ -265,6 +258,7 @@ static void init_map(int index)
printf("after write: DEVF_MAP: 0x%x\n", read_reg(DEVF_MAP, index));
}
#if 0
static int do_add(message *m)
{
int r;
@ -282,19 +276,19 @@ static int do_add(message *m)
size, start, proc);
#endif
if (start % PAGE_SIZE)
if (start % I386_PAGE_SIZE)
{
printf("amddev`do_add: bad start 0x%x from proc %d\n",
start, proc);
return EINVAL;
}
if (size % PAGE_SIZE)
if (size % I386_PAGE_SIZE)
{
printf("amddev`do_add: bad size 0x%x from proc %d\n",
size, proc);
return EINVAL;
}
r= sys_umap(proc, D, (vir_bytes)start, size, &busaddr);
r= sys_umap(proc, VM_D, (vir_bytes)start, size, &busaddr);
if (r != OK)
{
printf("amddev`do_add: umap failed for 0x%x@0x%x, proc %d\n",
@ -304,6 +298,7 @@ static int do_add(message *m)
add_range(busaddr, size);
}
#endif
static int do_add_phys(message *m)
{
@ -319,12 +314,12 @@ static int do_add_phys(message *m)
size, start);
#endif
if (start % PAGE_SIZE)
if (start % I386_PAGE_SIZE)
{
printf("amddev`do_add_phys: bad start 0x%x\n", start);
return EINVAL;
}
if (size % PAGE_SIZE)
if (size % I386_PAGE_SIZE)
{
printf("amddev`do_add_phys: bad size 0x%x\n", size);
return EINVAL;
@ -355,12 +350,12 @@ static int do_del_phys(message *m)
size, start);
#endif
if (start % PAGE_SIZE)
if (start % I386_PAGE_SIZE)
{
printf("amddev`do_del_phys: bad start 0x%x\n", start);
return EINVAL;
}
if (size % PAGE_SIZE)
if (size % I386_PAGE_SIZE)
{
printf("amddev`do_del_phys: bad size 0x%x\n", size);
return EINVAL;
@ -391,13 +386,13 @@ static int do_add4pci(message *m)
"amddev`do_add4pci: got request for 0x%x@0x%x from %d for pci dev %u.%u.%u\n",
size, start, proc, pci_bus, pci_dev, pci_func);
if (start % PAGE_SIZE)
if (start % I386_PAGE_SIZE)
{
printf("amddev`do_add4pci: bad start 0x%x from proc %d\n",
start, proc);
return EINVAL;
}
if (size % PAGE_SIZE)
if (size % I386_PAGE_SIZE)
{
printf("amddev`do_add4pci: bad size 0x%x from proc %d\n",
size, proc);
@ -406,7 +401,7 @@ static int do_add4pci(message *m)
printf("amddev`do_add4pci: should check with PCI\n");
r= sys_umap(proc, D, (vir_bytes)start, size, &busaddr);
r= sys_umap(proc, VM_D, (vir_bytes)start, size, &busaddr);
if (r != OK)
{
printf(
@ -415,7 +410,7 @@ static int do_add4pci(message *m)
return r;
}
r= adddma(proc, busaddr, size);
r= adddma(proc, start, size);
if (r != 0)
{
r= -errno;
@ -439,9 +434,9 @@ static void add_range(u32_t busaddr, u32_t size)
printf("add_range: mapping 0x%x@0x%x\n", size, busaddr);
#endif
for (o= 0; o<size; o += PAGE_SIZE)
for (o= 0; o<size; o += I386_PAGE_SIZE)
{
bit= (busaddr+o)/PAGE_SIZE;
bit= (busaddr+o)/I386_PAGE_SIZE;
table[bit/8] &= ~(1 << (bit % 8));
}
}
@ -454,9 +449,9 @@ static void del_range(u32_t busaddr, u32_t size)
printf("del_range: mapping 0x%x@0x%x\n", size, busaddr);
#endif
for (o= 0; o<size; o += PAGE_SIZE)
for (o= 0; o<size; o += I386_PAGE_SIZE)
{
bit= (busaddr+o)/PAGE_SIZE;
bit= (busaddr+o)/I386_PAGE_SIZE;
table[bit/8] |= (1 << (bit % 8));
}
}

View file

@ -15,7 +15,7 @@ MAKE = exec make
CC = exec cc
CFLAGS = -I$i $(CPROFILE)
LDFLAGS = -i -L../libdriver
LIBS = -lsysutil -lsys -ltimers -ldriver
LIBS = -ldriver -lsys -ltimers
OBJ = at_wini.o

View file

@ -18,8 +18,10 @@
#include <minix/sysutil.h>
#include <minix/keymap.h>
#include <minix/type.h>
#include <sys/ioc_disk.h>
#include <ibm/pci.h>
#include <sys/mman.h>
#define ATAPI_DEBUG 0 /* To debug ATAPI code. */
@ -294,7 +296,6 @@ PRIVATE struct wini { /* main drive struct, one entry per drive */
PRIVATE int w_device = -1;
PRIVATE int w_controller = -1;
PRIVATE int w_major = -1;
PRIVATE char w_id_string[40];
PRIVATE int win_tasknr; /* my task number */
PRIVATE int w_command; /* current command in execution */
@ -309,7 +310,7 @@ PRIVATE struct device *w_dv; /* device's base and size */
#define ATA_DMA_SECTORS 64
#define ATA_DMA_BUF_SIZE (ATA_DMA_SECTORS*SECTOR_SIZE)
PRIVATE char dma_buf[ATA_DMA_BUF_SIZE];
PRIVATE char *dma_buf;
PRIVATE phys_bytes dma_buf_phys;
#define N_PRDTE 1024 /* Should be enough for large requests */
@ -320,7 +321,10 @@ PRIVATE struct prdte
u16_t prdte_count;
u8_t prdte_reserved;
u8_t prdte_flags;
} prdt[N_PRDTE];
};
#define PRDT_BYTES (sizeof(struct prdte) * N_PRDTE)
PRIVATE struct prdte *prdt;
PRIVATE phys_bytes prdt_phys;
#define PRDTE_FL_EOT 0x80 /* End of table */
@ -428,6 +432,8 @@ PUBLIC int main(int argc, char *argv[])
/* Install signal handlers. Ask PM to transform signal into message. */
struct sigaction sa;
init_buffer();
sa.sa_handler = SIG_MESS;
sigemptyset(&sa.sa_mask);
sa.sa_flags = 0;
@ -475,16 +481,34 @@ PRIVATE void init_params()
w_identify_wakeup_ticks = WAKEUP_TICKS;
}
if (disable_dma)
printf("DMA for ATA devices is disabled.\n");
if (disable_dma) {
printf("at_wini%d: DMA for ATA devices is disabled.\n", w_instance);
} else {
/* Ask for anonymous memory for DMA, that is physically contiguous. */
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);
if(dma_buf == MAP_FAILED || prdt == MAP_FAILED) {
disable_dma = 1;
printf("at_wini%d: no dma\n", w_instance);
} else {
s= sys_umap(SELF, VM_D, (vir_bytes)dma_buf,
ATA_DMA_BUF_SIZE, &dma_buf_phys);
if (s != 0)
panic("at_wini", "can't map dma buffer", s);
s= sys_umap(SELF, D, (vir_bytes)dma_buf, sizeof(dma_buf), &dma_buf_phys);
if (s != 0)
panic("at_wini", "can't map dma buffer", s);
s= sys_umap(SELF, D, (vir_bytes)prdt, sizeof(prdt), &prdt_phys);
if (s != 0)
panic("at_wini", "can't map prd table", s);
s= sys_umap(SELF, VM_D, (vir_bytes)prdt,
PRDT_BYTES, &prdt_phys);
if (s != 0)
panic("at_wini", "can't map prd table", s);
#if 0
printf("at_wini%d: physical dma_buf: 0x%lx, "
"prdt tab: 0x%lx\n",
w_instance, dma_buf_phys, prdt_phys);
#endif
}
}
if (w_instance == 0) {
/* Get the number of drives from the BIOS data area */
@ -524,7 +548,7 @@ PRIVATE void init_params()
0 /* no DMA */, NO_IRQ, 0, 0, drive);
w_next_drive++;
}
}
}
/* Look for controllers on the pci bus. Skip none the first instance,
* skip one and then 2 for every instance, for every next instance.
@ -779,15 +803,6 @@ message *m_ptr;
wn->state |= IGNORING;
return(ENXIO);
}
#if VERBOSE
printf("%s: AT driver detected ", w_name());
if (wn->state & (SMART|ATAPI)) {
printf("%.40s\n", w_id_string);
} else {
printf("%ux%ux%u\n", wn->pcylinders, wn->pheads, wn->psectors);
}
#endif
}
#if ENABLE_ATAPI
@ -898,9 +913,6 @@ PRIVATE int w_identify()
/* This is an ATA device. */
wn->state |= SMART;
/* Why are the strings byte swapped??? */
for (i = 0; i < 40; i++) w_id_string[i] = id_byte(27)[i^1];
/* Preferred CHS translation mode. */
wn->pcylinders = id_word(1);
wn->pheads = id_word(3);
@ -958,7 +970,8 @@ PRIVATE int w_identify()
else if (id_dma && dma_base)
{
w= id_word(ID_MULTIWORD_DMA);
if (w & (ID_MWDMA_2_SUP|ID_MWDMA_1_SUP|ID_MWDMA_0_SUP))
if (w_pci_debug &&
(w & (ID_MWDMA_2_SUP|ID_MWDMA_1_SUP|ID_MWDMA_0_SUP)))
{
printf(
"%s: multiword DMA modes supported:%s%s%s\n",
@ -967,7 +980,8 @@ PRIVATE int w_identify()
(w & ID_MWDMA_1_SUP) ? " 1" : "",
(w & ID_MWDMA_2_SUP) ? " 2" : "");
}
if (w & (ID_MWDMA_0_SEL|ID_MWDMA_1_SEL|ID_MWDMA_2_SEL))
if (w_pci_debug &&
(w & (ID_MWDMA_0_SEL|ID_MWDMA_1_SEL|ID_MWDMA_2_SEL)))
{
printf(
"%s: multiword DMA mode selected:%s%s%s\n",
@ -976,7 +990,7 @@ PRIVATE int w_identify()
(w & ID_MWDMA_1_SEL) ? " 1" : "",
(w & ID_MWDMA_2_SEL) ? " 2" : "");
}
if (ultra_dma)
if (w_pci_debug && ultra_dma)
{
w= id_word(ID_ULTRA_DMA);
if (w & (ID_UDMA_0_SUP|ID_UDMA_1_SUP|
@ -1048,9 +1062,6 @@ PRIVATE int w_identify()
if ((s=sys_insw(wn->base_cmd + REG_DATA, SELF, tmp_buf, 512)) != OK)
panic(w_name(),"Call to sys_insw() failed", s);
/* Why are the strings byte swapped??? */
for (i = 0; i < 40; i++) w_id_string[i] = id_byte(27)[i^1];
size = 0; /* Size set later. */
#endif
} else {
@ -1114,14 +1125,17 @@ PRIVATE int w_io_test(void)
int r, save_dev;
int save_timeout, save_errors, save_wakeup;
iovec_t iov;
static char *buf;
#ifdef CD_SECTOR_SIZE
static char buf[CD_SECTOR_SIZE];
#define BUFSIZE CD_SECTOR_SIZE
#else
static char buf[SECTOR_SIZE];
#define BUFSIZE SECTOR_SIZE
#endif
STATICINIT(buf, BUFSIZE);
iov.iov_addr = (vir_bytes) buf;
iov.iov_size = sizeof(buf);
iov.iov_size = BUFSIZE;
save_dev = w_device;
/* Reduce timeout values for this test transaction. */
@ -1321,8 +1335,8 @@ int safe; /* iov contains addresses (0) or grants? */
nbytes = diff64(dv_size, position);
block = div64u(add64(w_dv->dv_base, position), SECTOR_SIZE);
do_dma= wn->dma;
do_write= (opcode == DEV_SCATTER_S);
do_dma= wn->dma;
if (nbytes >= wn->max_count) {
/* The drive can't do more then max_count at once. */
@ -1475,14 +1489,17 @@ int safe; /* iov contains addresses (0) or grants? */
s=sys_safe_insw(wn->base_cmd + REG_DATA, proc_nr,
(void *) (iov->iov_addr), addr_offset,
SECTOR_SIZE);
if(s != OK) {
panic(w_name(),"Call to sys_safe_insw() failed", s);
}
} else {
s=sys_insw(wn->base_cmd + REG_DATA, proc_nr,
(void *) (iov->iov_addr + addr_offset),
SECTOR_SIZE);
}
if(s != OK) {
panic(w_name(),"Call to sys_insw() failed", s);
}
}
} else {
if(safe) {
s=sys_safe_outsw(wn->base_cmd + REG_DATA, proc_nr,
@ -1662,14 +1679,14 @@ int safe;
offset= 0; /* Offset in current iov */
#if 0
printf("setup_dma: proc_nr %d\n", proc_nr);
printf("at_wini: setup_dma: proc_nr %d\n", proc_nr);
#endif
while (size > 0)
{
#if 0
printf(
"setup_dma: iov[%d]: addr 0x%x, size %d offset %d, size %d\n",
"at_wini: setup_dma: iov[%d]: addr 0x%x, size %d offset %d, size %d\n",
i, iov[i].iov_addr, iov[i].iov_size, offset, size);
#endif
@ -1679,13 +1696,15 @@ int safe;
if (n == 0 || (n & 1))
panic("at_wini", "bad size in iov", iov[i].iov_size);
if(safe) {
r= sys_umap(proc_nr, GRANT_SEG, iov[i].iov_addr, n,&user_phys);
r= sys_umap(proc_nr, VM_GRANT, iov[i].iov_addr, n,&user_phys);
if (r != 0)
panic("at_wini", "can't map user buffer (VM_GRANT)", r);
user_phys += offset;
} else {
r= sys_umap(proc_nr, D, iov[i].iov_addr+offset, n, &user_phys);
}
r= sys_umap(proc_nr, VM_D, iov[i].iov_addr+offset, n, &user_phys);
if (r != 0)
panic("at_wini", "can't map user buffer", r);
panic("at_wini", "can't map user buffer (VM_D)", r);
}
if (user_phys & 1)
{
/* Buffer is not aligned */
@ -2709,7 +2728,7 @@ PRIVATE int at_in(int line, u32_t port, u32_t *value,
return OK;
printf("at_wini%d: line %d: %s failed: %d; port %x\n",
w_instance, line, typename, s, value, port);
panic(w_name(), "sys_out failed", NO_NUM);
panic(w_name(), "sys_in failed", NO_NUM);
}
#undef panic

View file

@ -12,7 +12,7 @@ gen_drv_dir = ../../gen_drivers/cyclic_dma
CC = exec cc
CFLAGS = -I$i
LDFLAGS = -i
LIBS = -lsys -lsysutil
LIBS = -lsys
# build local binary
all: es1370

View file

@ -11,7 +11,7 @@ b = $i/ibm
CC = exec cc
CFLAGS = -I$i
LDFLAGS = -i
LIBS = -lsys -lsysutil
LIBS = -lsys
PROGRAM_NAME = es1371
INSTALL_BIN = /usr/sbin/$(PROGRAM_NAME)

View file

@ -45,6 +45,7 @@
#include "audio_fw.h"
#include <sys/vm.h>
#include <minix/ds.h>
#include <sys/vm_i386.h>
FORWARD _PROTOTYPE( int msg_open, (int minor_dev_nr) );
@ -85,7 +86,6 @@ PUBLIC void main(void)
/* Here is the main loop of the dma driver. It waits for a message,
carries it out, and sends a reply. */
printf("%s up and running\n", drv.DriverName);
while(1) {
receive(ANY, &mess);
@ -886,19 +886,16 @@ PRIVATE int init_buffers(sub_dev_t *sub_dev_ptr)
size_t size, off;
unsigned left;
u32_t i;
phys_bytes ph;
/* allocate dma buffer space */
size= sub_dev_ptr->DmaSize + 64 * 1024;
base= malloc(size + PAGE_SIZE);
off = base= alloc_contig(size, AC_ALIGN4K, &ph);
if (!base) {
error("%s: failed to allocate dma buffer for channel %d\n",
drv.DriverName,i);
return EIO;
}
/* Align base */
off= ((size_t)base % PAGE_SIZE);
if (off)
base += PAGE_SIZE-off;
sub_dev_ptr->DmaBuf= base;
tell_dev((vir_bytes)base, size, 0, 0, 0);

View file

@ -12,7 +12,7 @@ d = ..
CC = exec cc
CFLAGS = -I$i
LDFLAGS = -i
LIBS = -lsys -lsysutil
LIBS = -lsys
# build local binary

View file

@ -14,7 +14,7 @@ MAKE = exec make
CC = exec cc
CFLAGS = -I$i $(CPROFILE)
LDFLAGS = -i -L../libdriver
LIBS = -lsysutil -lsys -ltimers -ldriver
LIBS = -ldriver -lsys -lsys -ltimers
OBJ = bios_wini.o

View file

@ -166,7 +166,7 @@ vir_bytes from_vir;
endpoint_t to_proc;
int to_seg;
vir_bytes to_vir;
vir_bytes grant_offset;
size_t grant_offset;
size_t size;
{
phys_bytes addr;

View file

@ -13,7 +13,7 @@ d = ..
CC = exec cc
CFLAGS = -I$i $(CPROFILE)
LDFLAGS = -i
LIBS = -lsysutil -lsys -ltimers
LIBS = -lsys -ltimers
OBJ = 3c503.o dp8390.o ne2000.o rtl8029.o wdeth.o

View file

@ -59,6 +59,7 @@
#include <net/hton.h>
#include <net/gen/ether.h>
#include <net/gen/eth_io.h>
#include <sys/vm_i386.h>
#include <sys/vm.h>
#include "assert.h"
@ -2540,18 +2541,22 @@ dpeth_t *dep;
return;
}
size = dep->de_ramsize + PAGE_SIZE; /* Add PAGE_SIZE for
size = dep->de_ramsize + I386_PAGE_SIZE; /* Add I386_PAGE_SIZE for
* alignment
*/
buf= malloc(size);
if (buf == NULL)
panic(__FILE__, "map_hw_buffer: cannot malloc size", size);
o= PAGE_SIZE - ((vir_bytes)buf % PAGE_SIZE);
o= I386_PAGE_SIZE - ((vir_bytes)buf % I386_PAGE_SIZE);
abuf= buf + o;
printf("buf at 0x%x, abuf at 0x%x\n", buf, abuf);
#if 0
r= sys_vm_map(SELF, 1 /* map */, (vir_bytes)abuf,
dep->de_ramsize, (phys_bytes)dep->de_linmem);
#else
r = ENOSYS;
#endif
if (r != OK)
panic(__FILE__, "map_hw_buffer: sys_vm_map failed", r);
dep->de_locmem = abuf;

View file

@ -15,7 +15,7 @@ LDFLAGS = -i -o $@
SRCS = 3c501.c 3c509.c 3c503.c ne.c wd.c 8390.c devio.c netbuff.c dp.c
OBJS = 3c501.o 3c509.o 3c503.o ne.o wd.o 8390.o devio.o netbuff.o dp.o
LIBS = -lsysutil -lsys # -ltimers
LIBS = -lsys
## Build rules
all build: $(DRIVER)

View file

@ -14,7 +14,7 @@ MAKE = exec make
CC = exec cc
CFLAGS = -I$i $(CPROFILE)
LDFLAGS = -i -L../libdriver
LIBS = -lsysutil -ldriver -lsys -ltimers
LIBS = -ldriver -lsys -ltimers
OBJ = floppy.o

View file

@ -294,6 +294,8 @@ PUBLIC void main()
struct floppy *fp;
int s;
init_buffer();
f_next_timeout = TMR_NEVER;
tmr_inittimer(&f_tmr_timeout);

View file

@ -13,7 +13,7 @@ d = ..
CC = exec cc
CFLAGS = -I$i $(CPROFILE)
LDFLAGS = -i
LIBS = -lsysutil -lsys -ltimers
LIBS = -lsys -ltimers
OBJ = fxp.o mii.o
@ -21,7 +21,7 @@ OBJ = fxp.o mii.o
all build: $(DRIVER)
$(DRIVER): $(OBJ)
$(CC) -o $@ $(LDFLAGS) $(OBJ) $(LIBS)
install -S 96k $(DRIVER)
install -S 128k $(DRIVER)
# install with other drivers
install: /usr/sbin/$(DRIVER)

View file

@ -211,7 +211,8 @@ fxp_t;
#define FT_82558A 0x2
#define FT_82559 0x4
static fxp_t fxp_table[FXP_PORT_NR];
static fxp_t *fxp_table;
phys_bytes fxp_table_phys;
static u16_t eth_ign_proto;
static tmra_ut fxp_watchdog;
@ -281,6 +282,7 @@ int main(int argc, char *argv[])
u32_t tasknr;
fxp_t *fp;
long v;
vir_bytes ft = sizeof(*fxp_table)*FXP_PORT_NR;
if (argc < 1)
panic("FXP", "A head which at this time has no name", NO_NUM);
@ -292,6 +294,11 @@ int main(int argc, char *argv[])
#endif
eth_ign_proto= htons((u16_t) v);
if(!(fxp_table = alloc_contig(ft, 0, &fxp_table_phys)))
panic("FXP","couldn't allocate table", r);
memset(fxp_table, 0, ft);
if((r=micro_delay_calibrate()) != OK)
panic("FXP","rmicro_delay_calibrate failed", r);
@ -795,7 +802,7 @@ fxp_t *fp;
fxp_do_conf(fp);
/* Set pointer to statistical counters */
r= sys_umap(SELF, D, (vir_bytes)&fp->fxp_stat, sizeof(fp->fxp_stat),
r= sys_umap(SELF, VM_D, (vir_bytes)&fp->fxp_stat, sizeof(fp->fxp_stat),
&bus_addr);
if (r != OK)
panic("FXP","sys_umap failed", r);
@ -835,6 +842,7 @@ fxp_t *fp;
int i, r;
struct rfd *rfdp;
struct tx *txp;
phys_bytes ph;
fp->fxp_rx_nbuf= N_RX_BUF;
rx_totbufsize= fp->fxp_rx_nbuf * sizeof(struct rfd);
@ -844,33 +852,33 @@ fxp_t *fp;
tx_totbufsize= fp->fxp_tx_nbuf * sizeof(struct tx);
fp->fxp_tx_bufsize= tx_totbufsize;
#define BUFALIGN 4096
tot_bufsize= sizeof(*tmpbufp) + tx_totbufsize + rx_totbufsize;
if (tot_bufsize % 4096)
tot_bufsize += 4096 - (tot_bufsize % 4096);
alloc_bufsize= tot_bufsize+BUFALIGN;
alloc_buf= malloc(alloc_bufsize);
alloc_bufsize= tot_bufsize;
alloc_buf= alloc_contig(alloc_bufsize, AC_ALIGN4K, &ph);
if (alloc_buf == NULL)
{
panic(__FILE__, "fxp_init_buf: unable to malloc size",
panic(__FILE__, "fxp_init_buf: unable to alloc_contig size",
alloc_bufsize);
}
buf= (phys_bytes)alloc_buf;
buf += BUFALIGN - (buf % BUFALIGN);
tell_dev((vir_bytes)buf, tot_bufsize, 0, 0, 0);
tmpbufp= (union tmpbuf *)buf;
fp->fxp_rx_buf= (struct rfd *)&tmpbufp[1];
r= sys_umap(SELF, D, (vir_bytes)fp->fxp_rx_buf, rx_totbufsize,
r= sys_umap(SELF, VM_D, (vir_bytes)fp->fxp_rx_buf, rx_totbufsize,
&fp->fxp_rx_busaddr);
if (r != OK)
panic("FXP","sys_umap failed", r);
#if 0
printf("fxp_init_buf: got phys 0x%x for vir 0x%x\n",
fp->fxp_rx_busaddr, fp->fxp_rx_buf);
#endif
for (i= 0, rfdp= fp->fxp_rx_buf; i<fp->fxp_rx_nbuf; i++, rfdp++)
{
@ -878,7 +886,7 @@ fxp_t *fp;
rfdp->rfd_command= 0;
if (i != fp->fxp_rx_nbuf-1)
{
r= sys_umap(SELF, D, (vir_bytes)&rfdp[1],
r= sys_umap(SELF, VM_D, (vir_bytes)&rfdp[1],
sizeof(rfdp[1]), &rfdp->rfd_linkaddr);
if (r != OK)
panic("FXP","sys_umap failed", r);
@ -896,7 +904,7 @@ fxp_t *fp;
fp->fxp_rx_head= 0;
fp->fxp_tx_buf= (struct tx *)((char *)fp->fxp_rx_buf+rx_totbufsize);
r= sys_umap(SELF, D, (vir_bytes)fp->fxp_tx_buf,
r= sys_umap(SELF, VM_D, (vir_bytes)fp->fxp_tx_buf,
(phys_bytes)tx_totbufsize, &fp->fxp_tx_busaddr);
if (r != OK)
panic("FXP","sys_umap failed", r);
@ -907,7 +915,7 @@ fxp_t *fp;
txp->tx_command= TXC_EL | CBL_NOP; /* Just in case */
if (i != fp->fxp_tx_nbuf-1)
{
r= sys_umap(SELF, D, (vir_bytes)&txp[1],
r= sys_umap(SELF, VM_D, (vir_bytes)&txp[1],
(phys_bytes)sizeof(txp[1]),
&txp->tx_linkaddr);
if (r != OK)
@ -938,7 +946,7 @@ fxp_t *fp;
/* Reset device */
fxp_outl(port, CSR_PORT, CP_CMD_SOFT_RESET);
tickdelay(MICROS_TO_TICKS(CSR_PORT_RESET_DELAY));
tickdelay(micros_to_ticks(CSR_PORT_RESET_DELAY));
/* Disable interrupts */
fxp_outb(port, SCB_INT_MASK, SIM_M);
@ -995,7 +1003,7 @@ fxp_t *fp;
tmpbufp->ias.ias_linkaddr= 0;
memcpy(tmpbufp->ias.ias_ethaddr, fp->fxp_address.ea_addr,
sizeof(tmpbufp->ias.ias_ethaddr));
r= sys_umap(SELF, D, (vir_bytes)&tmpbufp->ias,
r= sys_umap(SELF, VM_D, (vir_bytes)&tmpbufp->ias,
(phys_bytes)sizeof(tmpbufp->ias), &bus_addr);
if (r != OK)
panic("FXP","sys_umap failed", r);
@ -1007,7 +1015,7 @@ fxp_t *fp;
/* Wait for CU command to complete */
if (tmpbufp->ias.ias_status & CBL_F_C)
break;
} while (getuptime(&t1)==OK && (t1-t0) < MICROS_TO_TICKS(1000));
} while (getuptime(&t1)==OK && (t1-t0) < micros_to_ticks(1000));
if (!(tmpbufp->ias.ias_status & CBL_F_C))
panic("FXP","fxp_confaddr: CU command failed to complete", NO_NUM);
@ -1731,7 +1739,7 @@ fxp_t *fp;
memcpy(tmpbufp->cc.cc_bytes, fp->fxp_conf_bytes,
sizeof(tmpbufp->cc.cc_bytes));
r= sys_umap(SELF, D, (vir_bytes)&tmpbufp->cc,
r= sys_umap(SELF, VM_D, (vir_bytes)&tmpbufp->cc,
(phys_bytes)sizeof(tmpbufp->cc), &bus_addr);
if (r != OK)
panic("FXP","sys_umap failed", r);
@ -1743,7 +1751,7 @@ fxp_t *fp;
/* Wait for CU command to complete */
if (tmpbufp->cc.cc_status & CBL_F_C)
break;
} while (getuptime(&t1)==OK && (t1-t0) < MICROS_TO_TICKS(100000));
} while (getuptime(&t1)==OK && (t1-t0) < micros_to_ticks(100000));
if (!(tmpbufp->cc.cc_status & CBL_F_C))
panic("FXP","fxp_do_conf: CU command failed to complete", NO_NUM);
@ -1786,7 +1794,7 @@ int check_idle;
scb_cmd= fxp_inb(port, SCB_CMD);
if ((scb_cmd & SC_CUC_MASK) == SC_CU_NOP)
break;
} while (getuptime(&t1)==OK && (t1-t0) < MICROS_TO_TICKS(100000));
} while (getuptime(&t1)==OK && (t1-t0) < micros_to_ticks(100000));
if ((scb_cmd & SC_CUC_MASK) != SC_CU_NOP)
panic("FXP","fxp_cu_ptr_cmd: CU does not accept command", NO_NUM);
@ -1823,7 +1831,7 @@ int check_idle;
scb_cmd= fxp_inb(port, SCB_CMD);
if ((scb_cmd & SC_RUC_MASK) == SC_RU_NOP)
break;
} while (getuptime(&t1)==OK && (t1-t0) < MICROS_TO_TICKS(1000));
} while (getuptime(&t1)==OK && (t1-t0) < micros_to_ticks(1000));
if ((scb_cmd & SC_RUC_MASK) != SC_RU_NOP)
panic("FXP","fxp_ru_ptr_cmd: RU does not accept command", NO_NUM);
@ -1899,7 +1907,7 @@ message *mp;
/* Wait for CU command to complete */
if (*p != 0)
break;
} while (getuptime(&t1)==OK && (t1-t0) < MICROS_TO_TICKS(1000));
} while (getuptime(&t1)==OK && (t1-t0) < micros_to_ticks(1000));
if (*p == 0)
panic("FXP","fxp_getstat: CU command failed to complete", NO_NUM);
@ -1983,7 +1991,7 @@ message *mp;
/* Wait for CU command to complete */
if (*p != 0)
break;
} while (getuptime(&t1)==OK && (t1-t0) < MICROS_TO_TICKS(1000));
} while (getuptime(&t1)==OK && (t1-t0) < micros_to_ticks(1000));
if (*p == 0)
panic("FXP","fxp_getstat: CU command failed to complete", NO_NUM);
@ -2798,7 +2806,7 @@ int reg;
v= fxp_inl(port, CSR_MDI_CTL);
if (v & CM_READY)
break;
} while (getuptime(&t1)==OK && (t1-t0) < MICROS_TO_TICKS(100000));
} while (getuptime(&t1)==OK && (t1-t0) < micros_to_ticks(100000));
if (!(v & CM_READY))
panic("FXP","mii_read: MDI not ready after command", NO_NUM);
@ -2932,9 +2940,11 @@ int pci_func;
r= ds_retrieve_u32("amddev", &u32);
if (r != OK)
{
#if 0
printf(
"fxp`tell_dev: ds_retrieve_u32 failed for 'amddev': %d\n",
r);
#endif
return;
}

View file

@ -13,7 +13,7 @@ d = ..
CC = exec cc
CFLAGS = -I$i $(CPROFILE)
LDFLAGS = -i
LIBS = -lsysutil -lsys
LIBS = -lsys
#-lutils -ltimers
OBJ = lance.o
@ -22,7 +22,7 @@ OBJ = lance.o
all build: $(DRIVER)
$(DRIVER): $(OBJ)
$(CC) -o $@ $(LDFLAGS) $(OBJ) $(LIBS)
install -S 16k $(DRIVER)
install -S 128k $(DRIVER)
# install with other drivers
install: /usr/sbin/$(DRIVER)

View file

@ -193,7 +193,7 @@ unsigned long vir2phys( unsigned long x )
int r;
unsigned long value;
if ( (r=sys_umap( SELF, D, x, 4, &value )) != OK )
if ( (r=sys_umap( SELF, VM_D, x, 4, &value )) != OK )
panic( "lance", "sys_umap failed", r );
return value;
@ -202,7 +202,7 @@ unsigned long vir2phys( unsigned long x )
/* DMA limitations */
#define DMA_ADDR_MASK 0xFFFFFF /* mask to verify DMA address is 24-bit */
#define CORRECT_DMA_MEM() ( (virt_to_bus(lance + sizeof(lance)) & ~DMA_ADDR_MASK) == 0 )
#define CORRECT_DMA_MEM() ( (virt_to_bus(lance_buf + sizeof(struct lance_interface)) & ~DMA_ADDR_MASK) == 0 )
#define ETH_FRAME_LEN 1518
@ -297,7 +297,8 @@ struct lance_interface
/* =============== global variables =============== */
static struct lance_interface *lp;
static char lance[sizeof(struct lance_interface)+8];
#define LANCE_BUF_SIZE (sizeof(struct lance_interface))
static char *lance_buf = NULL;
static int rx_slot_nr = 0; /* Rx-slot number */
static int tx_slot_nr = 0; /* Tx-slot number */
static int cur_tx_slot_nr = 0; /* Tx-slot number */
@ -1682,8 +1683,11 @@ ether_card_t *ec;
unsigned short ioaddr = ec->ec_port;
/* ============= setup init_block(cf. lance_probe1) ================ */
/* make sure data structure is 8-byte aligned */
l = ((Address)lance + 7) & ~7;
/* make sure data structure is 8-byte aligned and below 16MB (for DMA) */
assert(!lance_buf);
if(!(lance_buf = alloc_contig(LANCE_BUF_SIZE, AC_ALIGN4K|AC_LOWER16M, &l))) {
panic( "lance", "alloc_contig failed", LANCE_BUF_SIZE);
}
lp = (struct lance_interface *)l;
lp->init_block.mode = 0x3; /* disable Rx and Tx */
lp->init_block.filter[0] = lp->init_block.filter[1] = 0x0;

View file

@ -11,7 +11,7 @@ m = $i/minix
CC = exec cc
CFLAGS = -I$i $(CPROFILE)
LDFLAGS = -i
LIBS = -lsysutil -lsys
LIBS = -lsys
LIB = libdriver.a
OBJECTS = driver.o drvlib.o mq.o

View file

@ -43,29 +43,13 @@
#include <minix/mq.h>
#include "driver.h"
#if (CHIP == INTEL)
#if USE_EXTRA_DMA_BUF && DMA_BUF_SIZE < 2048
/* A bit extra scratch for the Adaptec driver. */
#define BUF_EXTRA (2048 - DMA_BUF_SIZE)
#else
#define BUF_EXTRA 0
#endif
/* Claim space for variables. */
PRIVATE u8_t buffer[(unsigned) 2 * DMA_BUF_SIZE + BUF_EXTRA];
#if 0
PRIVATE u8_t buffer[(unsigned) 2 * DMA_BUF_SIZE];
#endif
u8_t *tmp_buf; /* the DMA buffer eventually */
phys_bytes tmp_phys; /* phys address of DMA buffer */
#else /* CHIP != INTEL */
/* Claim space for variables. */
u8_t tmp_buf[DMA_BUF_SIZE]; /* the DMA buffer */
phys_bytes tmp_phys; /* phys address of DMA buffer */
#endif /* CHIP != INTEL */
FORWARD _PROTOTYPE( void init_buffer, (void) );
FORWARD _PROTOTYPE( int do_rdwt, (struct driver *dr, message *mp, int safe) );
FORWARD _PROTOTYPE( int do_vrdwt, (struct driver *dr, message *mp, int safe) );
@ -86,9 +70,6 @@ struct driver *dp; /* Device dependent entry points. */
/* Init MQ library. */
mq_init();
/* Get a DMA buffer. */
init_buffer();
/* Here is the main loop of the disk task. It waits for a message, carries
* it out, and sends a reply.
*/
@ -176,25 +157,17 @@ struct driver *dp; /* Device dependent entry points. */
/*===========================================================================*
* init_buffer *
*===========================================================================*/
PRIVATE void init_buffer()
PUBLIC void init_buffer(void)
{
/* Select a buffer that can safely be used for DMA transfers. It may also
* be used to read partition tables and such. Its absolute address is
* 'tmp_phys', the normal address is 'tmp_buf'.
*/
#if (CHIP == INTEL)
unsigned left;
tmp_buf = buffer;
sys_umap(SELF, D, (vir_bytes)buffer, (phys_bytes)sizeof(buffer), &tmp_phys);
if ((left = dma_bytes_left(tmp_phys)) < DMA_BUF_SIZE) {
/* First half of buffer crosses a 64K boundary, can't DMA into that */
tmp_buf += left;
tmp_phys += left;
}
#endif /* CHIP == INTEL */
if(!(tmp_buf = alloc_contig(2*DMA_BUF_SIZE, AC_ALIGN4K, &tmp_phys)))
panic(__FILE__, "can't allocate tmp_buf", DMA_BUF_SIZE);
}
/*===========================================================================*
@ -216,8 +189,8 @@ int safe; /* use safecopies? */
/* Check the user buffer (not relevant for safe copies). */
if(!safe) {
sys_umap(mp->IO_ENDPT, D, (vir_bytes) mp->ADDRESS, mp->COUNT, &phys_addr);
if (phys_addr == 0) return(EFAULT);
printf("libdriver_asyn: do_rdwt: no support for non-safe command.\n");
return EINVAL;
}
/* Prepare for I/O. */

View file

@ -45,14 +45,6 @@ struct driver {
_PROTOTYPE( int (*dr_hw_int), (struct driver *dp, message *m_ptr) );
};
#if (CHIP == INTEL)
/* Number of bytes you can DMA before hitting a 64K boundary: */
#define dma_bytes_left(phys) \
((unsigned) (sizeof(int) == 2 ? 0 : 0x10000) - (unsigned) ((phys) & 0xFFFF))
#endif /* CHIP == INTEL */
/* Base and size of a partition in bytes. */
struct device {
u64_t dv_base;
@ -75,6 +67,7 @@ _PROTOTYPE( int nop_select, (struct driver *dp, message *m_ptr) );
_PROTOTYPE( int do_diocntl, (struct driver *dp, message *m_ptr, int safe) );
_PROTOTYPE( int nop_ioctl, (struct driver *dp, message *m_ptr, int safe) );
_PROTOTYPE( int mq_queue, (message *m_ptr) );
_PROTOTYPE( void init_buffer, (void) );
/* Parameters for the disk drive. */
#define SECTOR_SIZE 512 /* physical sector size in bytes */

View file

@ -11,7 +11,7 @@ m = $i/minix
CC = exec cc
CFLAGS = -I$i $(CPROFILE)
LDFLAGS = -i
LIBS = -lsysutil -lsys
LIBS = -lsys
LIB = libdriver.a
OBJECTS = driver.o drvlib.o mq.o

View file

@ -43,28 +43,10 @@
#include <minix/mq.h>
#include "driver.h"
#if (CHIP == INTEL)
#if USE_EXTRA_DMA_BUF && DMA_BUF_SIZE < 2048
/* A bit extra scratch for the Adaptec driver. */
#define BUF_EXTRA (2048 - DMA_BUF_SIZE)
#else
#define BUF_EXTRA 0
#endif
/* Claim space for variables. */
PRIVATE u8_t buffer[(unsigned) 2 * DMA_BUF_SIZE + BUF_EXTRA];
u8_t *tmp_buf; /* the DMA buffer eventually */
u8_t *tmp_buf = NULL; /* the DMA buffer eventually */
phys_bytes tmp_phys; /* phys address of DMA buffer */
#else /* CHIP != INTEL */
/* Claim space for variables. */
u8_t tmp_buf[DMA_BUF_SIZE]; /* the DMA buffer */
phys_bytes tmp_phys; /* phys address of DMA buffer */
#endif /* CHIP != INTEL */
FORWARD _PROTOTYPE( void init_buffer, (void) );
FORWARD _PROTOTYPE( int do_rdwt, (struct driver *dr, message *mp, int safe) );
FORWARD _PROTOTYPE( int do_vrdwt, (struct driver *dr, message *mp, int safe) );
@ -88,9 +70,6 @@ struct driver *dp; /* Device dependent entry points. */
/* Init MQ library. */
mq_init();
/* Get a DMA buffer. */
init_buffer();
/* Here is the main loop of the disk task. It waits for a message, carries
* it out, and sends a reply.
*/
@ -112,6 +91,7 @@ struct driver *dp; /* Device dependent entry points. */
device_caller = mess.m_source;
proc_nr = mess.IO_ENDPT;
#if 0
if (mess.m_type != SYN_ALARM && mess.m_type != DEV_PING &&
mess.m_type != 4105 /* notify from TTY */ &&
mess.m_type != DEV_SELECT &&
@ -119,9 +99,10 @@ struct driver *dp; /* Device dependent entry points. */
mess.m_type != DIAGNOSTICS_S &&
mess.m_type != CANCEL)
{
printf("libdriver_asyn`driver_task: message %d\n",
mess.m_type);
printf("libdriver_asyn`driver_task: msg %d / 0x%x from %d\n",
mess.m_type, mess.m_type, mess.m_source);
}
#endif
if (mess.m_type == DEV_SELECT)
{
@ -129,9 +110,11 @@ struct driver *dp; /* Device dependent entry points. */
if (first)
{
first= 0;
#if 0
printf(
"libdriver_asyn`driver_task: first DEV_SELECT: minor 0x%x, ops 0x%x\n",
mess.DEVICE, mess.IO_ENDPT);
#endif
}
}
@ -223,15 +206,19 @@ struct driver *dp; /* Device dependent entry points. */
}
else if (mess.m_type == DIAGNOSTICS_S)
{
#if 0
if (device_caller == FS_PROC_NR)
printf("driver_task: sending DIAG_REPL to FS\n");
#endif
reply_mess.m_type = DIAG_REPL;
reply_mess.REP_STATUS = r;
}
else
{
#if 0
printf("driver_task: TASK_REPLY to req %d\n",
mess.m_type);
#endif
reply_mess.m_type = TASK_REPLY;
reply_mess.REP_ENDPT = proc_nr;
/* Status is # of bytes transferred or error code. */
@ -258,18 +245,11 @@ PRIVATE void init_buffer()
* 'tmp_phys', the normal address is 'tmp_buf'.
*/
#if (CHIP == INTEL)
unsigned left;
tmp_buf = buffer;
sys_umap(SELF, D, (vir_bytes)buffer, (phys_bytes)sizeof(buffer), &tmp_phys);
if ((left = dma_bytes_left(tmp_phys)) < DMA_BUF_SIZE) {
/* First half of buffer crosses a 64K boundary, can't DMA into that */
tmp_buf += left;
tmp_phys += left;
if(!(tmp_buf = alloc_contig(2*DMA_BUF_SIZE, 0, &tmp_phys))) {
panic(__FILE__, "can't allocate tmp_buf", NO_NUM);
}
#endif /* CHIP == INTEL */
}
/*===========================================================================*
@ -557,6 +537,8 @@ PUBLIC int mq_queue(message *m)
return OK;
}
#if 0
#define ASYN_NR 100
PRIVATE asynmsg_t msgtable[ASYN_NR];
PRIVATE int first_slot= 0, next_slot= 0;
@ -644,3 +626,4 @@ message *mp;
return senda(msgtable+first_slot, next_slot-first_slot);
}
#endif

View file

@ -45,14 +45,6 @@ struct driver {
_PROTOTYPE( int (*dr_hw_int), (struct driver *dp, message *m_ptr) );
};
#if (CHIP == INTEL)
/* Number of bytes you can DMA before hitting a 64K boundary: */
#define dma_bytes_left(phys) \
((unsigned) (sizeof(int) == 2 ? 0 : 0x10000) - (unsigned) ((phys) & 0xFFFF))
#endif /* CHIP == INTEL */
/* Base and size of a partition in bytes. */
struct device {
u64_t dv_base;

View file

@ -13,7 +13,7 @@ MAKE = exec make
CC = exec cc
CFLAGS = -I$i $(CPROFILE)
LDFLAGS = -i -L../libdriver_asyn
LIBS = -lsysutil -ldriver -lsys
LIBS = -ldriver -lsys
LIB_DEP = ../libdriver_asyn/libdriver.a
OBJ = log.o diag.o kputc.o
@ -22,11 +22,11 @@ OBJ = log.o diag.o kputc.o
all build: $(DRIVER)
$(DRIVER): $(OBJ) $(LIB_DEP)
$(CC) -o $@ $(LDFLAGS) $(OBJ) $(LIBS)
install -S 16kb $(DRIVER)
install -S 32kb $(DRIVER)
# install with other drivers
install: $(DRIVER)
install -o root -cs $? /sbin/$(DRIVER)
install -o root -cs $< /sbin/$(DRIVER)
# clean up local files
clean:

View file

@ -11,11 +11,9 @@
#include <fcntl.h>
#include <minix/type.h>
#include <minix/safecopies.h>
#include <minix/sys_config.h>
#include "log.h"
#include "../../kernel/const.h"
#include "../../kernel/config.h"
#include "../../kernel/type.h"
/*==========================================================================*
* do_new_kmess *
@ -24,8 +22,8 @@ PUBLIC int do_new_kmess(m)
message *m; /* notification message */
{
/* Notification for a new kernel message. */
struct kmessages kmess; /* entire kmess structure */
char print_buf[KMESS_BUF_SIZE]; /* copy new message here */
static struct kmessages kmess; /* entire kmess structure */
static char print_buf[_KMESS_BUF_SIZE]; /* copy new message here */
int bytes;
int i, r;
int *prev_nextp;
@ -79,12 +77,12 @@ message *m; /* notification message */
* Check for size being positive, the buffer might as well be emptied!
*/
if (kmess.km_size > 0) {
bytes = ((kmess.km_next + KMESS_BUF_SIZE) - (*prev_nextp)) %
KMESS_BUF_SIZE;
bytes = ((kmess.km_next + _KMESS_BUF_SIZE) - (*prev_nextp)) %
_KMESS_BUF_SIZE;
r= *prev_nextp; /* start at previous old */
i=0;
while (bytes > 0) {
print_buf[i] = kmess.km_buf[(r%KMESS_BUF_SIZE)];
print_buf[i] = kmess.km_buf[(r%_KMESS_BUF_SIZE)];
bytes --;
r ++;
i ++;
@ -136,5 +134,7 @@ PUBLIC int do_diagnostics(message *m, int safe)
}
log_append(diagbuf, i);
if(m->m_type == ASYN_DIAGNOSTICS) return EDONTREPLY;
return OK;
}

View file

@ -9,8 +9,6 @@
#include "log.h"
#include <sys/time.h>
#include <sys/select.h>
#include "../../kernel/const.h"
#include "../../kernel/type.h"
#define LOG_DEBUG 0 /* enable/ disable debugging */
@ -403,10 +401,10 @@ int safe;
r = do_diagnostics(m_ptr, 0);
break;
}
case DIAGNOSTICS_S: {
case ASYN_DIAGNOSTICS:
case DIAGNOSTICS_S:
r = do_diagnostics(m_ptr, 1);
break;
}
case DEV_STATUS: {
printf("log_other: unexpected DEV_STATUS request\n");
r = EDONTREPLY;

View file

@ -14,7 +14,7 @@ MAKE = exec make
CC = exec cc
CFLAGS = -I$i
LDFLAGS = -i -L../libdriver
LIBS = -lsysutil -ldriver -lsys
LIBS = -ldriver -lsys
# imgrd_s.s is the ACK assembler version of the ramdisk. For more portability,
# use the C version imgrd.c. However, the C compiler takes too much memory

View file

@ -27,6 +27,7 @@
#define MY_DS_NAME_SIZE "dev:memory:ramdisk_size"
#include <sys/vm.h>
#include <sys/vm_i386.h>
#include "assert.h"
@ -71,7 +72,7 @@ PRIVATE struct driver m_dtab = {
/* One page of temporary mapping area - enough to be able to page-align
* one page.
*/
static char pagedata_buf[2*PAGE_SIZE];
static char pagedata_buf[2*I386_PAGE_SIZE];
vir_bytes pagedata_aligned;
/* Buffer for the /dev/zero null byte feed. */
@ -171,8 +172,10 @@ int safe; /* safe copies */
break;
/* Virtual copying. For RAM disk, kernel memory and boot device. */
case RAM_DEV:
case KMEM_DEV:
return EIO;
break;
case RAM_DEV:
case BOOT_DEV:
if (position >= dv_size) return(OK); /* check for EOF */
if (position + count > dv_size) count = dv_size - position;
@ -207,15 +210,19 @@ int safe; /* safe copies */
count = dv_size - position;
mem_phys = cv64ul(dv->dv_base) + position;
page_off = mem_phys % PAGE_SIZE;
page_off = mem_phys % I386_PAGE_SIZE;
pagestart = mem_phys - page_off;
/* All memory to the map call has to be page-aligned.
* Don't have to map same page over and over.
*/
if(!any_mapped || pagestart_mapped != pagestart) {
#if 0
if((r=sys_vm_map(SELF, 1, pagedata_aligned,
PAGE_SIZE, pagestart)) != OK) {
I386_PAGE_SIZE, pagestart)) != OK) {
#else
if(1) {
#endif
printf("memory: sys_vm_map failed: %d\n", r);
return r;
}
@ -224,7 +231,7 @@ int safe; /* safe copies */
}
/* how much to be done within this page. */
subcount = PAGE_SIZE-page_off;
subcount = I386_PAGE_SIZE-page_off;
if(subcount > count)
subcount = count;
@ -324,12 +331,14 @@ PRIVATE void m_init()
}
/* Install remote segment for /dev/kmem memory. */
#if 0
m_geom[KMEM_DEV].dv_base = cvul64(kinfo.kmem_base);
m_geom[KMEM_DEV].dv_size = cvul64(kinfo.kmem_size);
if (OK != (s=sys_segctl(&m_seg[KMEM_DEV], (u16_t *) &s, (vir_bytes *) &s,
kinfo.kmem_base, kinfo.kmem_size))) {
panic("MEM","Couldn't install remote segment.",s);
}
#endif
/* Install remote segment for /dev/boot memory, if enabled. */
m_geom[BOOT_DEV].dv_base = cvul64(kinfo.bootdev_base);
@ -365,8 +374,8 @@ PRIVATE void m_init()
}
/* Page-align page pointer. */
pagedata_aligned = (u32_t) pagedata_buf + PAGE_SIZE;
pagedata_aligned -= pagedata_aligned % PAGE_SIZE;
pagedata_aligned = (u32_t) pagedata_buf + I386_PAGE_SIZE;
pagedata_aligned -= pagedata_aligned % I386_PAGE_SIZE;
/* Set up memory range for /dev/mem. */
m_geom[MEM_DEV].dv_size = cvul64(0xffffffff);
@ -404,15 +413,11 @@ int safe;
if (m_ptr->DEVICE != RAM_DEV) return(EINVAL);
if ((dv = m_prepare(m_ptr->DEVICE)) == NIL_DEV) return(ENXIO);
#if 0
ramdev_size= m_ptr->POSITION;
#else
/* Get request structure */
s= sys_safecopyfrom(m_ptr->IO_ENDPT, (vir_bytes)m_ptr->IO_GRANT,
0, (vir_bytes)&ramdev_size, sizeof(ramdev_size), D);
if (s != OK)
return s;
#endif
#if DEBUG
printf("allocating ramdisk of size 0x%x\n", ramdev_size);
@ -447,27 +452,6 @@ int safe;
first_time= 0;
break;
}
case MIOCMAP:
case MIOCUNMAP: {
int r, do_map;
struct mapreq mapreq;
if ((*dp->dr_prepare)(m_ptr->DEVICE) == NIL_DEV) return(ENXIO);
if (m_device != MEM_DEV)
return ENOTTY;
do_map= (m_ptr->REQUEST == MIOCMAP); /* else unmap */
/* Get request structure */
r= sys_safecopyfrom(m_ptr->IO_ENDPT, (vir_bytes)m_ptr->IO_GRANT,
0, (vir_bytes)&mapreq, sizeof(mapreq), D);
if (r != OK)
return r;
r= sys_vm_map(m_ptr->IO_ENDPT, do_map,
(phys_bytes)mapreq.base, mapreq.size, mapreq.offset);
return r;
}
default:
return(do_diocntl(&m_dtab, m_ptr, safe));

View file

@ -9,7 +9,6 @@ then
else
/bin/service -c up /bin/at_wini -dev /dev/c0d0 -config /etc/drivers.conf -label at_wini_0
/bin/service -c up /bin/at_wini -dev /dev/c1d0 -config /etc/drivers.conf -label at_wini_1 -args ata_instance=1
#/bin/service -c up /bin/at_wini -dev /dev/c0d0 -script /etc/rs.single -config /etc/drivers.conf
fi
rootdev=`sysenv rootdev` || echo 'No rootdev?'

View file

@ -13,7 +13,7 @@ d = ..
CC = exec cc
CFLAGS = -I$i $(CPROFILE)
LDFLAGS = -i
LIBS = -lsysutil -lsys -ltimers
LIBS = -lsys -ltimers
OBJ = orinoco.o hermes.o

View file

@ -44,8 +44,6 @@
#include "string.h"
int this_proc;
#define MICROS_TO_TICKS(m) (((m)*HZ/1000000)+1)
/*****************************************************************************
* milli_delay *
* *

View file

@ -93,7 +93,7 @@ static tmra_ut or_watchdog;
#include <net/hton.h>
#include <net/gen/ether.h>
#include <net/gen/eth_io.h>
#include <sys/vm.h>
#include <sys/vm_i386.h>
#include <sys/types.h>
#include <fcntl.h>
#include <unistd.h>
@ -738,24 +738,29 @@ static void map_hw_buffer(t_or *orp) {
char *buf, *abuf;
hermes_t *hw = &(orp->hw);
/* This way, the buffer will be at least PAGE_SIZE big: see
/* This way, the buffer will be at least I386_PAGE_SIZE big: see
* calculation with the offset */
size = 2 * PAGE_SIZE;
size = 2 * I386_PAGE_SIZE;
buf = (char *)malloc(size);
if(buf == NULL)
panic(__FILE__, "map_hw_buffer: cannot malloc size:", size);
/* Let the mapped memory by PAGE_SIZE aligned */
o = PAGE_SIZE - ((vir_bytes)buf % PAGE_SIZE);
/* Let the mapped memory by I386_PAGE_SIZE aligned */
o = I386_PAGE_SIZE - ((vir_bytes)buf % I386_PAGE_SIZE);
abuf = buf + o;
#if 0
r = sys_vm_map(SELF, 1, (vir_bytes)abuf,
1 * PAGE_SIZE, (phys_bytes)orp->or_base_port);
1 * I386_PAGE_SIZE, (phys_bytes)orp->or_base_port);
#else
r = ENOSYS;
#endif
if(r!=OK)
panic(__FILE__, "map_hw_buffer: sys_vm_map failed:", r);
hw->locmem = abuf;
}

View file

@ -13,7 +13,7 @@ d = ..
CC = cc
CFLAGS = -I$i $(CPROFILE)
LDFLAGS = -i
LIBS = -lsysutil -lsys -ltimers
LIBS = -lsys -ltimers
OBJ = main.o pci.o pci_table.o

View file

@ -388,8 +388,10 @@ message *mp;
}
acl[i].inuse= 0;
#if 0
printf("do_acl: deleting ACL for %d ('%s') at entry %d\n",
acl[i].acl.rsp_endpoint, acl[i].acl.rsp_label, i);
#endif
/* Also release all devices held by this process */
pci_release(proc_nr);

View file

@ -10,7 +10,7 @@ Created: Jan 2000 by Philip Homburg <philip@cs.vu.nl>
#include "../drivers.h"
#include <assert.h>
#include <ibm/pci.h>
#include <sys/vm.h>
#include <sys/vm_i386.h>
#include <minix/com.h>
#include <minix/rs.h>
#include <minix/syslib.h>
@ -118,7 +118,9 @@ FORWARD _PROTOTYPE( int do_piix, (int devind) );
FORWARD _PROTOTYPE( int do_amd_isabr, (int devind) );
FORWARD _PROTOTYPE( int do_sis_isabr, (int devind) );
FORWARD _PROTOTYPE( int do_via_isabr, (int devind) );
#if 0
FORWARD _PROTOTYPE( void report_vga, (int devind) );
#endif
FORWARD _PROTOTYPE( char *pci_vid_name, (U16_t vid) );
FORWARD _PROTOTYPE( char *pci_baseclass_name, (U8_t baseclass) );
FORWARD _PROTOTYPE( char *pci_subclass_name, (U8_t baseclass,
@ -872,8 +874,10 @@ printf("probe_bus(%d)\n", busind);
print_capabilities(devind);
t3= ((baseclass << 16) | (subclass << 8) | infclass);
#if 0
if (t3 == PCI_T3_VGA || t3 == PCI_T3_VGA_OLD)
report_vga(devind);
#endif
if (nr_pcidev >= NR_PCIDEV)
panic("PCI","too many PCI devices", nr_pcidev);
@ -1406,8 +1410,8 @@ PRIVATE void complete_bars()
if (!(pcidev[i].pd_bar[j].pb_flags & PBF_INCOMPLETE))
continue;
size= pcidev[i].pd_bar[j].pb_size;
if (size < PAGE_SIZE)
size= PAGE_SIZE;
if (size < I386_PAGE_SIZE)
size= I386_PAGE_SIZE;
base= memgap_high-size;
base &= ~(u32_t)(size-1);
if (base < memgap_low)
@ -2010,6 +2014,7 @@ int devind;
}
#if 0
/*===========================================================================*
* report_vga *
*===========================================================================*/
@ -2042,6 +2047,7 @@ int devind;
amount);
}
}
#endif
/*===========================================================================*

View file

@ -13,7 +13,7 @@ d = ..
CC = exec cc
CFLAGS = -I$i $(CPROFILE)
LDFLAGS = -i
LIBS = -lsysutil -lsys
LIBS = -lsys -lsys
OBJ = printer.o

View file

@ -14,7 +14,7 @@ MAKE = exec make
CC = exec cc
CFLAGS = -I$i $(CPROFILE)
LDFLAGS = -i -L../libdriver_asyn
LIBS = -lsysutil -ldriver -lsys
LIBS = -ldriver -lsys
LIB_DEPS=../libdriver_asyn/libdriver.a
OBJ = main.o random.o sha2.o aes/rijndael_api.o aes/rijndael_alg.o

View file

@ -6,7 +6,7 @@ MAKE = exec make
CC = exec cc
CFLAGS=-D_MINIX=1 -D_POSIX_SOURCE=1 -D_SYSTEM=1
LDFLAGS = -i
LIBS = -lsysutil -lsys
LIBS = -lsys
OBJ = readclock.o

View file

@ -14,7 +14,7 @@ MAKE = exec make
CC = exec cc
CFLAGS = -I$i $(CPROFILE)
LDFLAGS = -i
LIBS = -lsysutil -lsys -ltimers
LIBS = -lsys -ltimers
OBJ = rtl8139.o

View file

@ -12,7 +12,7 @@ d = ..
CC = exec cc
CFLAGS = -I$i $(CPROFILE)
LDFLAGS = -i
LIBS = -lsysutil -lsys
LIBS = -lsys
# build local binary

View file

@ -13,7 +13,7 @@ d = ..
CC = exec cc
CFLAGS = -I$i $(CPROFILE)
LDFLAGS = -i
LIBS = -lsysutil -lsys -ltimers
LIBS = -lsys -ltimers
OBJ = ti1225.o

View file

@ -7,6 +7,7 @@ Created: Dec 2005 by Philip Homburg
#include "../drivers.h"
#include <ibm/pci.h>
#include <sys/vm.h>
#include <sys/vm_i386.h>
#include "ti1225.h"
#include "i82365.h"
@ -29,7 +30,7 @@ PRIVATE struct port
char *base_ptr;
volatile struct csr *csr_ptr;
char buffer[2*PAGE_SIZE];
char buffer[2*I386_PAGE_SIZE];
} ports[NR_PORTS];
#define PF_PRESENT 1
@ -257,8 +258,8 @@ u32_t base;
vir_bytes buf_base;
buf_base= (vir_bytes)pp->buffer;
if (buf_base % PAGE_SIZE)
buf_base += PAGE_SIZE-(buf_base % PAGE_SIZE);
if (buf_base % I386_PAGE_SIZE)
buf_base += I386_PAGE_SIZE-(buf_base % I386_PAGE_SIZE);
pp->base_ptr= (char *)buf_base;
if (debug)
{
@ -269,8 +270,12 @@ u32_t base;
/* Clear low order bits in base */
base &= ~(u32_t)0xF;
#if 0
r= sys_vm_map(SELF, 1 /* map */, (vir_bytes)pp->base_ptr,
PAGE_SIZE, (phys_bytes)base);
I386_PAGE_SIZE, (phys_bytes)base);
#else
r = ENOSYS;
#endif
if (r != OK)
panic("ti1225", "map_regs: sys_vm_map failed", r);
}
@ -422,7 +427,7 @@ struct port *pp;
csr_present= pp->csr_ptr->csr_present;
if (csr_present & CP_PWRCYCLE)
break;
} while (getuptime(&t1)==OK && (t1-t0) < MICROS_TO_TICKS(100000));
} while (getuptime(&t1)==OK && (t1-t0) < micros_to_ticks(100000));
if (!(csr_present & CP_PWRCYCLE))
{

View file

@ -14,10 +14,10 @@ d = ..
# programs, flags, etc.
MAKE = exec make
CC = exec cc
CPPFLAGS = -I$i -I../../kernel/arch/$(ARCH)/include
CPPFLAGS = -I$i
CFLAGS = $(CPPFLAGS)
LDFLAGS = -i
LIBS = -lsysutil -lsys -ltimers
LIBS = -lsys -ltimers
OBJ = tty.o console.o vidcopy.o keyboard.o pty.o rs232.o
@ -25,7 +25,7 @@ OBJ = tty.o console.o vidcopy.o keyboard.o pty.o rs232.o
all build: $(DRIVER)
$(DRIVER): $(OBJ)
$(CC) -o $@ $(LDFLAGS) $(OBJ) $(LIBS)
install -S 8k $(DRIVER)
install -S 16k $(DRIVER)
# install with other drivers
install:

View file

@ -20,61 +20,27 @@
#include <termios.h>
#include <sys/ioctl.h>
#include <sys/vm.h>
#include <sys/video.h>
#include <minix/tty.h>
#include <minix/callnr.h>
#include <minix/com.h>
#include <minix/sys_config.h>
#include "tty.h"
#include "../../kernel/const.h"
#include "../../kernel/config.h"
#include "../../kernel/type.h"
/* Set this to 1 if you want console output duplicated on the first
* serial line.
*/
#define DUP_CONS_TO_SER 0
/* Definitions used by the console driver. */
#define MONO_BASE 0xB0000L /* base of mono video memory */
#define COLOR_BASE 0xB8000L /* base of color video memory */
#define MONO_SIZE 0x1000 /* 4K mono video memory */
#define COLOR_SIZE 0x4000 /* 16K color video memory */
#define EGA_SIZE 0x8000 /* EGA & VGA have at least 32K */
#define BLANK_COLOR 0x0700 /* determines cursor color on blank screen */
#define SCROLL_UP 0 /* scroll forward */
#define SCROLL_DOWN 1 /* scroll backward */
#define BLANK_MEM ((u16_t *) 0) /* tells mem_vid_copy() to blank the screen */
#define CONS_RAM_WORDS 80 /* video ram buffer size */
#define MAX_ESC_PARMS 4 /* number of escape sequence params allowed */
/* Constants relating to the controller chips. */
#define M_6845 0x3B4 /* port for 6845 mono */
#define C_6845 0x3D4 /* port for 6845 color */
#define INDEX 0 /* 6845's index register */
#define DATA 1 /* 6845's data register */
#define STATUS 6 /* 6845's status register */
#define VID_ORG 12 /* 6845's origin register */
#define CURSOR 14 /* 6845's cursor register */
/* The clock task should provide an interface for this */
#define TIMER_FREQ 1193182L /* clock frequency for timer in PC and AT */
/* Beeper. */
#define BEEP_FREQ 0x0533 /* value to put into timer to set beep freq */
#define B_TIME 3 /* length of CTRL-G beep is ticks */
/* definitions used for font management */
#define GA_SEQUENCER_INDEX 0x3C4
#define GA_SEQUENCER_DATA 0x3C5
#define GA_GRAPHICS_INDEX 0x3CE
#define GA_GRAPHICS_DATA 0x3CF
#define GA_VIDEO_ADDRESS 0xA0000L
#define GA_FONT_SIZE 8192
/* Global variables used by the console driver and assembly support. */
PUBLIC int vid_index; /* index of video segment in remote mem map */
PUBLIC u16_t vid_seg;
PUBLIC vir_bytes vid_off; /* video ram is found at vid_seg:vid_off */
PUBLIC unsigned vid_size; /* 0x2000 for color or 0x0800 for mono */
PUBLIC phys_bytes vid_size; /* 0x2000 for color or 0x0800 for mono */
PUBLIC phys_bytes vid_base;
PUBLIC unsigned vid_mask; /* 0x1FFF for color or 0x07FF for mono */
PUBLIC unsigned blank_color = BLANK_COLOR; /* display code for blank */
@ -87,6 +53,7 @@ PRIVATE unsigned font_lines; /* font lines per character */
PRIVATE unsigned scr_width; /* # characters on a line */
PRIVATE unsigned scr_lines; /* # lines on the screen */
PRIVATE unsigned scr_size; /* # characters on the screen */
PUBLIC unsigned info_location; /* location in video memory of struct */
PRIVATE int disabled_vc = -1; /* Virtual console that was active when
* disable_console was called.
@ -95,6 +62,9 @@ PRIVATE int disabled_sm; /* Scroll mode to be restored when re-enabling
* console
*/
/* boot_tty_info we use to communicate with the boot code. */
struct boot_tty_info boot_tty_info;
/* Per console data. */
typedef struct console {
tty_t *c_tty; /* associated TTY struct */
@ -113,11 +83,34 @@ typedef struct console {
int *c_esc_parmp; /* pointer to current escape parameter */
int c_esc_parmv[MAX_ESC_PARMS]; /* list of escape parameters */
u16_t c_ramqueue[CONS_RAM_WORDS]; /* buffer for video RAM */
int c_line; /* line no */
} console_t;
#define UPDATEBOOTINFO(ccons, infofield, value) { \
if(ccons->c_line == 0) { \
boot_tty_info.infofield = value; \
mem_vid_copy((u16_t *) &boot_tty_info, \
info_location/2, sizeof(boot_tty_info)/2); \
} \
}
#define UPDATE_CURSOR(ccons, cursor) { \
ccons->c_cur = cursor; \
UPDATEBOOTINFO(ccons, conscursor, ccons->c_cur); \
if(curcons && ccons == curcons) \
set_6845(CURSOR, ccons->c_cur); \
}
#define UPDATE_ORIGIN(ccons, origin) { \
ccons->c_org = origin; \
UPDATEBOOTINFO(ccons, consorigin, ccons->c_org); \
if (curcons && ccons == curcons) \
set_6845(VID_ORG, ccons->c_org); \
}
PRIVATE int nr_cons= 1; /* actual number of consoles */
PRIVATE console_t cons_table[NR_CONS];
PRIVATE console_t *curcons; /* currently visible */
PRIVATE console_t *curcons = NULL; /* currently visible */
/* Color if using a color controller. */
#define color (vid_port == C_6845)
@ -142,14 +135,20 @@ FORWARD _PROTOTYPE( void flush, (console_t *cons) );
FORWARD _PROTOTYPE( void parse_escape, (console_t *cons, int c) );
FORWARD _PROTOTYPE( void scroll_screen, (console_t *cons, int dir) );
FORWARD _PROTOTYPE( void set_6845, (int reg, unsigned val) );
FORWARD _PROTOTYPE( void get_6845, (int reg, unsigned *val) );
FORWARD _PROTOTYPE( void stop_beep, (timer_t *tmrp) );
FORWARD _PROTOTYPE( void cons_org0, (void) );
FORWARD _PROTOTYPE( void disable_console, (void) );
FORWARD _PROTOTYPE( void reenable_console, (void) );
FORWARD _PROTOTYPE( int ga_program, (struct sequence *seq) );
FORWARD _PROTOTYPE( int cons_ioctl, (tty_t *tp, int) );
#if DUP_CONS_TO_SER
FORWARD _PROTOTYPE( void ser_putc, (char c) );
#endif
#if 0
FORWARD _PROTOTYPE( void get_6845, (int reg, unsigned *val) );
#endif
/*===========================================================================*
* cons_write *
@ -174,7 +173,7 @@ int try;
/* Check quickly for nothing to do, so this can be called often without
* unmodular tests elsewhere.
*/
if ((count = tp->tty_outleft) == 0 || tp->tty_inhibited) return;
if ((count = tp->tty_outleft) == 0 || tp->tty_inhibited) return 0;
/* Copy the user bytes to buf[] for decent addressing. Loop over the
* copies, since the user buffer may be much larger than buf[].
@ -228,6 +227,8 @@ int try;
tp->tty_outcum);
tp->tty_outcum = 0;
}
return 0;
}
/*===========================================================================*
@ -365,9 +366,9 @@ int dir; /* SCROLL_UP or SCROLL_DOWN */
} else
if (!wrap && cons->c_org + scr_size + scr_width >= cons->c_limit) {
vid_vid_copy(cons->c_org + scr_width, cons->c_start, chars);
cons->c_org = cons->c_start;
UPDATE_ORIGIN(cons, cons->c_start);
} else {
cons->c_org = (cons->c_org + scr_width) & vid_mask;
UPDATE_ORIGIN(cons, (cons->c_org + scr_width) & vid_mask);
}
new_line = (cons->c_org + chars) & vid_mask;
} else {
@ -378,9 +379,9 @@ int dir; /* SCROLL_UP or SCROLL_DOWN */
if (!wrap && cons->c_org < cons->c_start + scr_width) {
new_org = cons->c_limit - scr_size;
vid_vid_copy(cons->c_org, new_org + scr_width, chars);
cons->c_org = new_org;
UPDATE_ORIGIN(cons, new_org);
} else {
cons->c_org = (cons->c_org - scr_width) & vid_mask;
UPDATE_ORIGIN(cons, (cons->c_org - scr_width) & vid_mask);
}
new_line = cons->c_org;
}
@ -388,8 +389,6 @@ int dir; /* SCROLL_UP or SCROLL_DOWN */
blank_color = cons->c_blank;
mem_vid_copy(BLANK_MEM, new_line, scr_width);
/* Set the new video origin. */
if (cons == curcons) set_6845(VID_ORG, cons->c_org);
flush(cons);
}
@ -421,10 +420,8 @@ register console_t *cons; /* pointer to console struct */
if (cons->c_row < 0) cons->c_row = 0;
if (cons->c_row >= scr_lines) cons->c_row = scr_lines - 1;
cur = cons->c_org + cons->c_row * scr_width + cons->c_column;
if (cur != cons->c_cur) {
if (cons == curcons) set_6845(CURSOR, cur);
cons->c_cur = cur;
}
if (cur != cons->c_cur)
UPDATE_CURSOR(cons, cur);
}
/*===========================================================================*
@ -747,6 +744,7 @@ unsigned val; /* 16-bit value to set it to */
sys_voutb(char_out, 4); /* do actual output */
}
#if 0
/*===========================================================================*
* get_6845 *
*===========================================================================*/
@ -765,6 +763,7 @@ unsigned *val; /* 16-bit value to set it to */
v2 = v;
*val = (v1 << 8) | v2;
}
#endif
/*===========================================================================*
* beep *
@ -810,8 +809,7 @@ PRIVATE void beep()
*===========================================================================*/
PUBLIC void do_video(message *m)
{
int i, n, r, ops, watch, safe = 0;
unsigned char c;
int r, safe = 0;
/* Execute the requested device driver function. */
r= EINVAL; /* just in case */
@ -827,8 +825,10 @@ PUBLIC void do_video(message *m)
break;
case DEV_IOCTL_S:
safe=1;
if (m->TTY_REQUEST == MIOCMAP || m->TTY_REQUEST == MIOCUNMAP)
{
switch(m->TTY_REQUEST) {
case MIOCMAP:
case MIOCUNMAP: {
#if 0
int r, do_map;
struct mapreq mapreq;
@ -859,8 +859,50 @@ PUBLIC void do_video(message *m)
r= sys_vm_map(safe ? m->POSITION : m->IO_ENDPT,
do_map, (phys_bytes)mapreq.base, mapreq.size,
mapreq.offset);
#else
r = ENOSYS;
printf("tty: %ld used old MIOCMAP interface\n",
safe ? m->POSITION : m->IO_ENDPT);
#endif
tty_reply(TASK_REPLY, m->m_source, m->IO_ENDPT, r);
return;
}
case TIOCMAPMEM:
case TIOCUNMAPMEM: {
int r, do_map;
struct mapreqvm mapreqvm;
void *result;
do_map= (m->REQUEST == TIOCMAPMEM); /* else unmap */
/* Get request structure */
if(safe) {
r = sys_safecopyfrom(m->IO_ENDPT,
(vir_bytes)m->ADDRESS, 0, (vir_bytes) &mapreqvm,
sizeof(mapreqvm), D);
} else {
r= sys_vircopy(m->IO_ENDPT, D,
(vir_bytes)m->ADDRESS,
SELF, D, (vir_bytes)&mapreqvm,sizeof(mapreqvm));
}
if (r != OK)
{
tty_reply(TASK_REPLY, m->m_source, m->IO_ENDPT,
r);
return;
}
/* In safe ioctl mode, the POSITION field contains
* the endpt number of the original requestor.
* IO_ENDPT is always FS.
*/
if(do_map) {
} else {
}
tty_reply(TASK_REPLY, m->m_source, m->IO_ENDPT, r);
return;
}
}
r= ENOTTY;
break;
@ -940,19 +982,19 @@ tty_t *tp;
{
/* Initialize the screen driver. */
console_t *cons;
phys_bytes vid_base;
u16_t bios_columns, bios_crtbase, bios_fontlines;
u8_t bios_rows;
int line;
int s;
static int vdu_initialized = 0;
unsigned page_size;
static unsigned page_size;
/* Associate console and TTY. */
line = tp - &tty_table[0];
if (line >= nr_cons) return;
cons = &cons_table[line];
cons->c_tty = tp;
cons->c_line = line;
tp->tty_priv = cons;
/* Fill in TTY function hooks. */
@ -987,6 +1029,7 @@ tty_t *tp;
}
if (machine.vdu_ega) vid_size = EGA_SIZE;
wrap = ! machine.vdu_ega;
info_location = vid_size - sizeof(struct boot_tty_info);
s = sys_segctl(&vid_index, &vid_seg, &vid_off, vid_base, vid_size);
@ -997,7 +1040,8 @@ tty_t *tp;
scr_size = scr_lines * scr_width;
/* There can be as many consoles as video memory allows. */
nr_cons = vid_size / scr_size;
nr_cons = (vid_size - sizeof(struct boot_tty_info)/2) / scr_size;
if (nr_cons > NR_CONS) nr_cons = NR_CONS;
if (nr_cons > 1) wrap = 0;
page_size = vid_size / nr_cons;
@ -1013,13 +1057,18 @@ tty_t *tp;
blank_color = BLANK_COLOR;
mem_vid_copy(BLANK_MEM, cons->c_start, scr_size);
} else {
int i, n;
/* Set the cursor of the console vty at the bottom. c_cur
* is updated automatically later.
*/
scroll_screen(cons, SCROLL_UP);
cons->c_row = scr_lines - 1;
cons->c_column = 0;
memset(&boot_tty_info, 0, sizeof(boot_tty_info));
UPDATE_CURSOR(cons, cons->c_cur);
UPDATE_ORIGIN(cons, cons->c_org);
boot_tty_info.flags = BTIF_CONSCURSOR | BTIF_CONSORIGIN;
boot_tty_info.magic = TTYMAGIC;
}
select_console(0);
cons_ioctl(tp, 0);
@ -1045,9 +1094,9 @@ int c;
cons_putk(c);
if (c != 0) {
kmess.km_buf[kmess.km_next] = c; /* put normal char in buffer */
if (kmess.km_size < KMESS_BUF_SIZE)
if (kmess.km_size < _KMESS_BUF_SIZE)
kmess.km_size += 1;
kmess.km_next = (kmess.km_next + 1) % KMESS_BUF_SIZE;
kmess.km_next = (kmess.km_next + 1) % _KMESS_BUF_SIZE;
} else {
notify(LOG_PROC_NR);
}
@ -1060,9 +1109,8 @@ PUBLIC void do_new_kmess(m)
message *m;
{
/* Notification for a new kernel message. */
struct kmessages kmess; /* kmessages structure */
static struct kmessages kmess; /* kmessages structure */
static int prev_next = 0; /* previous next seen */
int size, next;
int bytes;
int r;
@ -1081,15 +1129,15 @@ message *m;
/* Print only the new part. Determine how many new bytes there are with
* help of the current and previous 'next' index. Note that the kernel
* buffer is circular. This works fine if less then KMESS_BUF_SIZE bytes
* is new data; else we miss % KMESS_BUF_SIZE here.
* buffer is circular. This works fine if less then _KMESS_BUF_SIZE bytes
* is new data; else we miss % _KMESS_BUF_SIZE here.
* Check for size being positive, the buffer might as well be emptied!
*/
if (kmess.km_size > 0) {
bytes = ((kmess.km_next + KMESS_BUF_SIZE) - prev_next) % KMESS_BUF_SIZE;
bytes = ((kmess.km_next + _KMESS_BUF_SIZE) - prev_next) % _KMESS_BUF_SIZE;
r=prev_next; /* start at previous old */
while (bytes > 0) {
cons_putk( kmess.km_buf[(r%KMESS_BUF_SIZE)] );
cons_putk( kmess.km_buf[(r%_KMESS_BUF_SIZE)] );
bytes --;
r ++;
}
@ -1121,6 +1169,8 @@ int safe;
int r;
if(safe) {
r = sys_safecopyfrom(proc_nr, src, offset, (vir_bytes) &c, 1, D);
if(r != OK)
printf("<tty: proc %d, grant %ld>", proc_nr, src);
} else {
r = sys_vircopy(proc_nr, D, src+offset, SELF, D, (vir_bytes) &c, 1);
}
@ -1132,9 +1182,12 @@ int safe;
cons_putk(c);
}
cons_putk(0); /* always terminate, even with EFAULT */
m_ptr->m_type = DIAG_REPL;
m_ptr->REP_STATUS = result;
send(m_ptr->m_source, m_ptr);
if(m_ptr->m_type != ASYN_DIAGNOSTICS) {
m_ptr->m_type = DIAG_REPL;
m_ptr->REP_STATUS = result;
send(m_ptr->m_source, m_ptr);
}
}
/*===========================================================================*
@ -1237,7 +1290,7 @@ PRIVATE void cons_org0()
if (n > cons->c_org - cons->c_start)
n = cons->c_org - cons->c_start;
vid_vid_copy(cons->c_org, cons->c_org - n, scr_size);
cons->c_org -= n;
UPDATE_ORIGIN(cons, cons->c_org - n);
}
flush(cons);
}
@ -1283,10 +1336,12 @@ PUBLIC void select_console(int cons_line)
/* Set the current console to console number 'cons_line'. */
if (cons_line < 0 || cons_line >= nr_cons) return;
ccurrent = cons_line;
curcons = &cons_table[cons_line];
set_6845(VID_ORG, curcons->c_org);
set_6845(CURSOR, curcons->c_cur);
UPDATE_CURSOR(curcons, curcons->c_cur);
UPDATE_ORIGIN(curcons, curcons->c_org);
}
/*===========================================================================*
@ -1358,8 +1413,11 @@ int try;
tp->tty_winsize.ws_col= scr_width;
tp->tty_winsize.ws_xpixel= scr_width * 8;
tp->tty_winsize.ws_ypixel= scr_lines * font_lines;
return 0;
}
#if DUP_CONS_TO_SER
#define COM1_BASE 0x3F8
#define COM1_THR (COM1_BASE + 0)
#define LSR_THRE 0x20
@ -1381,3 +1439,4 @@ PRIVATE void ser_putc(char c)
}
sys_outb(thr, c);
}
#endif

View file

@ -14,16 +14,11 @@
#include <termios.h>
#include <signal.h>
#include <unistd.h>
#include <archtypes.h>
#include <minix/callnr.h>
#include <minix/com.h>
#include <minix/keymap.h>
#include "tty.h"
#include "keymaps/us-std.src"
#include "../../kernel/const.h"
#include "../../kernel/config.h"
#include "../../kernel/type.h"
#include "../../kernel/proc.h"
int irq_hook_id = -1;
int aux_irq_hook_id = -1;
@ -132,10 +127,9 @@ PRIVATE struct kbd_outack
PRIVATE int kbd_watchdog_set= 0;
PRIVATE int kbd_alive= 1;
PRIVATE int sticky_alt_mode = 0;
PRIVATE timer_t tmr_kbd_wd;
int sticky_alt_mode = 0;
FORWARD _PROTOTYPE( void handle_req, (struct kbd *kbdp, message *m) );
FORWARD _PROTOTYPE( int handle_status, (struct kbd *kbdp, message *m) );
FORWARD _PROTOTYPE( void kbc_cmd0, (int cmd) );
@ -153,6 +147,13 @@ FORWARD _PROTOTYPE( int kb_read, (struct tty *tp, int try) );
FORWARD _PROTOTYPE( unsigned map_key, (int scode) );
FORWARD _PROTOTYPE( void kbd_watchdog, (timer_t *tmrp) );
int micro_delay(u32_t usecs)
{
/* TTY can't use the library micro_delay() as that calls PM. */
tickdelay(micros_to_ticks(usecs));
return OK;
}
/*===========================================================================*
* do_kbd *
*===========================================================================*/
@ -500,7 +501,6 @@ message *m_ptr;
int o, isaux;
unsigned char scode;
struct kbd *kbdp;
static timer_t timer; /* timer must be static! */
/* Fetch the character from the keyboard hardware and acknowledge it. */
if (!scan_keyboard(&scode, &isaux))
@ -637,7 +637,7 @@ PRIVATE void kbd_send()
}
if (sb & (KB_OUT_FULL|KB_IN_FULL))
{
printf("not sending 1: sb = 0x%x\n", sb);
printf("not sending 1: sb = 0x%lx\n", sb);
return;
}
micro_delay(KBC_IN_DELAY);
@ -646,7 +646,7 @@ PRIVATE void kbd_send()
}
if (sb & (KB_OUT_FULL|KB_IN_FULL))
{
printf("not sending 2: sb = 0x%x\n", sb);
printf("not sending 2: sb = 0x%lx\n", sb);
return;
}
@ -864,10 +864,10 @@ PRIVATE int kbc_read()
while (micro_elapsed(&ms) < 1000000);
#endif
panic("TTY", "kbc_read failed to complete", NO_NUM);
return EINVAL;
}
/*===========================================================================*
* kb_wait *
*===========================================================================*/
@ -876,7 +876,7 @@ PRIVATE int kb_wait()
/* Wait until the controller is ready; return zero if this times out. */
int retries;
unsigned long status, temp;
unsigned long status;
int s, isaux;
unsigned char byte;
@ -940,6 +940,12 @@ PUBLIC void kb_init_once(void)
{
int i;
u8_t ccb;
char env[100];
if(env_get_param("sticky_alt", env, sizeof(env)-1) == OK
&& atoi(env) == 1) {
sticky_alt_mode = 1;
}
set_leds(); /* turn off numlock led */
scan_keyboard(NULL, NULL); /* discard leftover keystroke */
@ -1020,7 +1026,7 @@ message *m_ptr; /* pointer to the request message */
* notifications if it is pressed. At most one binding per key can exist.
*/
int i;
int result;
int result = EINVAL;
switch (m_ptr->FKEY_REQUEST) { /* see what we must do */
case FKEY_MAP: /* request for new mapping */
@ -1104,8 +1110,6 @@ message *m_ptr; /* pointer to the request message */
}
}
break;
default:
result = EINVAL; /* key cannot be observed */
}
/* Almost done, return result to caller. */
@ -1128,7 +1132,6 @@ int scode; /* scan code for a function key */
message m;
int key;
int proc_nr;
int i,s;
/* Ignore key releases. If this is a key press, get full key code. */
if (scode & KEY_RELEASE) return(FALSE); /* key release */
@ -1166,31 +1169,17 @@ int scode; /* scan code for a function key */
*===========================================================================*/
PRIVATE void show_key_mappings()
{
int i,s;
struct proc proc;
int i;
printf("\n");
printf("System information. Known function key mappings to request debug dumps:\n");
printf("-------------------------------------------------------------------------\n");
for (i=0; i<12; i++) {
printf(" %sF%d: ", i+1<10? " ":"", i+1);
if (fkey_obs[i].proc_nr != NONE) {
if ((s=sys_getproc(&proc, fkey_obs[i].proc_nr))!=OK)
printf("sys_getproc: %d\n", s);
printf("%-14.14s", proc.p_name);
} else {
printf("%-14.14s", "<none>");
}
printf("%-14.14s", "<none>");
printf(" %sShift-F%d: ", i+1<10? " ":"", i+1);
if (sfkey_obs[i].proc_nr != NONE) {
if ((s=sys_getproc(&proc, sfkey_obs[i].proc_nr))!=OK)
printf("sys_getproc: %d\n", s);
printf("%-14.14s", proc.p_name);
} else {
printf("%-14.14s", "<none>");
}
printf("%-14.14s", "<none>");
printf("\n");
}
printf("\n");
@ -1260,12 +1249,6 @@ int *isauxp;
#endif
}
int micro_delay(u32_t usecs)
{
tickdelay(MICROS_TO_TICKS(usecs));
return OK;
}
/*===========================================================================*
* kbd_watchdog *
*===========================================================================*/

View file

@ -4,8 +4,8 @@ LK = /usr/lib/keymaps
.SUFFIXES: .src .map
.src.map:
$(CC) -DKEYSRC=\"$<\" $(CPROFILE) genmap.c -lsysutil -lsys
.src.map:
$(CC) -DKEYSRC=\"$<\" genmap.c
./a.out > $@
@rm -f a.out

View file

@ -89,7 +89,6 @@ message *m_ptr;
/* Perform an open/close/read/write call on a /dev/ptypX device. */
pty_t *pp = tp->tty_priv;
int r;
phys_bytes p;
int safe = 0;
switch (m_ptr->m_type) {
@ -108,15 +107,6 @@ message *m_ptr;
r = EINVAL;
break;
}
#if DEAD_CODE
if (numap_local(m_ptr->IO_ENDPT, (vir_bytes) m_ptr->ADDRESS,
m_ptr->COUNT) == 0) {
#else
if ((r = sys_umap(m_ptr->IO_ENDPT, D, (vir_bytes) m_ptr->ADDRESS,
m_ptr->COUNT, &p)) != OK) {
#endif
break;
}
pp->rdsendreply = TRUE;
pp->rdcaller = m_ptr->m_source;
pp->rdproc = m_ptr->IO_ENDPT;
@ -130,12 +120,6 @@ message *m_ptr;
return; /* already done */
}
#if DEAD_CODE
if (m_ptr->TTY_FLAGS & O_NONBLOCK) {
r = EAGAIN; /* don't suspend */
pp->rdleft = pp->rdcum = 0;
} else
#endif
{
r = SUSPEND; /* do suspend */
pp->rdsendreply = FALSE;
@ -157,16 +141,6 @@ message *m_ptr;
r = EINVAL;
break;
}
#if DEAD_CODE
if (numap_local(m_ptr->IO_ENDPT, (vir_bytes) m_ptr->ADDRESS,
m_ptr->COUNT) == 0) {
r = EFAULT;
#else
if ((r = sys_umap(m_ptr->IO_ENDPT, D, (vir_bytes) m_ptr->ADDRESS,
m_ptr->COUNT, &p)) != OK) {
#endif
break;
}
pp->wrsendreply = TRUE;
pp->wrcaller = m_ptr->m_source;
pp->wrproc = m_ptr->IO_ENDPT;
@ -179,12 +153,6 @@ message *m_ptr;
return; /* already done */
}
#if DEAD_CODE
if (m_ptr->TTY_FLAGS & O_NONBLOCK) { /* don't suspend */
r = pp->wrcum > 0 ? pp->wrcum : EAGAIN;
pp->wrleft = pp->wrcum = 0;
} else
#endif
{
pp->wrsendreply = FALSE; /* do suspend */
r = SUSPEND;
@ -244,7 +212,7 @@ int try;
*/
pty_t *pp = tp->tty_priv;
int count, ocount, s;
phys_bytes user_phys;
/* PTY closed down? */
if (pp->state & PTY_CLOSED) {
@ -259,7 +227,7 @@ int try;
tp->tty_outleft = tp->tty_outcum = 0;
}
}
return;
return 0;
}
/* While there is something to do. */
@ -473,6 +441,8 @@ int try;
notify(pp->wrcaller);
}
}
return 0;
}
/*===========================================================================*
@ -485,7 +455,7 @@ int try;
/* The tty side has closed, so shut down the pty side. */
pty_t *pp = tp->tty_priv;
if (!(pp->state & PTY_ACTIVE)) return;
if (!(pp->state & PTY_ACTIVE)) return 0;
if (pp->rdleft > 0) {
assert(!pp->rdsendreply);
@ -498,6 +468,8 @@ int try;
}
if (pp->state & PTY_CLOSED) pp->state = 0; else pp->state |= TTY_CLOSED;
return 0;
}
/*===========================================================================*
@ -515,6 +487,8 @@ int try;
pp->wrleft= 0;
notify(pp->wrcaller);
}
return 0;
}
/*===========================================================================*
@ -529,6 +503,8 @@ int try;
pp->ocount = 0;
pp->otail = pp->ohead;
return 0;
}
/*===========================================================================*

View file

@ -11,21 +11,6 @@
#if NR_RS_LINES > 0
#if (MACHINE != IBM_PC) && (MACHINE != ATARI)
#error /* rs232.c only supports PC and Atari ST */
#endif
#if (MACHINE == ATARI)
#include "staddr.h"
#include "stsound.h"
#include "stmfp.h"
#if (NR_RS_LINES > 1)
#error /* Only one physical RS232 line available */
#endif
#endif
#if (MACHINE == IBM_PC) /* PC/AT 8250/16450 chip combination */
/* 8250 constants. */
#define UART_FREQ 115200L /* timer frequency */
@ -65,46 +50,25 @@
#define MS_RLSD 0x80 /* Received Line Signal Detect */
#define MS_DRLSD 0x08 /* RLSD Delta */
#else /* MACHINE == ATARI */ /* Atari ST 68901 USART */
#define DATA_BITS_SHIFT 8 /* amount data bits shifted in mode */
#define DEF_BAUD 1200 /* default baud rate */
/* Most of the USART constants are already defined in stmfp.h . The local
* definitions made here are for keeping C code changes smaller. --kub
*/
#define UART_FREQ 19200L /* timer frequency */
/* Line status bits. */
#define LS_OVERRUN_ERR R_OE
#define LS_PARITY_ERR R_PE
#define LS_FRAMING_ERR R_FE
#define LS_BREAK_INTERRUPT R_BREAK
/* Modem status bits. */
#define MS_CTS IO_SCTS /* 0x04 */
#endif /* MACHINE == ATARI */
#define DATA_BITS_SHIFT 8 /* amount data bits shifted in mode */
#define DEF_BAUD 1200 /* default baud rate */
#define RS_IBUFSIZE 1024 /* RS232 input buffer size */
#define RS_OBUFSIZE 1024 /* RS232 output buffer size */
#define RS_IBUFSIZE 1024 /* RS232 input buffer size */
#define RS_OBUFSIZE 1024 /* RS232 output buffer size */
/* Input buffer watermarks.
* The external device is asked to stop sending when the buffer
* exactly reaches high water, or when TTY requests it. Sending restarts
* when the input buffer empties below the low watermark.
*/
#define RS_ILOWWATER (1 * RS_IBUFSIZE / 4)
#define RS_IHIGHWATER (3 * RS_IBUFSIZE / 4)
#define RS_ILOWWATER (1 * RS_IBUFSIZE / 4)
#define RS_IHIGHWATER (3 * RS_IBUFSIZE / 4)
/* Output buffer low watermark.
* TTY is notified when the output buffer empties below the low watermark, so
* it may continue filling the buffer if doing a large write.
*/
#define RS_OLOWWATER (1 * RS_OBUFSIZE / 4)
#if (MACHINE == IBM_PC)
#define RS_OLOWWATER (1 * RS_OBUFSIZE / 4)
/* Macros to handle flow control.
* Interrupts must be off when they are used.
@ -141,36 +105,6 @@
#define devhup(rs) \
((my_inb(rs->modem_status_port) & (MS_RLSD|MS_DRLSD)) == MS_DRLSD)
#else /* MACHINE == ATARI */
/* Macros to handle flow control.
* Time is critical - already the function call for lock()/restore() is
* annoying.
* istart() tells external device we are ready by raising RTS.
* istop() tells external device we are not ready by dropping RTS.
* DTR is kept high all the time (it probably should be raised by open and
* dropped by close of the device). NOTE: The modem lines are active low.
*/
#define set_porta(msk,val) { register int s = lock(); \
SOUND->sd_selr = YM_IOA; \
SOUND->sd_wdat = \
SOUND->sd_rdat & (msk) | (val); \
restore(s); }
#define istart(rs) { set_porta( ~(PA_SRTS|PA_SDTR),0 ); \
(rs)->idevready = TRUE; }
#define istop(rs) { set_porta( ~PA_SDTR, PA_SRTS ); \
(rs)->idevready = FALSE; }
/* Macro to tell if device is ready. The rs->cts field is set to MS_CTS if
* CLOCAL is in effect for a line without a CTS wire.
*/
#define devready(rs) ((~MFP->mf_gpip | rs->cts) & MS_CTS)
/* Transmitter ready test */
#define txready(rs) (MFP->mf_tsr & (T_EMPTY | T_UE))
#endif /* MACHINE == ATARI */
/* Types. */
typedef unsigned char bool_t; /* boolean */
@ -234,11 +168,6 @@ typedef struct rs232 {
PUBLIC rs232_t rs_lines[NR_RS_LINES];
/* Table and macro to translate an RS232 line number to its rs_lines entry. */
PRIVATE rs232_t *p_rs_addr[NR_RS_LINES];
#define rs_addr(line) (p_rs_addr[line])
#if (MACHINE == IBM_PC)
/* 8250 base addresses. */
PRIVATE port_t addr_8250[] = {
@ -472,7 +401,6 @@ rs232_t *rs; /* which line */
}
if (divisor == 0) return; /* B0? */
#if (MACHINE == IBM_PC)
/* Compute line control flag bits. */
line_controls = 0;
if (tp->tty_termios.c_cflag & PARENB) {
@ -502,27 +430,6 @@ rs232_t *rs; /* which line */
rs->ostate &= ~ORAW;
unlock();
#else /* MACHINE == ATARI */
line_controls = U_Q16;
if (tp->tty_termios.c_cflag & PARENB) {
line_controls |= U_PAR;
if (!(tp->tty_termios.c_cflag & PARODD)) line_controls |= U_EVEN;
}
line_controls |= (divisor >= (UART_FREQ / 110)) ? U_ST2 : U_ST1;
switch (tp->tty_termios.c_cflag & CSIZE) { /* XXX - are U_Dn like CSn? */
case CS5: line_controls |= U_D5; break;
case CS5: line_controls |= U_D6; break;
case CS5: line_controls |= U_D7; break;
case CS5: line_controls |= U_D8; break;
}
lock();
MFP->mf_ucr = line_controls;
MFP->mf_tddr = divisor;
unlock();
#endif /* MACHINE == ATARI */
}
/*===========================================================================*
@ -536,11 +443,8 @@ tty_t *tp; /* which TTY */
register rs232_t *rs;
int line;
#if (MACHINE == IBM_PC)
port_t this_8250;
int irq;
long v;
#endif
/* Associate RS232 and TTY structures. */
line = tp - &tty_table[NR_CONS];
@ -550,7 +454,6 @@ tty_t *tp; /* which TTY */
/* Set up input queue. */
rs->ihead = rs->itail = rs->ibuf;
#if (MACHINE == IBM_PC)
/* Precalculate port numbers for speed. Magic numbers in the code (once). */
this_8250 = addr_8250[line];
rs->xmit_port = this_8250 + 0;
@ -563,7 +466,6 @@ tty_t *tp; /* which TTY */
rs->modem_ctl_port = this_8250 + 4;
rs->line_status_port = this_8250 + 5;
rs->modem_status_port = this_8250 + 6;
#endif
/* Set up the hardware to a base state, in particular
* o turn off DTR (MC_DTR) to try to stop the external device.
@ -580,22 +482,17 @@ tty_t *tp; /* which TTY */
*/
istop(rs); /* sets modem_ctl_port */
rs_config(rs);
#if (MACHINE == IBM_PC)
sys_outb(rs->int_enab_port, 0);
#endif
/* Clear any harmful leftover interrupts. An output interrupt is harmless
* and will occur when interrupts are enabled anyway. Set up the output
* queue using the status from clearing the modem status interrupt.
*/
#if (MACHINE == IBM_PC)
sys_inb(rs->line_status_port, &dummy);
sys_inb(rs->recv_port, &dummy);
#endif
rs->ostate = devready(rs) | ORAW | OSWREADY; /* reads modem_ctl_port */
rs->ohead = rs->otail = rs->obuf;
#if (MACHINE == IBM_PC)
/* Enable interrupts for both interrupt controller and device. */
irq = (line & 1) == 0 ? RS232_IRQ : SECONDARY_IRQ;
@ -613,20 +510,6 @@ tty_t *tp; /* which TTY */
sys_outb(rs->int_enab_port, IE_LINE_STATUS_CHANGE | IE_MODEM_STATUS_CHANGE
| IE_RECEIVER_READY | IE_TRANSMITTER_READY);
#else /* MACHINE == ATARI */
/* Initialize the 68901 chip, then enable interrupts. */
MFP->mf_scr = 0x00;
MFP->mf_tcdcr |= T_Q004;
MFP->mf_rsr = R_ENA;
MFP->mf_tsr = T_ENA;
MFP->mf_aer = (MFP->mf_aer | (IO_SCTS|IO_SDCD)) ^
(MFP->mf_gpip & (IO_SCTS|IO_SDCD));
MFP->mf_ddr = (MFP->mf_ddr & ~ (IO_SCTS|IO_SDCD));
MFP->mf_iera |= (IA_RRDY|IA_RERR|IA_TRDY|IA_TERR);
MFP->mf_imra |= (IA_RRDY|IA_RERR|IA_TRDY|IA_TERR);
MFP->mf_ierb |= (IB_SCTS|IB_SDCD);
MFP->mf_imrb |= (IB_SCTS|IB_SDCD);
#endif /* MACHINE == ATARI */
/* Fill in TTY function hooks. */
tp->tty_devread = rs_read;
@ -721,7 +604,7 @@ int try;
if (ostate & ODEVHUP) {
sigchar(tp, SIGHUP);
tp->tty_termios.c_ospeed = B0; /* Disable further I/O. */
return;
return 0;
}
}
@ -744,6 +627,8 @@ int try;
unlock();
if ((rs->itail += count) == bufend(rs->ibuf)) rs->itail = rs->ibuf;
}
return 0;
}
/*===========================================================================*
@ -787,7 +672,6 @@ int dummy;
{
/* The line is closed; optionally hang up. */
rs232_t *rs = tp->tty_priv;
int r;
if (tp->tty_termios.c_cflag & HUPCL) {
sys_outb(rs->modem_ctl_port, MC_OUT2 | MC_RTS);
@ -797,7 +681,6 @@ int dummy;
/* Low level (interrupt) routines. */
#if (MACHINE == IBM_PC)
/*===========================================================================*
* rs232_handler *
*===========================================================================*/
@ -831,50 +714,6 @@ struct rs232 *rs;
return;
}
}
#endif /* MACHINE == IBM_PC */
#if (MACHINE == ATARI)
/*===========================================================================*
* siaint *
*===========================================================================*/
PRIVATE void siaint(type)
int type; /* interrupt type */
{
/* siaint is the rs232 interrupt procedure for Atari ST's. For ST there are
* as much as 5 interrupt lines used for rs232. The trap type byte left on the
* stack by the assembler interrupt handler identifies the interrupt cause.
*/
register unsigned char code;
register rs232_t *rs = &rs_lines[0];
int s = lock();
switch (type & 0x00FF)
{
case 0x00: /* receive buffer full */
in_int(rs);
break;
case 0x01: /* receive error */
line_int(rs);
break;
case 0x02: /* transmit buffer empty */
out_int(rs);
break;
case 0x03: /* transmit error */
code = MFP->mf_tsr;
if (code & ~(T_ENA | T_UE | T_EMPTY))
{
printf("sia: transmit error: status=%x\r\n", code);
/* MFP->mf_udr = lastchar; */ /* retry */
}
break;
case 0x04: /* modem lines change */
modem_int(rs);
break;
}
restore(s);
}
#endif /* MACHINE == ATARI */
/*===========================================================================*
* in_int *
@ -895,11 +734,7 @@ register rs232_t *rs; /* line with input interrupt */
return;
#endif
#if (MACHINE == IBM_PC)
sys_inb(rs->recv_port, &c);
#else /* MACHINE == ATARI */
c = MFP->mf_udr;
#endif
if (!(rs->ostate & ORAW)) {
if (c == rs->oxoff) {
@ -937,14 +772,8 @@ register rs232_t *rs; /* line with line status interrupt */
/* Check for and record errors. */
unsigned long s;
#if (MACHINE == IBM_PC)
sys_inb(rs->line_status_port, &s);
rs->lstatus = s;
#else /* MACHINE == ATARI */
rs->lstatus = MFP->mf_rsr;
MFP->mf_rsr &= R_ENA;
rs->pad = MFP->mf_udr; /* discard char in case of LS_OVERRUN_ERR */
#endif /* MACHINE == ATARI */
if (rs->lstatus & LS_FRAMING_ERR) ++rs->framing_errors;
if (rs->lstatus & LS_OVERRUN_ERR) ++rs->overrun_errors;
if (rs->lstatus & LS_PARITY_ERR) ++rs->parity_errors;
@ -961,12 +790,6 @@ register rs232_t *rs; /* line with modem interrupt */
* If the device just became ready, restart output.
*/
#if (MACHINE == ATARI)
/* Set active edge interrupt so that next change causes a new interrupt */
MFP->mf_aer = (MFP->mf_aer | (IO_SCTS|IO_SDCD)) ^
(MFP->mf_gpip & (IO_SCTS|IO_SDCD));
#endif
if (devhup(rs)) {
rs->ostate |= ODEVHUP;
rs->tty->tty_events = 1;
@ -994,11 +817,7 @@ register rs232_t *rs; /* line with output interrupt */
if (rs->ostate >= (ODEVREADY | OQUEUED | OSWREADY)) {
/* Bit test allows ORAW and requires the others. */
#if (MACHINE == IBM_PC)
sys_outb(rs->xmit_port, *rs->otail);
#else /* MACHINE == ATARI */
MFP->mf_udr = *rs->otail;
#endif
if (++rs->otail == bufend(rs->obuf)) rs->otail = rs->obuf;
if (--rs->ocount == 0) {
rs->ostate ^= (ODONE | OQUEUED); /* ODONE on, OQUEUED off */

View file

@ -61,9 +61,9 @@
#include <sys/ioc_tty.h>
#include <signal.h>
#include <minix/callnr.h>
#if (CHIP == INTEL)
#include <minix/sys_config.h>
#include <minix/tty.h>
#include <minix/keymap.h>
#endif
#include "tty.h"
#include <sys/time.h>
@ -92,6 +92,7 @@ unsigned long rs_irq_set = 0;
#if NR_RS_LINES == 0
#define rs_init(tp) ((void) 0)
#endif
#if NR_PTYS == 0
#define pty_init(tp) ((void) 0)
#define do_pty(tp, mp) ((void) 0)
@ -138,17 +139,21 @@ PUBLIC timer_t *tty_timers; /* queue of TTY timers */
PUBLIC clock_t tty_next_timeout; /* time that the next alarm is due */
PUBLIC struct machine machine; /* kernel environment variables */
extern PUBLIC unsigned info_location;
extern PUBLIC phys_bytes vid_size; /* 0x2000 for color or 0x0800 for mono */
extern PUBLIC phys_bytes vid_base;
/*===========================================================================*
* tty_task *
*===========================================================================*/
PUBLIC void main(void)
PUBLIC int main(void)
{
/* Main routine of the terminal task. */
message tty_mess; /* buffer for all incoming messages */
unsigned line;
int r, s;
register struct proc *rp;
register tty_t *tp;
/* Get kernel environment (protected_mode, pc_at and ega are needed). */
@ -162,9 +167,8 @@ PUBLIC void main(void)
/* Final one-time keyboard initialization. */
kb_init_once();
printf("\n");
while (TRUE) {
int adflag = 0;
/* Check for and handle any events on any of the ttys. */
for (tp = FIRST_TTY; tp < END_TTY; tp++) {
@ -212,14 +216,16 @@ PUBLIC void main(void)
continue;
}
case DIAGNOSTICS: /* a server wants to print some */
#if 0
if (tty_mess.m_source != LOG_PROC_NR)
{
printf("WARNING: old DIAGNOSTICS from %d\n",
tty_mess.m_source);
printf("[%d ", tty_mess.m_source);
}
#endif
do_diagnostics(&tty_mess, 0);
continue;
case DIAGNOSTICS_S:
case ASYN_DIAGNOSTICS:
do_diagnostics(&tty_mess, 1);
continue;
case GET_KMESS:
@ -299,6 +305,8 @@ PUBLIC void main(void)
tty_mess.IO_ENDPT, EINVAL);
}
}
return 0;
}
/*===========================================================================*
@ -397,7 +405,7 @@ register message *m_ptr; /* pointer to message sent to the task */
int safe; /* use safecopies? */
{
/* A process wants to read from a terminal. */
int r, status;
int r;
/* Check if there is already a process hanging in a read, check if the
* parameters are correct, do I/O.
@ -775,9 +783,6 @@ message *m_ptr; /* pointer to message sent to task */
if ((mode & W_BIT) && tp->tty_outleft != 0 && proc_nr == tp->tty_outproc &&
(!tp->tty_out_safe || tp->tty_out_vir_g==(vir_bytes)m_ptr->IO_GRANT)) {
/* Process was writing when killed. Clean up output. */
#if DEAD_CODE
(*tp->tty_ocancel)(tp, 0);
#endif
r = tp->tty_outcum > 0 ? tp->tty_outcum : EAGAIN;
tp->tty_outleft = tp->tty_outcum = tp->tty_outrevived = 0;
}
@ -849,9 +854,6 @@ tty_t *tp; /* TTY to check for events. */
* messages (in proc.c). This is handled by explicitly checking each line
* for fresh input and completed output on each interrupt.
*/
char *buf;
unsigned count;
int status;
do {
tp->tty_events = 0;
@ -989,7 +991,6 @@ int count; /* number of input characters */
int ch, sig, ct;
int timeset = FALSE;
static unsigned char csize_mask[] = { 0x1F, 0x3F, 0x7F, 0xFF };
for (ct = 0; ct < count; ct++) {
/* Take one character. */
@ -1373,7 +1374,7 @@ tty_t *tp;
* sure that an attribute change doesn't affect the processing of current
* output. Once output finishes the ioctl is executed as in do_ioctl().
*/
int result;
int result = EINVAL;
if (tp->tty_outleft > 0) return; /* output not finished */
@ -1535,8 +1536,6 @@ PRIVATE void tty_init()
register tty_t *tp;
int s;
struct sigaction sa;
char env[100];
/* Initialize the terminal lines. */
for (tp = FIRST_TTY,s=0; tp < END_TTY; tp++,s++) {
@ -1566,25 +1565,6 @@ PRIVATE void tty_init()
tp->tty_minor = s - (NR_CONS+NR_RS_LINES) + TTYPX_MINOR;
}
}
if(env_get_param("sticky_alt", env, sizeof(env)-1) == OK
&& atoi(env) == 1) {
sticky_alt_mode = 1;
}
#if DEAD_CODE
/* Install signal handlers. Ask PM to transform signal into message. */
sa.sa_handler = SIG_MESS;
sigemptyset(&sa.sa_mask);
sa.sa_flags = 0;
if (sigaction(SIGTERM,&sa,NULL)<0) panic("TTY","sigaction failed", errno);
if (sigaction(SIGKMESS,&sa,NULL)<0) panic("TTY","sigaction failed", errno);
if (sigaction(SIGKSTOP,&sa,NULL)<0) panic("TTY","sigaction failed", errno);
#endif
#if DEBUG
printf("end of tty_init\n");
#endif
}
/*===========================================================================*
@ -1670,6 +1650,7 @@ tty_t *tp;
int try;
{
/* Some functions need not be implemented at the device level. */
return 0;
}
/*===========================================================================*

View file

@ -1,8 +1,6 @@
/* tty.h - Terminals */
#include <timers.h>
#include "../../kernel/const.h"
#include "../../kernel/type.h"
#undef lock
#undef unlock
@ -115,8 +113,6 @@ extern unsigned long rs_irq_set;
extern int panicing; /* From panic.c in sysutil */
extern int sticky_alt_mode; /* right-alt sticky to switch codepages */
/* Values for the fields. */
#define NOT_ESCAPED 0 /* previous character is not LNEXT (^V) */
#define ESCAPED 1 /* previous character was LNEXT (^V) */

View file

@ -163,6 +163,7 @@ driver is
GETINFO # 26
SETGRANT # 34
;
uid 0;
};
driver pci
@ -217,7 +218,9 @@ driver mfs
TIMES # 25
SAFECOPYFROM # 31
SAFECOPYTO # 32
GETINFO
SETGRANT # 34
UMAP # 14
;
uid 0;
};

View file

@ -1 +1,3 @@
# which architecture to compile for
ARCH=i386

1
etc/rc
View file

@ -42,7 +42,6 @@ esac
case $action in
start)
echo ""
echo -n "Multiuser startup in progress ...:"
# National keyboard?

View file

@ -36,13 +36,15 @@
/* User-space processes, that is, device drivers, servers, and INIT. */
#define PM_PROC_NR 0 /* process manager */
#define FS_PROC_NR 1 /* file system */
#define RS_PROC_NR 2 /* reincarnation server */
#define VFS_PROC_NR FS_PROC_NR /* FS has been renamed to VFS. */
#define RS_PROC_NR 2 /* memory driver (RAM disk, null, etc.) */
#define MEM_PROC_NR 3 /* memory driver (RAM disk, null, etc.) */
#define LOG_PROC_NR 4 /* log device driver */
#define TTY_PROC_NR 5 /* terminal (TTY) driver */
#define DS_PROC_NR 6 /* data store server */
#define MFS_PROC_NR 7 /* minix root filesystem */
#define INIT_PROC_NR 8 /* init -- goes multiuser */
#define VM_PROC_NR 8 /* memory server */
#define INIT_PROC_NR 9 /* init -- goes multiuser */
/* Number of processes contained in the system image. */
#define NR_BOOT_PROCS (NR_TASKS + INIT_PROC_NR + 1)
@ -166,6 +168,7 @@
#define DEV_SCATTER_S (DEV_RQ_BASE + 22) /* (safecopy) write from a vector */
#define DEV_GATHER_S (DEV_RQ_BASE + 23) /* (safecopy) read into a vector */
#define DEV_IOCTL_S (DEV_RQ_BASE + 24) /* (safecopy) I/O control code */
#define DEV_MMAP_S (DEV_RQ_BASE + 25) /* (safecopy) mmap interface */
#define DEV_REPLY (DEV_RS_BASE + 0) /* general task reply */
#define DEV_CLONED (DEV_RS_BASE + 1) /* return cloned minor */
@ -309,7 +312,6 @@
# define SYS_ABORT (KERNEL_CALL + 27) /* sys_abort() */
# define SYS_IOPENABLE (KERNEL_CALL + 28) /* sys_enable_iop() */
# define SYS_VM_SETBUF (KERNEL_CALL + 29) /* sys_vm_setbuf() */
# define SYS_VM_MAP (KERNEL_CALL + 30) /* sys_vm_map() */
# define SYS_SAFECOPYFROM (KERNEL_CALL + 31) /* sys_safecopyfrom() */
# define SYS_SAFECOPYTO (KERNEL_CALL + 32) /* sys_safecopyto() */
# define SYS_VSAFECOPY (KERNEL_CALL + 33) /* sys_vsafecopy() */
@ -323,8 +325,9 @@
# define SYS_STIME (KERNEL_CALL + 39) /* sys_stime() */
# define SYS_MAPDMA (KERNEL_CALL + 42) /* sys_mapdma() */
# define SYS_VMCTL (KERNEL_CALL + 43) /* sys_vmctl() */
#define NR_SYS_CALLS 43 /* number of system calls */
#define NR_SYS_CALLS 44 /* number of system calls */
/* Pseudo call for use in kernel/table.c. */
#define SYS_ALL_CALLS (NR_SYS_CALLS)
@ -455,12 +458,18 @@
# define GET_LOADINFO 15 /* get load average information */
# define GET_IRQACTIDS 16 /* get the IRQ masks */
# define GET_PRIVID 17 /* get ID of privilege structure */
# define GET_HZ 18 /* get HZ value */
# define GET_WHOAMI 19 /* get own name and endpoint */
#define I_ENDPT m7_i4 /* calling process */
#define I_VAL_PTR m7_p1 /* virtual address at caller */
#define I_VAL_LEN m7_i1 /* max length of value */
#define I_VAL_PTR2 m7_p2 /* second virtual address */
#define I_VAL_LEN2_E m7_i2 /* second length, or proc nr */
/* GET_WHOAMI fields. */
#define GIWHO_EP m3_i1
#define GIWHO_NAME m3_ca1
/* Field names for SYS_TIMES. */
#define T_ENDPT m4_l1 /* process to request time info for */
#define T_USER_TIME m4_l1 /* user time consumed by process */
@ -514,10 +523,14 @@
#define PR_MEM_PTR m1_p1 /* tells where memory map is for sys_newmap
* and sys_fork
*/
#define PR_FORK_FLAGS m1_i3
/* Field names for SYS_INT86 */
#define INT86_REG86 m1_p1 /* pointer to registers */
/* Flags for PR_FORK_FLAGS. */
#define PFF_VMINHIBIT 0x01 /* Don't schedule until release by VM. */
/* Field names for SYS_SAFECOPY* */
#define SCP_FROM_TO m2_i1 /* from/to whom? */
#define SCP_INFO m2_i2 /* byte: DDDDSSSS Dest and Src seg */
@ -559,6 +572,26 @@
#define RDB_ADDR m2_l1
#define RDB_BUF m2_p1
/* Field names for SYS_VMCTL. */
#define SVMCTL_WHO m1_i1
#define SVMCTL_PARAM m1_i2 /* All SYS_VMCTL requests. */
#define SVMCTL_VALUE m1_i3
#define SVMCTL_PF_WHO m1_i1 /* GET_PAGEFAULT reply: process ep */
#define SVMCTL_PF_I386_CR2 m1_i2 /* GET_PAGEFAULT reply: CR2 */
#define SVMCTL_PF_I386_ERR m1_i3 /* GET_PAGEFAULT reply: error code */
#define SVMCTL_MRG_ADDR m1_p1 /* MEMREQ_GET reply: address */
#define SVMCTL_MRG_LEN m1_i1 /* MEMREQ_GET reply: length */
#define SVMCTL_MRG_WRITE m1_i2 /* MEMREQ_GET reply: writeflag */
#define SVMCTL_MRG_EP m1_i3 /* MEMREQ_GET reply: process */
/* Values for SVMCTL_PARAM. */
#define VMCTL_I386_SETCR3 10
#define VMCTL_GET_PAGEFAULT 11
#define VMCTL_CLEAR_PAGEFAULT 12
#define VMCTL_I386_GETCR3 13
#define VMCTL_MEMREQ_GET 14
#define VMCTL_MEMREQ_REPLY 15
/*===========================================================================*
* Messages for the Reincarnation Server *
*===========================================================================*/
@ -626,6 +659,7 @@
# define GETKM_PTR m1_p1
#define GET_KMESS_S (DIAG_BASE+4) /* get kmess from TTY */
# define GETKM_GRANT m1_i1
#define ASYN_DIAGNOSTICS (DIAG_BASE+5) /* grant-based, replyless DIAGNOSTICS */
#define DIAG_REPL (DIAG_BASE+0x80+0) /* reply to DIAGNOSTICS(_S) */
@ -695,6 +729,7 @@
* FS to update its uid and gid
* fields.
*/
#define EXC_NM_RF_FULLVM 4
/* Parameters for the EXEC_RESTART call */
#define EXC_RS_PROC m1_i1 /* process that needs to be restarted */
@ -704,4 +739,115 @@
* implementations. See <minix/vfsif.h>
*/
/* Requests sent by VM to VFS, done on behalf of a user process. */
#define VM_VFS_BASE 0xB00
#define VM_VFS_OPEN (VM_VFS_BASE+0) /* open() on behalf of user process. */
# define VMVO_NAME_GRANT m2_i1 /* 0-terminated */
# define VMVO_NAME_LENGTH m2_i2 /* name length including 0 */
# define VMVO_FLAGS m2_i3
# define VMVO_MODE m2_l1
# define VMVO_ENDPOINT m2_l2
#define VM_VFS_MMAP (VM_VFS_BASE+1) /* mmap() */
#define VM_VFS_CLOSE (VM_VFS_BASE+2) /* close() */
# define VMVC_FD m1_i1
# define VMVC_ENDPOINT m1_i2
/*===========================================================================*
* Messages for VM server *
*===========================================================================*/
#define VM_RQ_BASE 0xC00
/* Calls from PM */
#define VM_EXIT (VM_RQ_BASE+0)
# define VME_ENDPOINT m1_i1
#define VM_FORK (VM_RQ_BASE+1)
# define VMF_ENDPOINT m1_i1
# define VMF_SLOTNO m1_i2
# define VMF_CHILD_ENDPOINT m1_i3 /* result */
#define VM_BRK (VM_RQ_BASE+2)
# define VMB_ENDPOINT m1_i1
# define VMB_ADDR m1_p1
# define VMB_RETADDR m1_p2 /* result */
#define VM_EXEC_NEWMEM (VM_RQ_BASE+3)
# define VMEN_ENDPOINT m1_i1
# define VMEN_ARGSPTR m1_p1
# define VMEN_ARGSSIZE m1_i2
# define VMEN_FLAGS m1_i3 /* result */
# define VMEN_STACK_TOP m1_p2 /* result */
#define VM_PUSH_SIG (VM_RQ_BASE+4)
# define VMPS_ENDPOINT m1_i1
# define VMPS_OLD_SP m1_p1 /* result */
#define VM_WILLEXIT (VM_RQ_BASE+5)
# define VMWE_ENDPOINT m1_i1
/* General calls. */
#define VM_MMAP (VM_RQ_BASE+10)
# define VMM_ADDR m5_l1
# define VMM_LEN m5_l2
# define VMM_PROT m5_c1
# define VMM_FLAGS m5_c2
# define VMM_FD m5_i1
# define VMM_OFFSET m5_i2
# define VMM_RETADDR m5_l1 /* result */
#define VM_UMAP (VM_RQ_BASE+11)
# define VMU_SEG m1_i1
# define VMU_OFFSET m1_p1
# define VMU_LENGTH m1_p2
# define VMU_RETADDR m1_p3
/* to VM: inform VM about a region of memory that is used for
* bus-master DMA
*/
#define VM_ADDDMA (VM_RQ_BASE+12)
# define VMAD_REQ m2_i2
# define VMAD_EP m2_i1
# define VMAD_START m2_l1
# define VMAD_SIZE m2_l2
/* to VM: inform VM that a region of memory that is no longer
* used for bus-master DMA
*/
#define VM_DELDMA (VM_RQ_BASE+13)
# define VMDD_REQ m2_i2
# define VMDD_EP m2_i1
# define VMDD_START m2_l1
# define VMDD_SIZE m2_l2
/* to VM: ask VM for a region of memory that should not
* be used for bus-master DMA any longer
*/
#define VM_GETDMA (VM_RQ_BASE+14)
# define VMGD_REQ m2_i2
# define VMGD_PROCP m2_i1
# define VMGD_BASEP m2_l1
# define VMGD_SIZEP m2_l2
#define VM_MAP_PHYS (VM_RQ_BASE+15)
# define VMMP_EP m1_i1
# define VMMP_PHADDR m1_p2
# define VMMP_LEN m1_i2
# define VMMP_VADDR_REPLY m1_p3
#define VM_UNMAP_PHYS (VM_RQ_BASE+16)
# define VMUP_EP m1_i1
# define VMUP_VADDR m1_p1
#define VM_UNMAP (VM_RQ_BASE+17)
# define VMUM_ADDR m1_p1
# define VMUM_LEN m1_i1
#define VM_ALLOCMEM (VM_RQ_BASE+18)
# define VMAM_CLICKS m1_p1
# define VMAM_MEMBASE m1_i1
/* Calls from VFS. */
# define VMV_ENDPOINT m1_i1 /* for all VM_VFS_REPLY_* */
#define VM_VFS_REPLY_OPEN (VM_RQ_BASE+30)
# define VMVRO_FD m1_i2
#define VM_VFS_REPLY_MMAP (VM_RQ_BASE+31)
#define VM_VFS_REPLY_CLOSE (VM_RQ_BASE+32)
/* Total. */
#define VM_NCALLS 33
#endif /* _MINIX_COM_H */

View file

@ -39,45 +39,9 @@
#define NR_PROCS _NR_PROCS
#define NR_SYS_PROCS _NR_SYS_PROCS
#if _MINIX_SMALL
#define NR_BUFS 100
#define NR_BUF_HASH 128
#else
/* The buffer cache should be made as large as you can afford. */
#if (MACHINE == IBM_PC && _WORD_SIZE == 2)
#define NR_BUFS 40 /* # blocks in the buffer cache */
#define NR_BUF_HASH 64 /* size of buf hash table; MUST BE POWER OF 2*/
#endif
#if (MACHINE == IBM_PC && _WORD_SIZE == 4)
#define NR_BUFS 1200 /* # blocks in the buffer cache */
#define NR_BUF_HASH 2048 /* size of buf hash table; MUST BE POWER OF 2*/
#endif
#if (MACHINE == SUN_4_60)
#define NR_BUFS 512 /* # blocks in the buffer cache (<=1536) */
#define NR_BUF_HASH 512 /* size of buf hash table; MUST BE POWER OF 2*/
#endif
#endif /* _MINIX_SMALL */
/* Number of controller tasks (/dev/cN device classes). */
#define NR_CTRLRS 2
/* Enable or disable the second level file system cache on the RAM disk. */
#define ENABLE_CACHE2 0
/* Enable or disable swapping processes to disk. */
#define ENABLE_SWAP 0
/* Include or exclude an image of /dev/boot in the boot image.
* Please update the makefile in /usr/src/tools/ as well.
*/
#define ENABLE_BOOTDEV 0 /* load image of /dev/boot at boot time */
/* DMA_SECTORS may be increased to speed up DMA based drivers. */
#define DMA_SECTORS 1 /* DMA buffer size (must be >= 1) */

View file

@ -11,7 +11,7 @@
#define TRUE 1 /* used for turning integers into Booleans */
#define FALSE 0 /* used for turning integers into Booleans */
#define HZ 60 /* clock freq (software settable on IBM-PC) */
#define HZ 600 /* clock freq (software settable on IBM-PC) */
#define SUPER_USER (uid_t) 0 /* uid_t of superuser */
@ -19,7 +19,7 @@
#define CPVEC_NR 16 /* max # of entries in a SYS_VCOPY request */
#define CPVVEC_NR 64 /* max # of entries in a SYS_VCOPY request */
#define SCPVEC_NR 64 /* max # of entries in a SYS_VSAFECOPY* request */
#define NR_IOREQS MIN(NR_BUFS, 64)
#define NR_IOREQS 64
/* maximum number of entries in an iorequest */
/* Message passing constants. */
@ -46,6 +46,12 @@
#define GRANT_SEG 0x0800 /* flag indicating grant for umap */
#define LOCAL_VM_SEG 0x1000 /* same as LOCAL_SEG, but with vm lookup */
#define VM_D (LOCAL_VM_SEG | D)
#define VM_T (LOCAL_VM_SEG | T)
#define MEM_GRANT 3
#define VM_GRANT (LOCAL_VM_SEG | MEM_GRANT)
/* Labels used to disable code sections for different reasons. */
#define DEAD_CODE 0 /* unused code in normal configuration */
#define FUTURE_CODE 0 /* new code to be activated + tested later */
@ -77,6 +83,13 @@
#define CLICK_SHIFT 12 /* log2 of CLICK_SIZE */
#endif
/* Sizes of memory tables. The boot monitor distinguishes three memory areas,
* namely low mem below 1M, 1M-16M, and mem after 16M. More chunks are needed
* for DOS MINIX.
*/
#define NR_MEMS 8
/* Click to byte conversions (and vice versa). */
#define HCLICK_SHIFT 4 /* log2 of HCLICK_SIZE */
#define HCLICK_SIZE 16 /* hardware segment conversion magic */
@ -108,8 +121,6 @@
#define I_NOT_ALLOC 0000000 /* this inode is free */
/* Some limits. */
#define MAX_BLOCK_NR ((block_t) 077777777) /* largest block number */
#define HIGHEST_ZONE ((zone_t) 077777777) /* largest zone number */
#define MAX_INODE_NR ((ino_t) 037777777777) /* largest inode number */
#define MAX_FILE_POS ((off_t) 0x7FFFFFFF) /* largest legal file offset */

View file

@ -29,8 +29,8 @@ typedef struct { u16_t port; u32_t value; } pvl_pair_t;
(pv).port = _p; \
(pv).value = _v; \
if((pv).port != _p || (pv).value != _v) { \
printf("%s:%d: actual port: %x != %x || " \
"actual value: %x != %x\n", \
printf("%s:%d: actual port: 0x%x != 0x%lx || " \
"actual value: 0x%x != 0x%lx\n", \
__FILE__, __LINE__, (pv).port, _p, (pv).value, _v); \
panic(__FILE__, "pv_set(" #pv ", " #p ", " #v ")", NO_NUM); \
} \

View file

@ -1,6 +1,8 @@
#ifndef _IPC_H
#define _IPC_H
#include <minix/type.h>
/*==========================================================================*
* Types relating to messages. *
*==========================================================================*/

View file

@ -20,7 +20,6 @@
#define _NR_PROCS 100
#define _NR_SYS_PROCS 32
#define _NR_HOLES (2*_NR_PROCS+4) /* No. of memory holes maintained by PM */
/* Set the CHIP type based on the machine selected. The symbol CHIP is actually
* indicative of more than just the CPU. For example, machines for which
@ -71,4 +70,6 @@ error "_MINIX_MACHINE has incorrect value (0)"
/* Kernel debug checks */
#define DEBUG_LOCK_CHECK 1 /* Interrupt Lock/unlock sanity checking. */
#define _KMESS_BUF_SIZE 30000
#endif /* _MINIX_SYS_CONFIG_H */

View file

@ -34,7 +34,8 @@ _PROTOTYPE( int sys_abort, (int how, ...));
_PROTOTYPE( int sys_enable_iop, (endpoint_t proc));
_PROTOTYPE( int sys_exec, (endpoint_t proc, char *ptr,
char *aout, vir_bytes initpc));
_PROTOTYPE( int sys_fork, (int parent, int child, int *, struct mem_map *ptr));
_PROTOTYPE( int sys_fork, (endpoint_t parent, endpoint_t child, int *,
struct mem_map *ptr, u32_t vm));
_PROTOTYPE( int sys_newmap, (endpoint_t proc, struct mem_map *ptr));
_PROTOTYPE( int sys_exit, (endpoint_t proc));
_PROTOTYPE( int sys_trace, (int req, endpoint_t proc, long addr, long *data_p));
@ -48,6 +49,13 @@ _PROTOTYPE( int sys_vm_setbuf, (phys_bytes base, phys_bytes size,
phys_bytes high));
_PROTOTYPE( int sys_vm_map, (endpoint_t proc_nr, int do_map,
phys_bytes base, phys_bytes size, phys_bytes offset));
_PROTOTYPE( int sys_vmctl, (endpoint_t who, int param, u32_t value));
_PROTOTYPE( int sys_vmctl_get_pagefault_i386, (endpoint_t *who, u32_t *cr2, u32_t *err));
_PROTOTYPE( int sys_vmctl_get_cr3_i386, (endpoint_t who, u32_t *cr3) );
_PROTOTYPE( int sys_vmctl_get_memreq, (endpoint_t *who, vir_bytes *mem,
vir_bytes *len, int *wrflag) );
_PROTOTYPE( int sys_readbios, (phys_bytes address, void *buf, size_t size));
_PROTOTYPE( int sys_stime, (time_t boottime));
@ -71,6 +79,9 @@ _PROTOTYPE( int sys_stime, (time_t boottime));
sys_sdevio(DIO_SAFE_OUTPUT_WORD, port, ept, (void*)grant, count, offset)
_PROTOTYPE( int sys_sdevio, (int req, long port, endpoint_t proc_nr,
void *buffer, int count, vir_bytes offset));
_PROTOTYPE(void *alloc_contig, (size_t len, int flags, phys_bytes *phys));
#define AC_ALIGN4K 0x01
#define AC_LOWER16M 0x02
/* Clock functionality: get system times or (un)schedule an alarm call. */
_PROTOTYPE( int sys_times, (endpoint_t proc_nr, clock_t *user_time,
@ -128,6 +139,8 @@ _PROTOTYPE(int sys_physvcopy, (phys_cp_req *vec_ptr,int vec_size,int *nr_ok));
_PROTOTYPE(int sys_umap, (endpoint_t proc_nr, int seg, vir_bytes vir_addr,
vir_bytes bytes, phys_bytes *phys_addr));
_PROTOTYPE(int sys_umap_data_fb, (endpoint_t proc_nr, vir_bytes vir_addr,
vir_bytes bytes, phys_bytes *phys_addr));
_PROTOTYPE(int sys_segctl, (int *index, u16_t *seg, vir_bytes *off,
phys_bytes phys, vir_bytes size));
@ -151,6 +164,7 @@ _PROTOTYPE(int sys_segctl, (int *index, u16_t *seg, vir_bytes *off,
#define sys_getprivid(nr) sys_getinfo(GET_PRIVID, 0, 0,0, nr)
_PROTOTYPE(int sys_getinfo, (int request, void *val_ptr, int val_len,
void *val_ptr2, int val_len2) );
_PROTOTYPE(int sys_whoami, (endpoint_t *ep, char *name, int namelen));
/* Signal control. */
_PROTOTYPE(int sys_kill, (endpoint_t proc, int sig) );

View file

@ -1,6 +1,8 @@
#ifndef _MINIX_SYSUTIL_H
#define _MINIX_SYSUTIL_H 1
#include <minix/ipc.h>
/* Extra system library definitions to support device drivers and servers.
*
* Created:
@ -48,9 +50,15 @@ _PROTOTYPE( int getuptime, (clock_t *ticks));
_PROTOTYPE( int getuptime2, (clock_t *ticks, time_t *boottime));
_PROTOTYPE( int tickdelay, (clock_t ticks));
_PROTOTYPE( int micro_delay_calibrate, (void));
_PROTOTYPE( u32_t sys_hz, (void));
_PROTOTYPE( void util_stacktrace, (void));
_PROTOTYPE( void util_nstrcat, (char *str, unsigned long n) );
_PROTOTYPE( void util_stacktrace_strcat, (char *));
_PROTOTYPE( int micro_delay, (u32_t micros));
_PROTOTYPE( u32_t micros_to_ticks, (u32_t micros));
_PROTOTYPE( int asynsend, (endpoint_t ep, message *msg));
#define MICROS_TO_TICKS(m) (((m)*HZ/1000000)+1)
#define ASSERT(c) if(!(c)) { panic(__FILE__, "assert " #c " failed at line", __LINE__); }
#endif /* _MINIX_SYSUTIL_H */

28
include/minix/tty.h Normal file
View file

@ -0,0 +1,28 @@
#ifndef _MINIX_TTY_H
#define _MINIX_TTY_H
#include <sys/types.h>
#define TTYMAGIC 0xb105
/* A struct that the tty driver can use to pass values to the boot monitor.
* Currently only the value of the origin of the first vty (console), so the
* boot monitor can properly display it when panicing (tty isn't scheduled
* to switch to the first vty). It's written at the end of video memory
* (video memory base + video memory size - sizeof(struct boot_tty_info).
*/
struct boot_tty_info {
u16_t reserved[30]; /* reserved, set to 0 */
u16_t consorigin; /* origin in video memory of console */
u16_t conscursor; /* position of cursor of console */
u16_t flags; /* flags indicating which fields are valid */
u16_t magic; /* magic number indicating struct is valid */
};
#define BTIF_CONSORIGIN 0x01 /* consorigin is set */
#define BTIF_CONSCURSOR 0x02 /* conscursor is set */
#endif

View file

@ -16,7 +16,7 @@ typedef unsigned int phys_clicks; /* physical addr/length in clicks */
typedef int endpoint_t; /* process identifier */
#if (_MINIX_CHIP == _CHIP_INTEL)
typedef unsigned int vir_bytes; /* virtual addresses and lengths in bytes */
typedef long unsigned int vir_bytes; /* virtual addresses/lengths in bytes */
#endif
#if (_MINIX_CHIP == _CHIP_M68000)
@ -48,19 +48,6 @@ struct vir_addr {
vir_bytes offset;
};
/* Memory allocation by PM. */
struct hole {
struct hole *h_next; /* pointer to next entry on the list */
phys_clicks h_base; /* where does the hole begin? */
phys_clicks h_len; /* how big is the hole? */
};
/* Memory info from PM. */
struct pm_mem_info {
struct hole pmi_holes[_NR_HOLES];/* memory (un)allocations */
u32_t pmi_hi_watermark; /* highest ever-used click + 1 */
};
#define phys_cp_req vir_cp_req
struct vir_cp_req {
struct vir_addr src;
@ -98,14 +85,14 @@ struct kinfo {
phys_bytes data_base; /* base of kernel data */
phys_bytes data_size;
vir_bytes proc_addr; /* virtual address of process table */
phys_bytes kmem_base; /* kernel memory layout (/dev/kmem) */
phys_bytes kmem_size;
phys_bytes _kmem_base; /* kernel memory layout (/dev/kmem) */
phys_bytes _kmem_size;
phys_bytes bootdev_base; /* boot device from boot image (/dev/boot) */
phys_bytes bootdev_size;
phys_bytes ramdev_base; /* boot device from boot image (/dev/boot) */
phys_bytes ramdev_size;
phys_bytes params_base; /* parameters passed by boot monitor */
phys_bytes params_size;
phys_bytes _params_base; /* parameters passed by boot monitor */
phys_bytes _params_size;
int nr_procs; /* number of user processes */
int nr_tasks; /* number of kernel tasks */
char release[6]; /* kernel release number */
@ -176,4 +163,21 @@ struct memory {
phys_bytes size;
};
#define STATICINIT(v, n) \
if(!(v)) { \
phys_bytes myph; \
if(!((v) = alloc_contig(sizeof(*(v)) * (n), 0, &myph))) { \
panic(__FILE__, "allocating " #v " failed", n); \
} \
}
/* The kernel outputs diagnostic messages in a circular buffer. */
struct kmessages {
int km_next; /* next index to write */
int km_size; /* current size in buffer */
char km_buf[_KMESS_BUF_SIZE]; /* buffer for messages */
};
#endif /* _TYPE_H */

29
include/minix/vm.h Executable file
View file

@ -0,0 +1,29 @@
/* Prototypes and definitions for VM interface. */
#ifndef _MINIX_VM_H
#define _MINIX_VM_H
#include <sys/types.h>
#include <minix/endpoint.h>
_PROTOTYPE( int vm_exit, (endpoint_t ep));
_PROTOTYPE( int vm_fork, (endpoint_t ep, int slotno, int *child_ep));
_PROTOTYPE( int vm_brk, (endpoint_t ep, char *newaddr));
_PROTOTYPE( int vm_exec_newmem, (endpoint_t ep, struct exec_newmem *args,
int args_bytes, char **ret_stack_top, int *ret_flags));
_PROTOTYPE( int vm_push_sig, (endpoint_t ep, vir_bytes *old_sp));
_PROTOTYPE( int vm_willexit, (endpoint_t ep));
_PROTOTYPE( int vm_adddma, (endpoint_t req_e, endpoint_t proc_e,
phys_bytes start, phys_bytes size) );
_PROTOTYPE( int vm_deldma, (endpoint_t req_e, endpoint_t proc_e,
phys_bytes start, phys_bytes size) );
_PROTOTYPE( int vm_getdma, (endpoint_t req_e, endpoint_t *procp,
phys_bytes *basep, phys_bytes *sizep) );
_PROTOTYPE( void *vm_map_phys, (endpoint_t who, size_t len, void *physaddr));
_PROTOTYPE( int vm_unmap_phys, (endpoint_t who, void *vaddr, size_t len));
_PROTOTYPE( int vm_allocmem, (phys_clicks memclicks, phys_clicks *retmembase));
#endif /* _MINIX_VM_H */

View file

@ -36,4 +36,8 @@
#define KIOCSLEDS _IOW('k', 2, struct kio_leds)
#define KIOCSMAP _IOW('k', 3, keymap_t)
/* /dev/video ioctls. */
#define TIOCMAPMEM _IORW('v', 1, struct mapreqvm)
#define TIOCUNMAPMEM _IORW('v', 2, struct mapreqvm)
#endif /* _S_I_TTY_H */

29
include/sys/mman.h Executable file
View file

@ -0,0 +1,29 @@
#ifndef _MMAN_H
#define _MMAN_H
#ifndef _TYPES_H
#include <sys/types.h>
#endif
/* prot argument for mmap() */
#define PROT_NONE 0x00 /* no permissions */
#define PROT_READ 0x01 /* pages can be read */
#define PROT_WRITE 0x02 /* pages can be written */
#define PROT_EXEC 0x04 /* pages can be executed */
/* flags argument for mmap() */
#define MAP_SHARED 0x0001 /* share changes */
#define MAP_PRIVATE 0x0002 /* changes are private */
#define MAP_ANON 0x0004 /* anonymous memory */
#define MAP_PREALLOC 0x0008 /* not on-demand */
#define MAP_CONTIG 0x0010 /* contiguous in physical memory */
#define MAP_LOWER16M 0x0020 /* physically below 16MB */
/* mmap() error return */
#define MAP_FAILED ((void *)-1)
_PROTOTYPE( void *mmap, (void *, size_t, int, int, int, off_t));
_PROTOTYPE( int munmap, (void *, size_t));
#endif /* _MMAN_H */

39
include/sys/video.h Normal file
View file

@ -0,0 +1,39 @@
#ifndef _SYS_VIDEO_H
#define _SYS_VIDEO_H 1
/* Definitions used by the console driver. */
#define MONO_BASE 0xB0000L /* base of mono video memory */
#define COLOR_BASE 0xB8000L /* base of color video memory */
#define MONO_SIZE 0x1000 /* 4K mono video memory */
#define COLOR_SIZE 0x4000 /* 16K color video memory */
#define EGA_SIZE 0x8000 /* EGA & VGA have at least 32K */
#define BLANK_COLOR 0x0700 /* determines cursor color on blank screen */
#define SCROLL_UP 0 /* scroll forward */
#define SCROLL_DOWN 1 /* scroll backward */
#define BLANK_MEM ((u16_t *) 0) /* tells mem_vid_copy() to blank the screen */
#define CONS_RAM_WORDS 80 /* video ram buffer size */
#define MAX_ESC_PARMS 4 /* number of escape sequence params allowed */
/* Constants relating to the controller chips. */
#define M_6845 0x3B4 /* port for 6845 mono */
#define C_6845 0x3D4 /* port for 6845 color */
#define INDEX 0 /* 6845's index register */
#define DATA 1 /* 6845's data register */
#define STATUS 6 /* 6845's status register */
#define VID_ORG 12 /* 6845's origin register */
#define CURSOR 14 /* 6845's cursor register */
/* Beeper. */
#define BEEP_FREQ 0x0533 /* value to put into timer to set beep freq */
#define B_TIME 3 /* length of CTRL-G beep is ticks */
/* definitions used for font management */
#define GA_SEQUENCER_INDEX 0x3C4
#define GA_SEQUENCER_DATA 0x3C5
#define GA_GRAPHICS_INDEX 0x3CE
#define GA_GRAPHICS_DATA 0x3CF
#define GA_VIDEO_ADDRESS 0xA0000L
#define GA_FONT_SIZE 8192
#endif

View file

@ -2,8 +2,6 @@
sys/vm.h
*/
#define PAGE_SIZE 4096
/* MIOCMAP */
struct mapreq
{
@ -13,18 +11,14 @@ struct mapreq
int readonly;
};
/* i386 paging constants */
#define I386_VM_PRESENT 0x001 /* Page is present */
#define I386_VM_WRITE 0x002 /* Read/write access allowed */
#define I386_VM_USER 0x004 /* User access allowed */
#define I386_VM_PWT 0x008 /* Write through */
#define I386_VM_PCD 0x010 /* Cache disable */
#define I386_VM_ADDR_MASK 0xFFFFF000 /* physical address */
#define I386_VM_PT_ENT_SIZE 4 /* Size of a page table entry */
#define I386_VM_DIR_ENTRIES 1024 /* Number of entries in a page dir */
#define I386_VM_DIR_ENT_SHIFT 22 /* Shift to get entry in page dir. */
#define I386_VM_PT_ENT_SHIFT 12 /* Shift to get entry in page table */
#define I386_VM_PT_ENT_MASK 0x3FF /* Mask to get entry in page table */
#define I386_CR0_PG 0x80000000 /* Enable paging */
/* MIOCMAPVM */
struct mapreqvm
{
int flags; /* reserved, must be 0 */
off_t phys_offset;
size_t size;
int readonly;
char reserved[40]; /* reserved, must be 0 */
void *vaddr_ret; /* result vaddr */
};

45
include/sys/vm_i386.h Normal file
View file

@ -0,0 +1,45 @@
/*
sys/vm_i386.h
*/
#define I386_PAGE_SIZE 4096
/* i386 paging constants */
#define I386_VM_PRESENT 0x001 /* Page is present */
#define I386_VM_WRITE 0x002 /* Read/write access allowed */
#define I386_VM_USER 0x004 /* User access allowed */
#define I386_VM_PWT 0x008 /* Write through */
#define I386_VM_PCD 0x010 /* Cache disable */
#define I386_VM_ACC 0x020 /* Accessed */
#define I386_VM_ADDR_MASK 0xFFFFF000 /* physical address */
/* Page directory specific flags. */
#define I386_VM_BIGPAGE 0x080 /* 4MB page */
/* Page table specific flags. */
#define I386_VM_DIRTY 0x040 /* Dirty */
#define I386_VM_PTAVAIL1 0x080 /* Available for use. */
#define I386_VM_PTAVAIL2 0x100 /* Available for use. */
#define I386_VM_PT_ENT_SIZE 4 /* Size of a page table entry */
#define I386_VM_DIR_ENTRIES 1024 /* Number of entries in a page dir */
#define I386_VM_DIR_ENT_SHIFT 22 /* Shift to get entry in page dir. */
#define I386_VM_PT_ENT_SHIFT 12 /* Shift to get entry in page table */
#define I386_VM_PT_ENT_MASK 0x3FF /* Mask to get entry in page table */
#define I386_VM_PT_ENTRIES 1024 /* Number of entries in a page table */
#define I386_VM_PFA_SHIFT 22 /* Page frame address shift */
#define I386_CR0_PG 0x80000000 /* Enable paging */
/* i386 paging 'functions' */
#define I386_VM_PTE(v) (((v) >> I386_VM_PT_ENT_SHIFT) & I386_VM_PT_ENT_MASK)
#define I386_VM_PDE(v) ( (v) >> I386_VM_DIR_ENT_SHIFT)
#define I386_VM_PFA(e) ( (e) & I386_VM_ADDR_MASK)
#define I386_VM_PAGE(v) ( (v) >> I386_VM_PFA_SHIFT)
/* i386 pagefault error code bits */
#define I386_VM_PFE_P 0x01 /* Pagefault caused by non-present page.
* (otherwise protection violation.)
*/
#define I386_VM_PFE_W 0x02 /* Caused by write (otherwise read) */
#define I386_VM_PFE_U 0x04 /* CPU in user mode (otherwise supervisor) */

View file

@ -9,7 +9,7 @@
#ifndef _TIME_H
#define _TIME_H
#define CLOCKS_PER_SEC 60 /* MINIX always uses 60 Hz, even in Europe */
#define CLOCKS_PER_SEC 60
#ifdef _POSIX_SOURCE
#define CLK_TCK CLOCKS_PER_SEC /* obsolescent mame for CLOCKS_PER_SEC */

View file

@ -1,3 +1,6 @@
#ifndef _INCLUDE_TOOLS_H
#define _INCLUDE_TOOLS_H 1
/* Constants describing the disk */
#define SECTOR_SIZE 512
#define SECTOR_SHIFT 9
@ -121,3 +124,4 @@ _PROTOTYPE( void relocate, (void));
_PROTOTYPE( int writesectors, (int _off, int _seg, off_t _adr, int _ct));
#endif
#endif

View file

@ -18,21 +18,20 @@ CFLAGS=$(CPROFILE) $(CPPFLAGS) $(EXTRA_OPTS)
LDFLAGS=-i
# first-stage, arch-dependent startup code
HEAD = head.o
FULLHEAD = $a/$(HEAD)
HEAD = $a/mpx386.o
OBJS = start.o table.o main.o proc.o \
system.o clock.o utility.o debug.o profile.o interrupt.o
SYSTEM = system.a
ARCHLIB = $a/$(ARCH).a
LIBS = -ltimers -lsysutil
LIBS = -ltimers -lsys
# What to make.
all: build
kernel build install: $(HEAD) $(OBJS)
kernel build install: $(OBJS)
cd system && $(MAKE) $@
cd $a && $(MAKE) $@
$(LD) $(CFLAGS) $(LDFLAGS) -o kernel $(FULLHEAD) $(OBJS) \
$(LD) $(CFLAGS) $(LDFLAGS) -o kernel $(HEAD) $(OBJS) \
$(SYSTEM) $(ARCHLIB) $(LIBS)
install -S 0 kernel
@ -50,8 +49,5 @@ depend:
.c.o:
$(CC) $(CFLAGS) -c -o $@ $<
$(HEAD):
cd $a && make HEAD=$(HEAD) $(HEAD)
# Include generated dependencies.
include .depend

View file

@ -8,17 +8,19 @@ ARCHAR=$(ARCH).a
# the HEAD variable is passed as an argument to this Makefile
# by an upper level Makefile.
OBJS=$(ARCHAR)(exception.o) \
$(ARCHAR)(i8259.o) \
$(ARCHAR)(memory.o) \
$(ARCHAR)(protect.o) \
$(ARCHAR)(system.o) \
$(ARCHAR)(clock.o) \
$(ARCHAR)(klib386.o) \
$(ARCHAR)(do_readbios.o) \
$(ARCHAR)(do_int86.o) \
$(ARCHAR)(do_sdevio.o) \
$(ARCHAR)(do_iopenable.o)
OBJS= arch_do_vmctl.o \
clock.o \
do_int86.o \
do_iopenable.o \
do_readbios.o \
do_sdevio.o \
exception.o \
i8259.o \
klib386.o \
memory.o \
mpx386.o \
protect.o \
system.o
CPPFLAGS=-Iinclude
CFLAGS=$(CPPFLAGS) -Wall
@ -56,6 +58,9 @@ $(ARCHAR)(do_int86.o): do_int86.c
$(ARCHAR)(do_iopenable.o): do_iopenable.c
$(CC) $(CFLAGS) -c $<
$(ARCHAR)(arch_do_vmctl.o): arch_do_vmctl.c
$(CC) $(CFLAGS) -c $<
$(ARCHAR)(do_readbios.o): do_readbios.c
$(CC) $(CFLAGS) -c $<

View file

@ -0,0 +1,56 @@
/* The kernel call implemented in this file:
* m_type: SYS_VMCTL
*
* The parameters for this kernel call are:
* SVMCTL_WHO which process
* SVMCTL_PARAM set this setting (VMCTL_*)
* SVMCTL_VALUE to this value
*/
#include "../../system.h"
#include <minix/type.h>
extern u32_t kernel_cr3;
/*===========================================================================*
* arch_do_vmctl *
*===========================================================================*/
PUBLIC int arch_do_vmctl(m_ptr, p)
register message *m_ptr; /* pointer to request message */
struct proc *p;
{
switch(m_ptr->SVMCTL_PARAM) {
case VMCTL_I386_GETCR3:
/* Get process CR3. */
m_ptr->SVMCTL_VALUE = p->p_seg.p_cr3;
return OK;
case VMCTL_I386_SETCR3:
/* Set process CR3. */
if(m_ptr->SVMCTL_VALUE) {
p->p_seg.p_cr3 = m_ptr->SVMCTL_VALUE;
p->p_misc_flags |= MF_FULLVM;
} else {
p->p_seg.p_cr3 = kernel_cr3;
p->p_misc_flags &= ~MF_FULLVM;
}
RTS_LOCK_UNSET(p, VMINHIBIT);
return OK;
case VMCTL_GET_PAGEFAULT:
{
struct proc *rp;
if(!(rp=pagefaults))
return ESRCH;
pagefaults = rp->p_nextpagefault;
if(!RTS_ISSET(rp, PAGEFAULT))
minix_panic("non-PAGEFAULT process on pagefault chain",
rp->p_endpoint);
m_ptr->SVMCTL_PF_WHO = rp->p_endpoint;
m_ptr->SVMCTL_PF_I386_CR2 = rp->p_pagefault.pf_virtual;
m_ptr->SVMCTL_PF_I386_ERR = rp->p_pagefault.pf_flags;
return OK;
}
}
kprintf("arch_do_vmctl: strange param %d\n", m_ptr->SVMCTL_PARAM);
return EINVAL;
}

View file

@ -21,28 +21,23 @@ struct reg86u reg86;
PUBLIC int do_int86(m_ptr)
register message *m_ptr; /* pointer to request message */
{
vir_bytes caller_vir;
phys_bytes caller_phys, kernel_phys;
caller_vir = (vir_bytes) m_ptr->INT86_REG86;
caller_phys = umap_local(proc_addr(who_p), D, caller_vir, sizeof(reg86));
if (0 == caller_phys) return(EFAULT);
kernel_phys = vir2phys(&reg86);
phys_copy(caller_phys, kernel_phys, (phys_bytes) sizeof(reg86));
data_copy(who_e, (vir_bytes) m_ptr->INT86_REG86,
SYSTEM, (vir_bytes) &reg86, sizeof(reg86));
level0(int86);
/* Copy results back to the caller */
phys_copy(kernel_phys, caller_phys, (phys_bytes) sizeof(reg86));
data_copy(SYSTEM, (vir_bytes) &reg86,
who_e, (vir_bytes) m_ptr->INT86_REG86, sizeof(reg86));
/* The BIOS call eats interrupts. Call get_randomness to generate some
* entropy. Normally, get_randomness is called from an interrupt handler.
* Figuring out the exact source is too complicated. CLOCK_IRQ is normally
* not very random.
*/
lock(0, "do_int86");
lock;
get_randomness(CLOCK_IRQ);
unlock(0);
unlock;
return(OK);
}

View file

@ -16,24 +16,14 @@
PUBLIC int do_readbios(m_ptr)
register message *m_ptr; /* pointer to request message */
{
int proc_nr;
struct proc *p;
phys_bytes address, phys_buf, phys_bios;
vir_bytes buf;
size_t size;
struct vir_addr src, dst;
src.segment = BIOS_SEG;
dst.segment = D;
src.offset = m_ptr->RDB_ADDR;
dst.offset = (vir_bytes) m_ptr->RDB_BUF;
src.proc_nr_e = NONE;
dst.proc_nr_e = m_ptr->m_source;
address = m_ptr->RDB_ADDR;
buf = (vir_bytes)m_ptr->RDB_BUF;
size = m_ptr->RDB_SIZE;
okendpt(m_ptr->m_source, &proc_nr);
p = proc_addr(proc_nr);
phys_buf = umap_local(p, D, buf, size);
if (phys_buf == 0)
return EFAULT;
phys_bios = umap_bios(p, address, size);
if (phys_bios == 0)
return EPERM;
phys_copy(phys_bios, phys_buf, size);
return 0;
return virtual_copy_vmcheck(&src, &dst, m_ptr->RDB_SIZE);
}

View file

@ -77,7 +77,7 @@ register message *m_ptr; /* pointer to request message */
return EPERM;
}
/* Get and check physical address. */
if ((phys_buf = numap_local(proc_nr,
if ((phys_buf = umap_virtual(proc_addr(proc_nr), D,
(vir_bytes) m_ptr->DIO_VEC_ADDR, count)) == 0)
return(EFAULT);
}

View file

@ -6,8 +6,66 @@
#include "../../kernel.h"
#include "proto.h"
#include <signal.h>
#include <stdio.h>
#include <string.h>
#include <minix/sysutil.h>
#include "../../proc.h"
extern int vm_copy_in_progress;
extern struct proc *vm_copy_from, *vm_copy_to;
extern u32_t vm_copy_from_v, vm_copy_to_v;
extern u32_t vm_copy_from_p, vm_copy_to_p, vm_copy_cr3;
u32_t pagefault_cr2, pagefault_count = 0;
void pagefault(struct proc *pr, int trap_errno)
{
int s;
vir_bytes ph;
u32_t pte;
if(pagefault_count != 1)
minix_panic("recursive pagefault", pagefault_count);
/* Don't schedule this process until pagefault is handled. */
if(RTS_ISSET(pr, PAGEFAULT))
minix_panic("PAGEFAULT set", pr->p_endpoint);
RTS_LOCK_SET(pr, PAGEFAULT);
if(pr->p_endpoint <= INIT_PROC_NR) {
/* Page fault we can't / don't want to
* handle.
*/
kprintf("pagefault for process %d ('%s'), pc = 0x%x\n",
pr->p_endpoint, pr->p_name, pr->p_reg.pc);
proc_stacktrace(pr);
minix_panic("page fault in system process", pr->p_endpoint);
return;
}
/* Save pagefault details, suspend process,
* add process to pagefault chain,
* and tell VM there is a pagefault to be
* handled.
*/
pr->p_pagefault.pf_virtual = pagefault_cr2;
pr->p_pagefault.pf_flags = trap_errno;
pr->p_nextpagefault = pagefaults;
pagefaults = pr;
lock_notify(HARDWARE, VM_PROC_NR);
pagefault_count = 0;
#if 0
kprintf("pagefault for process %d ('%s'), pc = 0x%x\n",
pr->p_endpoint, pr->p_name, pr->p_reg.pc);
proc_stacktrace(pr);
#endif
return;
}
/*===========================================================================*
* exception *
*===========================================================================*/
@ -62,8 +120,13 @@ u32_t old_eflags;
* k_reenter larger than zero.
*/
if (k_reenter == 0 && ! iskernelp(saved_proc)) {
#if 0
{
switch(vec_nr) {
case PAGE_FAULT_VECTOR:
pagefault(saved_proc, trap_errno);
return;
}
kprintf(
"exception for process %d, endpoint %d ('%s'), pc = 0x%x:0x%x, sp = 0x%x:0x%x\n",
proc_nr(saved_proc), saved_proc->p_endpoint,
@ -75,12 +138,11 @@ u32_t old_eflags;
vec_nr, (unsigned long)trap_errno,
(unsigned long)old_eip, old_cs,
(unsigned long)old_eflags);
#if DEBUG_STACKTRACE
stacktrace(saved_proc);
#endif
proc_stacktrace(saved_proc);
}
#endif
kprintf("kernel: cause_sig %d for %d\n",
ep->signum, saved_proc->p_endpoint);
cause_sig(proc_nr(saved_proc), ep->signum);
return;
}
@ -92,43 +154,45 @@ u32_t old_eflags;
kprintf("\n%s\n", ep->msg);
kprintf("k_reenter = %d ", k_reenter);
kprintf("process %d (%s), ", proc_nr(saved_proc), saved_proc->p_name);
kprintf("pc = %u:0x%x", (unsigned) saved_proc->p_reg.cs,
(unsigned) saved_proc->p_reg.pc);
kprintf("pc = %u:0x%x\n", (unsigned) saved_proc->p_reg.cs,
(unsigned) saved_proc->p_reg.pc);
kprintf(
"vec_nr= %d, trap_errno= 0x%lx, eip= 0x%lx, cs= 0x%x, eflags= 0x%lx\n",
vec_nr, (unsigned long)trap_errno,
(unsigned long)old_eip, old_cs, (unsigned long)old_eflags);
proc_stacktrace(saved_proc);
panic("exception in a kernel task", NO_NUM);
minix_panic("exception in a kernel task", saved_proc->p_endpoint);
}
#if DEBUG_STACKTRACE
/*===========================================================================*
* stacktrace *
*===========================================================================*/
PUBLIC void stacktrace(struct proc *proc)
PUBLIC void proc_stacktrace(struct proc *proc)
{
reg_t bp, v_bp, v_pc, v_hbp;
v_bp = proc->p_reg.fp;
kprintf("stacktrace: ");
kprintf("ep %d pc 0x%lx stack ", proc->p_endpoint, proc->p_reg.pc);
while(v_bp) {
phys_bytes p;
if(!(p = umap_local(proc, D, v_bp, sizeof(v_bp)))) {
kprintf("(bad bp %lx)", v_bp);
if(data_copy(proc->p_endpoint, v_bp,
SYSTEM, (vir_bytes) &v_hbp, sizeof(v_hbp)) != OK) {
kprintf("(v_bp 0x%lx ?)", v_bp);
break;
}
if(data_copy(proc->p_endpoint, v_bp + sizeof(v_pc),
SYSTEM, (vir_bytes) &v_pc, sizeof(v_pc)) != OK) {
kprintf("(v_pc 0x%lx ?)", v_pc);
break;
}
phys_copy(p+sizeof(v_pc), vir2phys(&v_pc), sizeof(v_pc));
phys_copy(p, vir2phys(&v_hbp), sizeof(v_hbp));
kprintf("0x%lx ", (unsigned long) v_pc);
if(v_hbp != 0 && v_hbp <= v_bp) {
kprintf("(bad hbp %lx)", v_hbp);
kprintf("(hbp %lx ?)", v_hbp);
break;
}
v_bp = v_hbp;
}
kprintf("\n");
}
#endif

View file

@ -135,12 +135,6 @@
#define IF_MASK 0x00000200
#define IOPL_MASK 0x003000
/* Sizes of memory tables. The boot monitor distinguishes three memory areas,
* namely low mem below 1M, 1M-16M, and mem after 16M. More chunks are needed
* for DOS MINIX.
*/
#define NR_MEMS 8
#define vir2phys(vir) (kinfo.data_base + (vir_bytes) (vir))
#endif /* _I386_ACONST_H */

View file

@ -55,8 +55,18 @@ struct segdesc_s { /* segment descriptor for protected mode */
typedef struct segframe {
reg_t p_ldt_sel; /* selector in gdt with ldt base and limit */
reg_t p_cr3; /* page table root */
struct segdesc_s p_ldt[2+NR_REMOTE_SEGS]; /* CS, DS and remote */
} segframe_t;
/* Page fault event. Stored in process table. Only valid if PAGEFAULT
* set in p_rts_flags.
*/
struct pagefault
{
u32_t pf_virtual; /* Address causing fault (CR2). */
u32_t pf_flags; /* Pagefault flags on stack. */
};
#endif /* #ifndef _I386_TYPES_H */

View file

@ -8,6 +8,7 @@
#include <ibm/interrupt.h>
#include <archconst.h>
#include "../../const.h"
#include "vm.h"
#include "sconst.h"
! This file contains a number of assembly code utility routines needed by the
@ -15,7 +16,7 @@
.define _monitor ! exit Minix and return to the monitor
.define _int86 ! let the monitor make an 8086 interrupt call
.define _cp_mess ! copies messages from source to destination
!.define _cp_mess ! copies messages from source to destination
.define _exit ! dummy for library routines
.define __exit ! dummy for library routines
.define ___exit ! dummy for library routines
@ -34,8 +35,11 @@
.define _level0 ! call a function at level 0
.define _read_cpu_flags ! read the cpu flags
.define _read_cr0 ! read cr0
.define _write_cr3 ! write cr3
.define _last_cr3
.define _write_cr0 ! write a value in cr0
.define _write_cr3 ! write a value in cr3 (root of the page table)
.define _kernel_cr3
! The routines only guarantee to preserve the registers the C compiler
! expects to be preserved (ebx, esi, edi, ebp, esp, segment registers, and
@ -162,42 +166,42 @@ csinit: mov eax, DS_SELECTOR
! Note that the message size, "Msize" is in DWORDS (not bytes) and must be set
! correctly. Changing the definition of message in the type file and not
! changing it here will lead to total disaster.
CM_ARGS = 4 + 4 + 4 + 4 + 4 ! 4 + 4 + 4 + 4 + 4
! es ds edi esi eip proc scl sof dcl dof
.align 16
_cp_mess:
cld
push esi
push edi
push ds
push es
mov eax, FLAT_DS_SELECTOR
mov ds, ax
mov es, ax
mov esi, CM_ARGS+4(esp) ! src clicks
shl esi, CLICK_SHIFT
add esi, CM_ARGS+4+4(esp) ! src offset
mov edi, CM_ARGS+4+4+4(esp) ! dst clicks
shl edi, CLICK_SHIFT
add edi, CM_ARGS+4+4+4+4(esp) ! dst offset
mov eax, CM_ARGS(esp) ! process number of sender
stos ! copy number of sender to dest message
add esi, 4 ! do not copy first word
mov ecx, Msize - 1 ! remember, first word does not count
rep
movs ! copy the message
pop es
pop ds
pop edi
pop esi
ret ! that is all folks!
!
!CM_ARGS = 4 + 4 + 4 + 4 + 4 ! 4 + 4 + 4 + 4 + 4
!! es ds edi esi eip proc scl sof dcl dof
!
! .align 16
!_cp_mess:
! cld
! push esi
! push edi
! push ds
! push es
!
! mov eax, FLAT_DS_SELECTOR
! mov ds, ax
! mov es, ax
!
! mov esi, CM_ARGS+4(esp) ! src clicks
! shl esi, CLICK_SHIFT
! add esi, CM_ARGS+4+4(esp) ! src offset
! mov edi, CM_ARGS+4+4+4(esp) ! dst clicks
! shl edi, CLICK_SHIFT
! add edi, CM_ARGS+4+4+4+4(esp) ! dst offset
!
! mov eax, CM_ARGS(esp) ! process number of sender
! stos ! copy number of sender to dest message
! add esi, 4 ! do not copy first word
! mov ecx, Msize - 1 ! remember, first word does not count
! rep
! movs ! copy the message
!
! pop es
! pop ds
! pop edi
! pop esi
! ret ! that is all folks!
!
!*===========================================================================*
!* exit *
@ -229,6 +233,9 @@ _phys_insw:
cld
push edi
push es
LOADKERNELCR3
mov ecx, FLAT_DS_SELECTOR
mov es, cx
mov edx, 8(ebp) ! port to read from
@ -254,6 +261,9 @@ _phys_insb:
cld
push edi
push es
LOADKERNELCR3
mov ecx, FLAT_DS_SELECTOR
mov es, cx
mov edx, 8(ebp) ! port to read from
@ -280,6 +290,9 @@ _phys_outsw:
cld
push esi
push ds
LOADKERNELCR3
mov ecx, FLAT_DS_SELECTOR
mov ds, cx
mov edx, 8(ebp) ! port to write to
@ -306,6 +319,9 @@ _phys_outsb:
cld
push esi
push ds
LOADKERNELCR3
mov ecx, FLAT_DS_SELECTOR
mov ds, cx
mov edx, 8(ebp) ! port to write to
@ -412,6 +428,8 @@ _phys_copy:
push edi
push es
LOADKERNELCR3
mov eax, FLAT_DS_SELECTOR
mov es, ax
@ -456,6 +474,9 @@ _phys_memset:
push esi
push ebx
push ds
LOADKERNELCR3
mov esi, 8(ebp)
mov eax, 16(ebp)
mov ebx, FLAT_DS_SELECTOR
@ -485,6 +506,7 @@ fill_done:
pop esi
pop ebp
ret
!*===========================================================================*
!* mem_rdw *
@ -585,14 +607,13 @@ _write_cr0:
ret
!*===========================================================================*
!* write_cr3 *
!* write_cr3 *
!*===========================================================================*
! PUBLIC void write_cr3(unsigned long value);
_write_cr3:
push ebp
mov ebp, esp
mov eax, 8(ebp)
mov cr3, eax
pop ebp
push ebp
mov ebp, esp
LOADCR3WITHEAX(0x22, 8(ebp))
pop ebp
ret

View file

@ -1,20 +1,26 @@
#include "../../kernel.h"
#include "../../proc.h"
#include "../../vm.h"
#include <minix/type.h>
#include <minix/syslib.h>
#include <minix/sysutil.h>
#include <string.h>
#include <sys/vm.h>
#include <sys/vm_i386.h>
#include <minix/portio.h>
#include "proto.h"
#include "../../proto.h"
#include "../../debug.h"
/* VM functions and data. */
PRIVATE int vm_needs_init= 1;
PRIVATE u32_t vm_cr3;
PUBLIC u32_t kernel_cr3;
extern u32_t cswitch;
u32_t last_cr3 = 0;
FORWARD _PROTOTYPE( void phys_put32, (phys_bytes addr, u32_t value) );
FORWARD _PROTOTYPE( u32_t phys_get32, (phys_bytes addr) );
@ -22,6 +28,13 @@ FORWARD _PROTOTYPE( void vm_set_cr3, (u32_t value) );
FORWARD _PROTOTYPE( void set_cr3, (void) );
FORWARD _PROTOTYPE( void vm_enable_paging, (void) );
#if DEBUG_VMASSERT
#define vmassert(t) { \
if(!(t)) { minix_panic("vm: assert " #t " failed\n", __LINE__); } }
#else
#define vmassert(t) { }
#endif
/* *** Internal VM Functions *** */
PUBLIC void vm_init(void)
@ -31,31 +44,35 @@ PUBLIC void vm_init(void)
phys_bytes vm_dir_base, vm_pt_base, phys_mem;
u32_t entry;
unsigned pages;
struct proc* rp;
if (!vm_size)
panic("i386_vm_init: no space for page tables", NO_NUM);
minix_panic("i386_vm_init: no space for page tables", NO_NUM);
if(vm_running)
return;
/* Align page directory */
o= (vm_base % PAGE_SIZE);
o= (vm_base % I386_PAGE_SIZE);
if (o != 0)
o= PAGE_SIZE-o;
o= I386_PAGE_SIZE-o;
vm_dir_base= vm_base+o;
/* Page tables start after the page directory */
vm_pt_base= vm_dir_base+PAGE_SIZE;
vm_pt_base= vm_dir_base+I386_PAGE_SIZE;
pt_size= (vm_base+vm_size)-vm_pt_base;
pt_size -= (pt_size % PAGE_SIZE);
pt_size -= (pt_size % I386_PAGE_SIZE);
/* Compute the number of pages based on vm_mem_high */
pages= (vm_mem_high-1)/PAGE_SIZE + 1;
pages= (vm_mem_high-1)/I386_PAGE_SIZE + 1;
if (pages * I386_VM_PT_ENT_SIZE > pt_size)
panic("i386_vm_init: page table too small", NO_NUM);
minix_panic("i386_vm_init: page table too small", NO_NUM);
for (p= 0; p*I386_VM_PT_ENT_SIZE < pt_size; p++)
{
phys_mem= p*PAGE_SIZE;
phys_mem= p*I386_PAGE_SIZE;
entry= phys_mem | I386_VM_USER | I386_VM_WRITE |
I386_VM_PRESENT;
if (phys_mem >= vm_mem_high)
@ -65,15 +82,33 @@ PUBLIC void vm_init(void)
for (p= 0; p < I386_VM_DIR_ENTRIES; p++)
{
phys_mem= vm_pt_base + p*PAGE_SIZE;
phys_mem= vm_pt_base + p*I386_PAGE_SIZE;
entry= phys_mem | I386_VM_USER | I386_VM_WRITE |
I386_VM_PRESENT;
if (phys_mem >= vm_pt_base + pt_size)
entry= 0;
phys_put32(vm_dir_base + p*I386_VM_PT_ENT_SIZE, entry);
}
/* Set this cr3 in all currently running processes for
* future context switches.
*/
for (rp=BEG_PROC_ADDR; rp<END_PROC_ADDR; rp++) {
u32_t mycr3;
if(isemptyp(rp)) continue;
rp->p_seg.p_cr3 = vm_dir_base;
}
kernel_cr3 = vm_dir_base;
/* Set this cr3 now (not active until paging enabled). */
vm_set_cr3(vm_dir_base);
/* Actually enable paging (activating cr3 load above). */
level0(vm_enable_paging);
/* Don't do this init in the future. */
vm_running = 1;
}
PRIVATE void phys_put32(addr, value)
@ -113,50 +148,6 @@ PRIVATE void vm_enable_paging(void)
write_cr0(cr0 | I386_CR0_PG);
}
PUBLIC void vm_map_range(base, size, offset)
u32_t base;
u32_t size;
u32_t offset;
{
u32_t curr_pt, curr_pt_addr, entry;
int dir_ent, pt_ent;
if (base % PAGE_SIZE != 0)
panic("map_range: bad base", base);
if (size % PAGE_SIZE != 0)
panic("map_range: bad size", size);
if (offset % PAGE_SIZE != 0)
panic("map_range: bad offset", offset);
curr_pt= -1;
curr_pt_addr= 0;
while (size != 0)
{
dir_ent= (base >> I386_VM_DIR_ENT_SHIFT);
pt_ent= (base >> I386_VM_PT_ENT_SHIFT) & I386_VM_PT_ENT_MASK;
if (dir_ent != curr_pt)
{
/* Get address of page table */
curr_pt= dir_ent;
curr_pt_addr= phys_get32(vm_cr3 +
dir_ent * I386_VM_PT_ENT_SIZE);
curr_pt_addr &= I386_VM_ADDR_MASK;
}
entry= offset | I386_VM_USER | I386_VM_WRITE |
I386_VM_PRESENT;
#if 0 /* Do we need this for memory mapped I/O? */
entry |= I386_VM_PCD | I386_VM_PWT;
#endif
phys_put32(curr_pt_addr + pt_ent * I386_VM_PT_ENT_SIZE, entry);
offset += PAGE_SIZE;
base += PAGE_SIZE;
size -= PAGE_SIZE;
}
/* reload root of page table. */
vm_set_cr3(vm_cr3);
}
PUBLIC vir_bytes alloc_remote_segment(u32_t *selector,
segframe_t *segments, int index, phys_bytes phys, vir_bytes size,
int priv)
@ -188,6 +179,10 @@ PUBLIC phys_bytes umap_remote(struct proc* rp, int seg,
/* Calculate the physical memory address for a given virtual address. */
struct far_mem *fm;
#if 0
if(rp->p_misc_flags & MF_FULLVM) return 0;
#endif
if (bytes <= 0) return( (phys_bytes) 0);
if (seg < 0 || seg >= NR_REMOTE_SEGS) return( (phys_bytes) 0);
@ -212,6 +207,9 @@ vir_bytes bytes; /* # of bytes to be copied */
phys_bytes pa; /* intermediate variables as phys_bytes */
phys_bytes seg_base;
if(seg != T && seg != D && seg != S)
minix_panic("umap_local: wrong seg", seg);
if (bytes <= 0) return( (phys_bytes) 0);
if (vir_addr + bytes <= vir_addr) return 0; /* overflow */
vc = (vir_addr + bytes - 1) >> CLICK_SHIFT; /* last click of data */
@ -232,3 +230,569 @@ vir_bytes bytes; /* # of bytes to be copied */
return(seg_base + pa);
}
/*===========================================================================*
* umap_virtual *
*===========================================================================*/
PUBLIC phys_bytes umap_virtual(rp, seg, vir_addr, bytes)
register struct proc *rp; /* pointer to proc table entry for process */
int seg; /* T, D, or S segment */
vir_bytes vir_addr; /* virtual address in bytes within the seg */
vir_bytes bytes; /* # of bytes to be copied */
{
vir_bytes linear;
u32_t phys = 0;
if(seg == MEM_GRANT) {
phys = umap_grant(rp, vir_addr, bytes);
} else {
if(!(linear = umap_local(rp, seg, vir_addr, bytes))) {
kprintf("SYSTEM:umap_virtual: umap_local failed\n");
phys = 0;
} else {
if(vm_lookup(rp, linear, &phys, NULL) != OK) {
kprintf("SYSTEM:umap_virtual: vm_lookup of %s: seg 0x%lx: 0x%lx failed\n", rp->p_name, seg, vir_addr);
phys = 0;
}
if(phys == 0)
minix_panic("vm_lookup returned phys", phys);
}
}
if(phys == 0) {
kprintf("SYSTEM:umap_virtual: lookup failed\n");
return 0;
}
/* Now make sure addresses are contiguous in physical memory
* so that the umap makes sense.
*/
if(bytes > 0 && !vm_contiguous(rp, linear, bytes)) {
kprintf("umap_virtual: %s: %d at 0x%lx (vir 0x%lx) not contiguous\n",
rp->p_name, bytes, linear, vir_addr);
return 0;
}
/* phys must be larger than 0 (or the caller will think the call
* failed), and address must not cross a page boundary.
*/
vmassert(phys);
return phys;
}
/*===========================================================================*
* vm_lookup *
*===========================================================================*/
PUBLIC int vm_lookup(struct proc *proc, vir_bytes virtual, vir_bytes *physical, u32_t *ptent)
{
u32_t *root, *pt;
int pde, pte;
u32_t pde_v, pte_v;
vmassert(proc);
vmassert(physical);
vmassert(!(proc->p_rts_flags & SLOT_FREE));
/* Retrieve page directory entry. */
root = (u32_t *) proc->p_seg.p_cr3;
vmassert(!((u32_t) root % I386_PAGE_SIZE));
pde = I386_VM_PDE(virtual);
vmassert(pde >= 0 && pde < I386_VM_DIR_ENTRIES);
pde_v = phys_get32((u32_t) (root + pde));
if(!(pde_v & I386_VM_PRESENT)) {
#if 0
kprintf("vm_lookup: %d:%s:0x%lx: cr3 0x%lx: pde %d not present\n",
proc->p_endpoint, proc->p_name, virtual, root, pde);
kprintf("kernel stack: ");
util_stacktrace();
#endif
return EFAULT;
}
/* Retrieve page table entry. */
pt = (u32_t *) I386_VM_PFA(pde_v);
vmassert(!((u32_t) pt % I386_PAGE_SIZE));
pte = I386_VM_PTE(virtual);
vmassert(pte >= 0 && pte < I386_VM_PT_ENTRIES);
pte_v = phys_get32((u32_t) (pt + pte));
if(!(pte_v & I386_VM_PRESENT)) {
#if 0
kprintf("vm_lookup: %d:%s:0x%lx: cr3 %lx: pde %d: pte %d not present\n",
proc->p_endpoint, proc->p_name, virtual, root, pde, pte);
kprintf("kernel stack: ");
util_stacktrace();
#endif
return EFAULT;
}
if(ptent) *ptent = pte_v;
/* Actual address now known; retrieve it and add page offset. */
*physical = I386_VM_PFA(pte_v);
*physical += virtual % I386_PAGE_SIZE;
return OK;
}
/* From virtual address v in process p,
* lookup physical address and assign it to d.
* If p is NULL, assume it's already a physical address.
*/
#define LOOKUP(d, p, v, flagsp) { \
int r; \
if(!(p)) { (d) = (v); } \
else { \
if((r=vm_lookup((p), (v), &(d), flagsp)) != OK) { \
kprintf("vm_copy: lookup failed of 0x%lx in %d (%s)\n"\
"kernel stacktrace: ", (v), (p)->p_endpoint, \
(p)->p_name); \
util_stacktrace(); \
return r; \
} } }
/*===========================================================================*
* vm_copy *
*===========================================================================*/
int vm_copy(vir_bytes src, struct proc *srcproc,
vir_bytes dst, struct proc *dstproc, phys_bytes bytes)
{
#define WRAPS(v) (ULONG_MAX - (v) <= bytes)
if(WRAPS(src) || WRAPS(dst))
minix_panic("vm_copy: linear address wraps", NO_NUM);
while(bytes > 0) {
u32_t n, flags;
phys_bytes p_src, p_dst;
#define PAGEREMAIN(v) (I386_PAGE_SIZE - ((v) % I386_PAGE_SIZE))
/* We can copy this number of bytes without
* crossing a page boundary, but don't copy more
* than asked.
*/
n = MIN(PAGEREMAIN(src), PAGEREMAIN(dst));
n = MIN(n, bytes);
vmassert(n > 0);
vmassert(n <= I386_PAGE_SIZE);
/* Convert both virtual addresses to physical and do
* copy.
*/
LOOKUP(p_src, srcproc, src, NULL);
LOOKUP(p_dst, dstproc, dst, &flags);
if(!(flags & I386_VM_WRITE)) {
kprintf("vm_copy: copying to nonwritable page\n");
kprintf("kernel stack: ");
util_stacktrace();
return EFAULT;
}
phys_copy(p_src, p_dst, n);
/* Book number of bytes copied. */
vmassert(bytes >= n);
bytes -= n;
src += n;
dst += n;
}
return OK;
}
/*===========================================================================*
* vm_contiguous *
*===========================================================================*/
PUBLIC int vm_contiguous(struct proc *targetproc, u32_t vir_buf, size_t bytes)
{
int first = 1, r, boundaries = 0;
u32_t prev_phys, po;
u32_t prev_vir;
vmassert(targetproc);
vmassert(bytes > 0);
vmassert(vm_running);
/* Start and end at page boundary to make logic simpler. */
po = vir_buf % I386_PAGE_SIZE;
if(po > 0) {
bytes += po;
vir_buf -= po;
}
po = (vir_buf + bytes) % I386_PAGE_SIZE;
if(po > 0)
bytes += I386_PAGE_SIZE - po;
/* Keep going as long as we cross a page boundary. */
while(bytes > 0) {
u32_t phys;
if((r=vm_lookup(targetproc, vir_buf, &phys, NULL)) != OK) {
kprintf("vm_contiguous: vm_lookup failed, %d\n", r);
kprintf("kernel stack: ");
util_stacktrace();
return 0;
}
if(!first) {
if(prev_phys+I386_PAGE_SIZE != phys) {
kprintf("vm_contiguous: no (0x%lx, 0x%lx)\n",
prev_phys, phys);
kprintf("kernel stack: ");
util_stacktrace();
return 0;
}
}
first = 0;
prev_phys = phys;
prev_vir = vir_buf;
vir_buf += I386_PAGE_SIZE;
bytes -= I386_PAGE_SIZE;
boundaries++;
}
if(verbose_vm)
kprintf("vm_contiguous: yes (%d boundaries tested)\n",
boundaries);
return 1;
}
int vm_checkrange_verbose = 0;
/*===========================================================================*
* 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;
vmassert(vm_running);
/* If caller has had a reply to this request, return it. */
if(RTS_ISSET(caller, VMREQUEST)) {
if(caller->p_vmrequest.who == target->p_endpoint) {
if(caller->p_vmrequest.vmresult == VMSUSPEND)
minix_panic("check sees VMSUSPEND?", NO_NUM);
RTS_LOCK_UNSET(caller, VMREQUEST);
#if 0
kprintf("SYSTEM: vm_checkrange: returning vmresult %d\n",
caller->p_vmrequest.vmresult);
#endif
return caller->p_vmrequest.vmresult;
} else {
#if 0
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;
/* If page exists and it's writable if desired, we're OK
* for this page.
*/
if(vm_lookup(target, v, &phys, &flags) == OK &&
!(wrfl && !(flags & I386_VM_WRITE))) {
if(vm_checkrange_verbose) {
#if 0
kprintf("SYSTEM: checkrange:%s:%d: 0x%lx: write 0x%lx, flags 0x%lx, phys 0x%lx, OK\n",
target->p_name, target->p_endpoint, v, wrfl, flags, phys);
#endif
}
continue;
}
if(vm_checkrange_verbose) {
kprintf("SYSTEM: checkrange:%s:%d: 0x%lx: write 0x%lx, flags 0x%lx, phys 0x%lx, NOT OK\n",
target->p_name, target->p_endpoint, v, wrfl, flags, phys);
}
if(checkonly)
return VMSUSPEND;
/* This range is not OK for this process. Set parameters
* of the request and notify VM about the pending request.
*/
if(RTS_ISSET(caller, VMREQUEST))
minix_panic("VMREQUEST already set", caller->p_endpoint);
RTS_LOCK_SET(caller, VMREQUEST);
/* Set parameters in caller. */
caller->p_vmrequest.writeflag = wrfl;
caller->p_vmrequest.start = vir;
caller->p_vmrequest.length = bytes;
caller->p_vmrequest.who = target->p_endpoint;
/* Set caller in target. */
target->p_vmrequest.requestor = caller;
/* Connect caller on vmrequest wait queue. */
caller->p_vmrequest.nextrequestor = vmrequest;
vmrequest = caller;
soft_notify(VM_PROC_NR);
#if 0
kprintf("SYSTEM: vm_checkrange: range bad for "
"target %s:0x%lx-0x%lx, caller %s\n",
target->p_name, vir, vir+bytes, caller->p_name);
kprintf("vm_checkrange kernel trace: ");
util_stacktrace();
kprintf("target trace: ");
proc_stacktrace(target);
#endif
if(target->p_endpoint == VM_PROC_NR) {
kprintf("caller trace: ");
proc_stacktrace(caller);
kprintf("target trace: ");
proc_stacktrace(target);
minix_panic("VM ranges should be OK", NO_NUM);
}
return VMSUSPEND;
}
return OK;
}
char *flagstr(u32_t e, int dir)
{
static char str[80];
strcpy(str, "");
#define FLAG(v) do { if(e & (v)) { strcat(str, #v " "); } } while(0)
FLAG(I386_VM_PRESENT);
FLAG(I386_VM_WRITE);
FLAG(I386_VM_USER);
FLAG(I386_VM_PWT);
FLAG(I386_VM_PCD);
if(dir)
FLAG(I386_VM_BIGPAGE); /* Page directory entry only */
else
FLAG(I386_VM_DIRTY); /* Page table entry only */
return str;
}
void vm_pt_print(u32_t *pagetable, u32_t v)
{
int pte, l = 0;
int col = 0;
vmassert(!((u32_t) pagetable % I386_PAGE_SIZE));
for(pte = 0; pte < I386_VM_PT_ENTRIES; pte++) {
u32_t pte_v, pfa;
pte_v = phys_get32((u32_t) (pagetable + pte));
if(!(pte_v & I386_VM_PRESENT))
continue;
pfa = I386_VM_PFA(pte_v);
kprintf("%4d:%08lx:%08lx ",
pte, v + I386_PAGE_SIZE*pte, pfa);
col++;
if(col == 3) { kprintf("\n"); col = 0; }
}
if(col > 0) kprintf("\n");
return;
}
/*===========================================================================*
* vm_print *
*===========================================================================*/
void vm_print(u32_t *root)
{
int pde;
vmassert(!((u32_t) root % I386_PAGE_SIZE));
for(pde = 0; pde < I386_VM_DIR_ENTRIES; pde++) {
u32_t pde_v;
u32_t *pte_a;
pde_v = phys_get32((u32_t) (root + pde));
if(!(pde_v & I386_VM_PRESENT))
continue;
pte_a = (u32_t *) I386_VM_PFA(pde_v);
kprintf("%4d: pt %08lx %s\n",
pde, pte_a, flagstr(pde_v, 1));
vm_pt_print(pte_a, pde * I386_VM_PT_ENTRIES * I386_PAGE_SIZE);
}
return;
}
/*===========================================================================*
* virtual_copy_f *
*===========================================================================*/
PUBLIC int virtual_copy_f(src_addr, dst_addr, bytes, vmcheck)
struct vir_addr *src_addr; /* source virtual address */
struct vir_addr *dst_addr; /* destination virtual address */
vir_bytes bytes; /* # of bytes to copy */
int vmcheck; /* if nonzero, can return VMSUSPEND */
{
/* Copy bytes from virtual address src_addr to virtual address dst_addr.
* Virtual addresses can be in ABS, LOCAL_SEG, REMOTE_SEG, or BIOS_SEG.
*/
struct vir_addr *vir_addr[2]; /* virtual source and destination address */
phys_bytes phys_addr[2]; /* absolute source and destination */
int seg_index;
int i, r;
struct proc *procs[2];
/* Check copy count. */
if (bytes <= 0) return(EDOM);
/* Do some more checks and map virtual addresses to physical addresses. */
vir_addr[_SRC_] = src_addr;
vir_addr[_DST_] = dst_addr;
for (i=_SRC_; i<=_DST_; i++) {
int proc_nr, type;
struct proc *p;
type = vir_addr[i]->segment & SEGMENT_TYPE;
if((type != PHYS_SEG && type != BIOS_SEG) &&
isokendpt(vir_addr[i]->proc_nr_e, &proc_nr))
p = proc_addr(proc_nr);
else
p = NULL;
procs[i] = p;
/* Get physical address. */
switch(type) {
case LOCAL_SEG:
case LOCAL_VM_SEG:
if(!p) return EDEADSRCDST;
seg_index = vir_addr[i]->segment & SEGMENT_INDEX;
if(type == LOCAL_SEG)
phys_addr[i] = umap_local(p, seg_index, vir_addr[i]->offset,
bytes);
else
phys_addr[i] = umap_virtual(p, seg_index, vir_addr[i]->offset,
bytes);
if(phys_addr[i] == 0) {
kprintf("virtual_copy: map 0x%x failed for %s seg %d, "
"offset %lx, len %d, i %d\n",
type, p->p_name, seg_index, vir_addr[i]->offset,
bytes, i);
}
break;
case REMOTE_SEG:
if(!p) return EDEADSRCDST;
seg_index = vir_addr[i]->segment & SEGMENT_INDEX;
phys_addr[i] = umap_remote(p, seg_index, vir_addr[i]->offset, bytes);
break;
#if _MINIX_CHIP == _CHIP_INTEL
case BIOS_SEG:
phys_addr[i] = umap_bios(vir_addr[i]->offset, bytes );
break;
#endif
case PHYS_SEG:
phys_addr[i] = vir_addr[i]->offset;
break;
case GRANT_SEG:
phys_addr[i] = umap_grant(p, vir_addr[i]->offset, bytes);
break;
default:
kprintf("virtual_copy: strange type 0x%x\n", type);
return(EINVAL);
}
/* Check if mapping succeeded. */
if (phys_addr[i] <= 0 && vir_addr[i]->segment != PHYS_SEG) {
kprintf("virtual_copy EFAULT\n");
return(EFAULT);
}
}
if(vmcheck && procs[_SRC_])
CHECKRANGE_OR_SUSPEND(procs[_SRC_], phys_addr[_SRC_], bytes, 0);
if(vmcheck && procs[_DST_])
CHECKRANGE_OR_SUSPEND(procs[_DST_], phys_addr[_DST_], bytes, 1);
/* Now copy bytes between physical addresseses. */
if(!vm_running || (procs[_SRC_] == NULL && procs[_DST_] == NULL)) {
/* Without vm, address ranges actually are physical. */
phys_copy(phys_addr[_SRC_], phys_addr[_DST_], (phys_bytes) bytes);
r = OK;
} else {
/* With vm, addresses need further interpretation. */
r = vm_copy(phys_addr[_SRC_], procs[_SRC_],
phys_addr[_DST_], procs[_DST_], (phys_bytes) bytes);
if(r != OK) {
kprintf("vm_copy: %lx to %lx failed\n",
phys_addr[_SRC_],phys_addr[_DST_]);
}
}
return(r);
}
/*===========================================================================*
* data_copy *
*===========================================================================*/
PUBLIC int data_copy(
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(&src, &dst, bytes);
}
/*===========================================================================*
* arch_pre_exec *
*===========================================================================*/
PUBLIC int arch_pre_exec(struct proc *pr, u32_t ip, u32_t sp)
{
/* wipe extra LDT entries, set program counter, and stack pointer. */
memset(pr->p_seg.p_ldt + EXTRA_LDT_INDEX, 0,
sizeof(pr->p_seg.p_ldt[0]) * (LDT_SIZE - EXTRA_LDT_INDEX));
pr->p_reg.pc = ip;
pr->p_reg.sp = sp;
}
/*===========================================================================*
* arch_umap *
*===========================================================================*/
PUBLIC int arch_umap(struct proc *pr, vir_bytes offset, vir_bytes count,
int seg, phys_bytes *addr)
{
switch(seg) {
case BIOS_SEG:
*addr = umap_bios(offset, count);
return OK;
}
/* This must be EINVAL; the umap fallback function in
* lib/syslib/alloc_util.c depends on it to detect an
* older kernel (as opposed to mapping error).
*/
return EINVAL;
}

View file

@ -1,4 +1,4 @@
#
#
! This file, mpx386.s, is included by mpx.s when Minix is compiled for
! 32-bit Intel CPUs. The alternative mpx88.s is compiled for 16-bit CPUs.
@ -58,6 +58,7 @@ begbss:
#include <ibm/interrupt.h>
#include <archconst.h>
#include "../../const.h"
#include "vm.h"
#include "sconst.h"
/* Selected 386 tss offsets. */
@ -71,6 +72,13 @@ begbss:
.define _restart
.define save
.define _kernel_cr3
.define _pagefault_cr2
.define _pagefault_count
.define errexception
.define exception1
.define exception
.define _divide_error
.define _single_step_exception
@ -88,6 +96,9 @@ begbss:
.define _general_protection
.define _page_fault
.define _copr_error
.define _params_size
.define _params_offset
.define _mon_ds
.define _hwint00 ! handlers for hardware interrupts
.define _hwint01
@ -173,6 +184,11 @@ copygdt:
mov ss, ax
mov esp, k_stktop ! set sp to point to the top of kernel stack
! Save boot parameters into these global variables for i386 code
mov (_params_size), edx
mov (_params_offset), ebx
mov (_mon_ds), SS_SELECTOR
! Call C startup code to set up a proper environment to run main().
push edx
push ebx
@ -216,6 +232,7 @@ csinit:
#define hwint_master(irq) \
call save /* save interrupted process state */;\
push (_irq_handlers+4*irq) /* irq_handlers[irq] */;\
LOADCR3WITHEAX(irq, (_kernel_cr3)) /* switch to kernel page table */;\
call _intr_handle /* intr_handle(irq_handlers[irq]) */;\
pop ecx ;\
cmp (_irq_actids+4*irq), 0 /* interrupt still active? */;\
@ -267,6 +284,7 @@ _hwint07: ! Interrupt routine for irq 7 (printer)
#define hwint_slave(irq) \
call save /* save interrupted process state */;\
push (_irq_handlers+4*irq) /* irq_handlers[irq] */;\
LOADCR3WITHEAX(irq, (_kernel_cr3)) /* switch to kernel page table */;\
call _intr_handle /* intr_handle(irq_handlers[irq]) */;\
pop ecx ;\
cmp (_irq_actids+4*irq), 0 /* interrupt still active? */;\
@ -358,6 +376,7 @@ _p_s_call:
o16 push es
o16 push fs
o16 push gs
mov si, ss ! ss is kernel data segment
mov ds, si ! load rest of kernel segments
mov es, si ! kernel does not use fs, gs
@ -371,6 +390,9 @@ _p_s_call:
push ebx ! pointer to user message
push eax ! source / destination
push ecx ! call number (ipc primitive to use)
! LOADCR3WITHEAX(0x20, (_kernel_cr3))
call _sys_call ! sys_call(call_nr, src_dst, m_ptr, bit_map)
! caller is now explicitly in proc_ptr
mov AXREG(esi), eax ! sys_call MUST PRESERVE si
@ -391,6 +413,7 @@ _restart:
mov (_next_ptr), 0
0: mov esp, (_proc_ptr) ! will assume P_STACKBASE == 0
lldt P_LDT_SEL(esp) ! enable process' segment descriptors
LOADCR3WITHEAX(0x21, P_CR3(esp)) ! switch to process page table
lea eax, P_STACKTOP(esp) ! arrange for next interrupt
mov (_tss+TSS3_S_SP0), eax ! to save state in process table
restart1:
@ -464,6 +487,11 @@ _general_protection:
_page_fault:
push PAGE_FAULT_VECTOR
push eax
mov eax, cr2
sseg mov (_pagefault_cr2), eax
sseg inc (_pagefault_count)
pop eax
jmp errexception
_copr_error:
@ -492,12 +520,16 @@ errexception:
sseg pop (trap_errno)
exception1: ! Common for all exceptions.
push eax ! eax is scratch register
mov eax, 0+4(esp) ! old eip
sseg mov (old_eip), eax
movzx eax, 4+4(esp) ! old cs
sseg mov (old_cs), eax
mov eax, 8+4(esp) ! old eflags
sseg mov (old_eflags), eax
LOADCR3WITHEAX(0x24, (_kernel_cr3))
pop eax
call save
push (old_eflags)
@ -517,6 +549,15 @@ _level0_call:
call save
jmp (_level0_func)
!*===========================================================================*
!* load_kernel_cr3 *
!*===========================================================================*
.align 16
_load_kernel_cr3:
mov eax, (_kernel_cr3)
mov cr3, eax
ret
!*===========================================================================*
!* data *
!*===========================================================================*
@ -533,3 +574,4 @@ k_stktop: ! top of kernel stack
.comm old_eip, 4
.comm old_cs, 4
.comm old_eflags, 4

View file

@ -307,7 +307,10 @@ PUBLIC void alloc_segments(register struct proc *rp)
code_bytes = data_bytes; /* common I&D, poor protect */
else
code_bytes = (phys_bytes) rp->p_memmap[T].mem_len << CLICK_SHIFT;
privilege = (iskernelp(rp)) ? TASK_PRIVILEGE : USER_PRIVILEGE;
if( (iskernelp(rp)))
privilege = TASK_PRIVILEGE;
else
privilege = USER_PRIVILEGE;
init_codeseg(&rp->p_seg.p_ldt[CS_LDT_INDEX],
(phys_bytes) rp->p_memmap[T].mem_phys << CLICK_SHIFT,
code_bytes, privilege);

Some files were not shown because too many files have changed in this diff Show more