Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
93 commits
Select commit Hold shift + click to select a range
19f1119
omit one un-needed mention of machine mode
Sep 11, 2024
347b0ba
to avoid masking errors, make push_off() only turn interrupts
Oct 6, 2024
29ba4ec
we don't need SSIE any more
Oct 6, 2024
fd2ee94
maybe this is a more logical place to read uart's ISR
Oct 6, 2024
4f641a1
better comments
Oct 15, 2024
5a7ecd4
Add "," in printf
kaashoek Oct 19, 2024
1eebe7e
Merge branch 'riscv' of g.csail.mit.edu:xv6-dev into riscv
Oct 21, 2024
1312f0b
Delete comment that was made obsolete by FD_DEVICE
kaashoek Oct 28, 2024
f8a26e9
Merge branch 'riscv' of g.csail.mit.edu:xv6-dev into riscv
Nov 13, 2024
f7b14e5
maybe fix a race between interrupt and wfi
Nov 13, 2024
2e72ada
Remove wfi for fs lab
ivywu2003 Nov 13, 2024
3803df5
Revert "Remove wfi for fs lab"
ivywu2003 Nov 13, 2024
2a39c5a
Fixed buffer overflow in printint (#299)
HirbodBehnam Jul 8, 2025
df61469
add riscv64-elf as TOOLPREFIX
BielLopes Jun 18, 2025
01484b5
fix rwsbrk type sig compile error with recent gcc
zeldovich Jul 2, 2025
7e88901
Fixed buffer overflow in printint (#299)
HirbodBehnam Jul 8, 2025
caac117
Merge branch 'riscv-github' into riscv
kaashoek Jul 30, 2025
401f186
Merge branch 'riscv' of g.csail.mit.edu:xv6-dev into riscv
Jul 30, 2025
c4de4b0
Check qemu version
kaashoek Jul 30, 2025
9ef6407
Support lazy page allocation as a simple example to show off page
kaashoek Jul 31, 2025
a9c5760
Merge branch 'riscv' of g.csail.mit.edu:xv6-dev into riscv
Jul 31, 2025
9c2419f
push_off() previously used mycpu() without first turning off
Aug 2, 2025
f76993d
nits
Aug 4, 2025
79b579a
warn when usertests justone matches no tests
zeldovich Aug 4, 2025
98107c6
pretend to address issue #269, about -ffreestanding
Aug 4, 2025
e6e698d
address PR 377
Aug 4, 2025
7e95e76
issue 331 -- don't save/restore sp
Aug 4, 2025
3259cfc
Merge branch 'lazy' into riscv
kaashoek Aug 4, 2025
5628970
Merge branch 'riscv-github' into riscv
kaashoek Aug 5, 2025
a45c117
Trim leading whitespaces to avoid `cd` failure
segfauIt Jun 8, 2025
32167c7
Ignore blank command
segfauIt Jun 8, 2025
43297ab
Use `else` instead of `continue`
segfauIt Jun 8, 2025
b698485
No need to exec init process through initcode
segfauIt Jun 8, 2025
51e2fd2
remove ramdisk functions from defs.h
GerfautGE Nov 8, 2024
5e6b14e
refactor: clear user.h
AnzhiZhang Oct 31, 2024
4dae6fb
let printf understands %c
AnzhiZhang Oct 24, 2024
709cbab
update kernal/printf.c
AnzhiZhang Oct 31, 2024
4b6137a
fix comment in entry.S
papparapa Aug 12, 2024
d93ef57
UART: replace magic value 0x01 with LSR_RX_READY
Mes0903 Aug 2, 2025
181a084
Relink user object file when user/user.ld changes
segfauIt Aug 2, 2025
f454a11
Fix compile error
kaashoek Aug 5, 2025
d234f7b
Kill #if 0
kaashoek Aug 5, 2025
e87826f
Update for recent contributors
kaashoek Aug 5, 2025
5de84ba
PR 302
kaashoek Aug 5, 2025
d712f59
fix kernel.ld so that _entry will appear in the right place
HHHHao-s Oct 30, 2024
e78cd36
Fix tags
kaashoek Aug 5, 2025
7c0db5d
Update
kaashoek Aug 5, 2025
5aed199
Document that name in dirent may not be a null-terminated string.
kaashoek Aug 5, 2025
b444f06
Merge branch 'riscv-github' into riscv
kaashoek Aug 5, 2025
c161fb7
fix things so that usertrap() returns to the trampoline,
Aug 6, 2025
b8f3093
x
kaashoek Aug 6, 2025
c968038
x
kaashoek Aug 6, 2025
10d9e78
x
kaashoek Aug 6, 2025
590b978
x
kaashoek Aug 6, 2025
3c20f7d
x
kaashoek Aug 6, 2025
4afc4c1
x
kaashoek Aug 6, 2025
fe989da
Checkpoint WIP: a crash test
kaashoek Aug 6, 2025
db26774
PR 359, thanks segfault
kaashoek Aug 6, 2025
52efd73
Crash tests for reclaiming an orphaned file and directory
kaashoek Aug 6, 2025
35cd49c
x
kaashoek Aug 6, 2025
5493ec0
x
kaashoek Aug 6, 2025
d7df697
x
kaashoek Aug 6, 2025
2295a9d
Try test_log a few times before failing the test
kaashoek Aug 7, 2025
2134b23
Support running usertests from test script
kaashoek Aug 7, 2025
b715361
Kill #if 0 here too
kaashoek Aug 7, 2025
33844c1
Make %u, %x, and %c unsigned
kaashoek Aug 7, 2025
ab958d7
Revert "Document that name in dirent may not be a null-terminated str…
kaashoek Aug 7, 2025
2e5f272
qhuo
kaashoek Aug 7, 2025
1a8645f
move a few vm.c functions to match book's flow a bit better
Aug 10, 2025
f61e51d
nits
Aug 10, 2025
2f69c72
Add sbrkalloc to capture a test pattern that forces allocation
kaashoek Aug 10, 2025
3d815fc
x
kaashoek Aug 10, 2025
707a9f7
Rename to use lazy instead of sparse
kaashoek Aug 11, 2025
36a255c
more precise tracking of block space in log
zeldovich Aug 11, 2025
5f2fbe1
Merge branch 'riscv-crash' into riscv
kaashoek Aug 11, 2025
79fa703
x
kaashoek Aug 12, 2025
4a92b85
Add a flag to the sbrk system call indicating eager or lazy allocation
kaashoek Aug 12, 2025
4dfca4a
4096 -> PGSIZE
kaashoek Aug 12, 2025
11362fe
Make generation of syscall stub ready for prefix
kaashoek Aug 12, 2025
6d2592a
Clean up sbrk error handling
kaashoek Aug 12, 2025
a843829
uart tx code better suited to the sleep/wakeup lecture.
Aug 12, 2025
9374395
Use mem instead of ka
kaashoek Aug 14, 2025
f5dea58
user sleep() -> pause()
Aug 19, 2025
0bb6995
null-terminate fmtname() result
Aug 21, 2025
2ce32bd
PR 383
kaashoek Aug 25, 2025
7d7adbb
Add DOC: for reference in book
kaashoek Sep 2, 2025
d366b51
propagate main return value to exit status
zeldovich Sep 3, 2025
4f1bdde
try again to fix the dirent name strncpy warning
zeldovich Sep 4, 2025
c6a6eaa
fix user printf for uint64
zeldovich Sep 7, 2025
996f6ee
fix start() args
zeldovich Sep 8, 2025
9dbd536
Update comment
kaashoek Sep 10, 2025
c14b639
pass -Wno-unknown-attributes for mkfs too
zeldovich Sep 15, 2025
6f04a20
Merge branch 'main' into 39-upd-upstream
Sep 21, 2025
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ mkfs
kernel/kernel
user/usys.S
.gdbinit
TAGS

# Clangd
compile_commands.json
Expand Down
42 changes: 27 additions & 15 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -53,17 +53,18 @@ TOOLPREFIX := $(shell if riscv64-unknown-elf-objdump -i 2>&1 | grep 'elf64-big'
endif

QEMU = qemu-system-riscv64
MIN_QEMU_VERSION = 7.2

CC = $(TOOLPREFIX)gcc
AS = $(TOOLPREFIX)gas
LD = $(TOOLPREFIX)ld
OBJCOPY = $(TOOLPREFIX)objcopy
OBJDUMP = $(TOOLPREFIX)objdump

CFLAGS = -Wall -Werror -O -fno-omit-frame-pointer -ggdb -gdwarf-2
CFLAGS = -Wall -Werror -Wno-unknown-attributes -O -fno-omit-frame-pointer -ggdb -gdwarf-2
CFLAGS += -MD
CFLAGS += -mcmodel=medany
# CFLAGS += -ffreestanding -fno-common -nostdlib -mno-relax
CFLAGS += -ffreestanding
CFLAGS += -fno-common -nostdlib
CFLAGS += -fno-builtin-strncpy -fno-builtin-strncmp -fno-builtin-strlen -fno-builtin-memset
CFLAGS += -fno-builtin-memmove -fno-builtin-memcmp -fno-builtin-log -fno-builtin-bzero
Expand All @@ -84,24 +85,21 @@ endif

LDFLAGS = -z max-page-size=4096

$K/kernel: $(OBJS) $K/kernel.ld $U/initcode
$K/kernel: $(OBJS) $K/kernel.ld
$(LD) $(LDFLAGS) -T $K/kernel.ld -o $K/kernel $(OBJS)
$(OBJDUMP) -S $K/kernel > $K/kernel.asm
$(OBJDUMP) -t $K/kernel | sed '1,/SYMBOL TABLE/d; s/ .* / /; /^$$/d' > $K/kernel.sym

$U/initcode: $U/initcode.S
$(CC) $(CFLAGS) -march=rv64g -nostdinc -I. -Ikernel -c $U/initcode.S -o $U/initcode.o
$(LD) $(LDFLAGS) -N -e start -Ttext 0 -o $U/initcode.out $U/initcode.o
$(OBJCOPY) -S -O binary $U/initcode.out $U/initcode
$(OBJDUMP) -S $U/initcode.o > $U/initcode.asm
$K/%.o: $K/%.S
$(CC) -g -c -o $@ $<

tags: $(OBJS) _init
etags *.S *.c
tags: $(OBJS)
etags kernel/*.S kernel/*.c

ULIB = $U/ulib.o $U/usys.o $U/printf.o $U/umalloc.o

_%: %.o $(ULIB)
$(LD) $(LDFLAGS) -T $U/user.ld -o $@ $^
_%: %.o $(ULIB) $U/user.ld
$(LD) $(LDFLAGS) -T $U/user.ld -o $@ $< $(ULIB)
$(OBJDUMP) -S $@ > $*.asm
$(OBJDUMP) -t $@ | sed '1,/SYMBOL TABLE/d; s/ .* / /; /^$$/d' > $*.sym

Expand All @@ -128,7 +126,7 @@ $U/dump2tests.o: $U/dump2tests.S $U/dump2tests.c $K/syscall.h
$(LD) -r $U/dump2tests.c.o $U/dump2tests.s.o -o $U/dump2tests.o

mkfs/mkfs: mkfs/mkfs.c $K/fs.h $K/param.h
gcc -Werror -Wall -I. -o mkfs/mkfs mkfs/mkfs.c
gcc -Wno-unknown-attributes -I. -o mkfs/mkfs mkfs/mkfs.c

# Prevent deletion of intermediate files, e.g. cat.o, after first build, so
# that disk image changes after first build are persistent until clean. More
Expand All @@ -153,6 +151,11 @@ UPROGS=\
$U/_grind\
$U/_wc\
$U/_zombie\
$U/_logstress\
$U/_forphan\
$U/_dorphan\

UPROGS+=\
$U/_dumptests\
$U/_dump2tests\
$U/_alloctest\
Expand All @@ -167,7 +170,7 @@ fs.img: mkfs/mkfs README $(UPROGS)
clean:
rm -f *.tex *.dvi *.idx *.aux *.log *.ind *.ilg \
*/*.o */*.d */*.asm */*.sym \
$U/initcode $U/initcode.out $K/kernel fs.img \
$K/kernel fs.img \
mkfs/mkfs .gdbinit \
$U/usys.S \
$(UPROGS)
Expand All @@ -187,7 +190,7 @@ QEMUOPTS += -global virtio-mmio.force-legacy=false
QEMUOPTS += -drive file=fs.img,if=none,format=raw,id=x0
QEMUOPTS += -device virtio-blk-device,drive=x0,bus=virtio-mmio-bus.0

qemu: $K/kernel fs.img
qemu: check-qemu-version $K/kernel fs.img
$(QEMU) $(QEMUOPTS)

.gdbinit: .gdbinit.tmpl-riscv
Expand All @@ -197,3 +200,12 @@ qemu-gdb: $K/kernel .gdbinit fs.img
@echo "*** Now run 'gdb' in another window." 1>&2
$(QEMU) $(QEMUOPTS) -S $(QEMUGDB)

print-gdbport:
@echo $(GDBPORT)

QEMU_VERSION := $(shell $(QEMU) --version | head -n 1 | sed -E 's/^QEMU emulator version ([0-9]+\.[0-9]+)\..*/\1/')
check-qemu-version:
@if [ "$(shell echo "$(QEMU_VERSION) >= $(MIN_QEMU_VERSION)" | bc)" -eq 0 ]; then \
echo "ERROR: Need qemu version >= $(MIN_QEMU_VERSION)"; \
exit 1; \
fi
30 changes: 16 additions & 14 deletions README
Original file line number Diff line number Diff line change
Expand Up @@ -14,22 +14,24 @@ locking), Cliff Frey (MP), Xiao Yu (MP), Nickolai Zeldovich, and Austin
Clements.

We are also grateful for the bug reports and patches contributed by
Takahiro Aoyagi, Marcelo Arroyo, Silas Boyd-Wickizer, Anton Burtsev,
carlclone, Ian Chen, Dan Cross, Cody Cutler, Mike CAT, Tej Chajed,
Asami Doi,Wenyang Duan, eyalz800, Nelson Elhage, Saar Ettinger, Alice
Ferrazzi, Nathaniel Filardo, flespark, Peter Froehlich, Yakir Goaron,
Shivam Handa, Matt Harvey, Bryan Henry, jaichenhengjie, Jim Huang,
Matúš Jókay, John Jolly, Alexander Kapshuk, Anders Kaseorg, kehao95,
Abhinavpatel00, Takahiro Aoyagi, Marcelo Arroyo, Hirbod Behnam, Silas
Boyd-Wickizer, Anton Burtsev, carlclone, Ian Chen, clivezeng, Dan
Cross, Cody Cutler, Mike CAT, Tej Chajed, Asami Doi,Wenyang Duan,
echtwerner, eyalz800, Nelson Elhage, Saar Ettinger, Alice Ferrazzi,
Nathaniel Filardo, flespark, Peter Froehlich, Yakir Goaron, Shivam
Handa, Matt Harvey, Bryan Henry, jaichenhengjie, Jim Huang, Matúš
Jókay, John Jolly, Alexander Kapshuk, Anders Kaseorg, kehao95,
Wolfgang Keller, Jungwoo Kim, Jonathan Kimmitt, Eddie Kohler, Vadim
Kolontsov, Austin Liew, l0stman, Pavan Maddamsetti, Imbar Marinescu,
Yandong Mao, Matan Shabtay, Hitoshi Mitake, Carmi Merimovich, Mark
Morrissey, mtasm, Joel Nider, Hayato Ohhashi, OptimisticSide,
phosphagos, Harry Porter, Greg Price, RayAndrew, Jude Rich, segfault,
Ayan Shafqat, Eldar Sehayek, Yongming Shen, Fumiya Shigemitsu, snoire,
Taojie, Cam Tenny, tyfkda, Warren Toomey, Stephen Tu, Alissa Tung,
Rafael Ubal, Amane Uehara, Pablo Ventura, Xi Wang, WaheedHafez,
Keiichi Watanabe, Lucas Wolf, Nicolas Wolovick, wxdao, Grant Wu, x653,
Jindong Zhang, Icenowy Zheng, ZhUyU1997, and Zou Chang Wei.
Yandong Mao, Matan Shabtay, Hitoshi Mitake, Carmi Merimovich,
mes900903, Mark Morrissey, mtasm, Joel Nider, Hayato Ohhashi,
OptimisticSide, papparapa, phosphagos, Harry Porter, Greg Price, Zheng
qhuo, Quancheng, RayAndrew, Jude Rich, segfault, Ayan Shafqat, Eldar
Sehayek, Yongming Shen, Fumiya Shigemitsu, snoire, Taojie, Cam Tenny,
tyfkda, Warren Toomey, Stephen Tu, Alissa Tung, Rafael Ubal, unicornx,
Amane Uehara, Pablo Ventura, Luc Videau, Xi Wang, WaheedHafez, Keiichi
Watanabe, Lucas Wolf, Nicolas Wolovick, wxdao, Grant Wu, x653, Andy
Zhang, Jindong Zhang, Icenowy Zheng, ZhUyU1997, and Zou Chang Wei.

ERROR REPORTS

Expand Down
16 changes: 10 additions & 6 deletions kernel/console.c
Original file line number Diff line number Diff line change
Expand Up @@ -58,13 +58,17 @@ struct {
int
consolewrite(int user_src, uint64 src, int n)
{
int i;

for(i = 0; i < n; i++){
char c;
if(either_copyin(&c, user_src, src+i, 1) == -1)
char buf[32];
int i = 0;

while(i < n){
int nn = sizeof(buf);
if(nn > n - i)
nn = n - i;
if(either_copyin(buf, user_src, src+i, nn) == -1)
break;
uartputc(c);
uartwrite(buf, nn);
i += nn;
}

return i;
Expand Down
26 changes: 11 additions & 15 deletions kernel/defs.h
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ void consoleintr(int);
void consputc(int);

// exec.c
int exec(char*, char**);
int kexec(char*, char**);

// file.c
struct file* filealloc(void);
Expand Down Expand Up @@ -54,11 +54,7 @@ int readi(struct inode*, int, uint64, uint, uint);
void stati(struct inode*, struct stat*);
int writei(struct inode*, int, uint64, uint, uint);
void itrunc(struct inode*);

// ramdisk.c
void ramdiskinit(void);
void ramdiskintr(void);
void ramdiskrw(struct buf*);
void ireclaim(int);

// kalloc.c
void* kalloc(void);
Expand All @@ -78,30 +74,29 @@ int piperead(struct pipe*, uint64, int);
int pipewrite(struct pipe*, uint64, int);

// printf.c
int printf(char*, ...) __attribute__ ((format (printf, 1, 2)));
int printf(char*, ...) __attribute__ ((format (printf, 1, 2)));
void panic(char*) __attribute__((noreturn));
void printfinit(void);

// proc.c
int cpuid(void);
void exit(int);
int fork(void);
void kexit(int);
int kfork(void);
int growproc(int);
void proc_mapstacks(pagetable_t);
pagetable_t proc_pagetable(struct proc *);
void proc_freepagetable(pagetable_t, uint64);
int kill(int);
int kkill(int);
int killed(struct proc*);
void setkilled(struct proc*);
struct cpu* mycpu(void);
struct cpu* getmycpu(void);
struct proc* myproc();
void procinit(void);
void scheduler(void) __attribute__((noreturn));
void sched(void);
void sleep(void*, struct spinlock*);
void userinit(void);
int wait(uint64);
int kwait(uint64);
void wakeup(void*);
void yield(void);
int either_copyout(int user_dst, uint64 dst, void *src, uint64 len);
Expand Down Expand Up @@ -147,12 +142,12 @@ extern uint ticks;
void trapinit(void);
void trapinithart(void);
extern struct spinlock tickslock;
void usertrapret(void);
void prepare_return(void);

// uart.c
void uartinit(void);
void uartintr(void);
void uartputc(int);
void uartwrite(char [], int);
void uartputc_sync(int);
int uartgetc(void);

Expand All @@ -162,7 +157,6 @@ void kvminithart(void);
void kvmmap(pagetable_t, uint64, uint64, uint64, int);
int mappages(pagetable_t, uint64, uint64, uint64, int);
pagetable_t uvmcreate(void);
void uvmfirst(pagetable_t, uchar *, uint);
uint64 uvmalloc(pagetable_t, uint64, uint64, int);
uint64 uvmdealloc(pagetable_t, uint64, uint64);
int uvmcopy(pagetable_t, pagetable_t, uint64);
Expand All @@ -174,6 +168,8 @@ uint64 walkaddr(pagetable_t, uint64);
int copyout(pagetable_t, uint64, char *, uint64);
int copyin(pagetable_t, char *, uint64, uint64);
int copyinstr(pagetable_t, char *, uint64, uint64);
int ismapped(pagetable_t, uint64);
uint64 vmfault(pagetable_t, uint64, int);

// plic.c
void plicinit(void);
Expand Down
2 changes: 1 addition & 1 deletion kernel/entry.S
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ _entry:
# set up a stack for C.
# stack0 is declared in start.c,
# with a 4096-byte stack per CPU.
# sp = stack0 + (hartid * 4096)
# sp = stack0 + ((hartid + 1) * 4096)
la sp, stack0
li a0, 1024*4
csrr a1, mhartid
Expand Down
21 changes: 14 additions & 7 deletions kernel/exec.c
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@

static int loadseg(pde_t *, uint64, struct inode *, uint, uint);

// map ELF permissions to PTE permission bits.
int flags2perm(int flags)
{
int perm = 0;
Expand All @@ -19,8 +20,11 @@ int flags2perm(int flags)
return perm;
}

//
// the implementation of the exec() system call
//
int
exec(char *path, char **argv)
kexec(char *path, char **argv)
{
char *s, *last;
int i, off;
Expand All @@ -33,16 +37,18 @@ exec(char *path, char **argv)

begin_op();

// Open the executable file.
if((ip = namei(path)) == 0){
end_op();
return -1;
}
ilock(ip);

// Check ELF header
// Read the ELF header.
if(readi(ip, 0, (uint64)&elf, 0, sizeof(elf)) != sizeof(elf))
goto bad;

// Is this really an ELF file?
if(elf.magic != ELF_MAGIC)
goto bad;

Expand Down Expand Up @@ -87,7 +93,8 @@ exec(char *path, char **argv)
sp = sz;
stackbase = sp - USERSTACK*PGSIZE;

// Push argument strings, prepare rest of stack in ustack.
// Copy argument strings into new stack, remember their
// addresses in ustack[].
for(argc = 0; argv[argc]; argc++) {
if(argc >= MAXARG)
goto bad;
Expand All @@ -101,15 +108,15 @@ exec(char *path, char **argv)
}
ustack[argc] = 0;

// push the array of argv[] pointers.
// push a copy of ustack[], the array of argv[] pointers.
sp -= (argc+1) * sizeof(uint64);
sp -= sp % 16;
if(sp < stackbase)
goto bad;
if(copyout(pagetable, sp, (char *)ustack, (argc+1)*sizeof(uint64)) < 0)
goto bad;

// arguments to user main(argc, argv)
// a0 and a1 contain arguments to user main(argc, argv)
// argc is returned via the system call return
// value, which goes in a0.
p->trapframe->a1 = sp;
Expand All @@ -124,7 +131,7 @@ exec(char *path, char **argv)
oldpagetable = p->pagetable;
p->pagetable = pagetable;
p->sz = sz;
p->trapframe->epc = elf.entry; // initial program counter = main
p->trapframe->epc = elf.entry; // initial program counter = ulib.c:start()
p->trapframe->sp = sp; // initial stack pointer
proc_freepagetable(oldpagetable, oldsz);

Expand All @@ -140,7 +147,7 @@ exec(char *path, char **argv)
return -1;
}

// Load a program segment into pagetable at virtual address va.
// Load an ELF program segment into pagetable at virtual address va.
// va must be page-aligned
// and the pages from va to va+sz must already be mapped.
// Returns 0 on success, -1 on failure.
Expand Down
2 changes: 0 additions & 2 deletions kernel/file.c
Original file line number Diff line number Diff line change
Expand Up @@ -150,8 +150,6 @@ filewrite(struct file *f, uint64 addr, int n)
// the maximum log transaction size, including
// i-node, indirect block, allocation blocks,
// and 2 blocks of slop for non-aligned writes.
// this really belongs lower down, since writei()
// might be writing a device like the console.
int max = ((MAXOPBLOCKS-1-1-2) / 2) * BSIZE;
int i = 0;
while(i < n){
Expand Down
Loading
Loading