From c51624f779142e9d9fda04aa8757e84df1d86a20 Mon Sep 17 00:00:00 2001 From: Huan <2981268462@qq.com> Date: Thu, 8 Jul 2021 16:10:09 +0100 Subject: [PATCH] 5 --- linux-0.11-lab/1/.DS_Store | Bin 0 -> 8196 bytes linux-0.11-lab/1/._.DS_Store | Bin 0 -> 4096 bytes linux-0.11-lab/1/README | 6 + .../1/Source-Insight/Linux-0.11.IAB | Bin 0 -> 102400 bytes .../1/Source-Insight/Linux-0.11.IAD | Bin 0 -> 1328 bytes .../1/Source-Insight/Linux-0.11.IMB | Bin 0 -> 81920 bytes .../1/Source-Insight/Linux-0.11.IMD | Bin 0 -> 1128 bytes .../1/Source-Insight/Linux-0.11.PFI | Bin 0 -> 412 bytes linux-0.11-lab/1/Source-Insight/Linux-0.11.PO | Bin 0 -> 776 bytes linux-0.11-lab/1/Source-Insight/Linux-0.11.PR | Bin 0 -> 32648 bytes .../1/Source-Insight/Linux-0.11.PRI | Bin 0 -> 208984 bytes linux-0.11-lab/1/Source-Insight/Linux-0.11.PS | Bin 0 -> 623496 bytes .../1/Source-Insight/Linux-0.11.SearchResults | 2 + .../1/Source-Insight/Linux-0.11.WK3 | Bin 0 -> 8851 bytes linux-0.11-lab/1/linux/.DS_Store | Bin 0 -> 14340 bytes linux-0.11-lab/1/linux/._.DS_Store | 0 linux-0.11-lab/1/linux/._execve2.patch | Bin 0 -> 4096 bytes linux-0.11-lab/1/linux/Image | Bin 0 -> 138372 bytes linux-0.11-lab/1/linux/Image.bkp | Bin 0 -> 131556 bytes linux-0.11-lab/1/linux/Makefile | 125 ++ linux-0.11-lab/1/linux/System.map | 589 +++++++++ linux-0.11-lab/1/linux/System.map.2 | 1100 +++++++++++++++++ linux-0.11-lab/1/linux/boot/bootsect | Bin 0 -> 544 bytes linux-0.11-lab/1/linux/boot/bootsect.o | Bin 0 -> 923 bytes linux-0.11-lab/1/linux/boot/bootsect.s | 260 ++++ linux-0.11-lab/1/linux/boot/head.o | Bin 0 -> 27012 bytes linux-0.11-lab/1/linux/boot/head.s | 240 ++++ linux-0.11-lab/1/linux/boot/setup | Bin 0 -> 344 bytes linux-0.11-lab/1/linux/boot/setup.o | Bin 0 -> 596 bytes linux-0.11-lab/1/linux/boot/setup.s | 231 ++++ linux-0.11-lab/1/linux/execve2.patch | 41 + linux-0.11-lab/1/linux/fs/Makefile | 101 ++ linux-0.11-lab/1/linux/fs/bitmap.c | 168 +++ linux-0.11-lab/1/linux/fs/bitmap.o | Bin 0 -> 10280 bytes linux-0.11-lab/1/linux/fs/block_dev.c | 73 ++ linux-0.11-lab/1/linux/fs/block_dev.o | Bin 0 -> 7296 bytes linux-0.11-lab/1/linux/fs/buffer.c | 384 ++++++ linux-0.11-lab/1/linux/fs/buffer.o | Bin 0 -> 13348 bytes linux-0.11-lab/1/linux/fs/char_dev.c | 104 ++ linux-0.11-lab/1/linux/fs/char_dev.o | Bin 0 -> 8288 bytes linux-0.11-lab/1/linux/fs/exec.c | 542 ++++++++ linux-0.11-lab/1/linux/fs/exec.o | Bin 0 -> 19528 bytes linux-0.11-lab/1/linux/fs/fcntl.c | 75 ++ linux-0.11-lab/1/linux/fs/fcntl.o | Bin 0 -> 6748 bytes linux-0.11-lab/1/linux/fs/file_dev.c | 90 ++ linux-0.11-lab/1/linux/fs/file_dev.o | Bin 0 -> 7828 bytes linux-0.11-lab/1/linux/fs/file_table.c | 9 + linux-0.11-lab/1/linux/fs/file_table.o | Bin 0 -> 2644 bytes linux-0.11-lab/1/linux/fs/fs.o | Bin 0 -> 149888 bytes linux-0.11-lab/1/linux/fs/inode.c | 340 +++++ linux-0.11-lab/1/linux/fs/inode.o | Bin 0 -> 14072 bytes linux-0.11-lab/1/linux/fs/ioctl.c | 46 + linux-0.11-lab/1/linux/fs/ioctl.o | Bin 0 -> 5828 bytes linux-0.11-lab/1/linux/fs/namei.c | 908 ++++++++++++++ linux-0.11-lab/1/linux/fs/namei.o | Bin 0 -> 23120 bytes linux-0.11-lab/1/linux/fs/open.c | 208 ++++ linux-0.11-lab/1/linux/fs/open.o | Bin 0 -> 11192 bytes linux-0.11-lab/1/linux/fs/pipe.c | 111 ++ linux-0.11-lab/1/linux/fs/pipe.o | Bin 0 -> 8104 bytes linux-0.11-lab/1/linux/fs/read_write.c | 103 ++ linux-0.11-lab/1/linux/fs/read_write.o | Bin 0 -> 7520 bytes linux-0.11-lab/1/linux/fs/select.c | 10 + linux-0.11-lab/1/linux/fs/select.o | Bin 0 -> 1776 bytes linux-0.11-lab/1/linux/fs/stat.c | 66 + linux-0.11-lab/1/linux/fs/stat.o | Bin 0 -> 7212 bytes linux-0.11-lab/1/linux/fs/super.c | 282 +++++ linux-0.11-lab/1/linux/fs/super.o | Bin 0 -> 12284 bytes linux-0.11-lab/1/linux/fs/truncate.c | 65 + linux-0.11-lab/1/linux/fs/truncate.o | Bin 0 -> 6848 bytes linux-0.11-lab/1/linux/include/.DS_Store | Bin 0 -> 6148 bytes linux-0.11-lab/1/linux/include/._.DS_Store | Bin 0 -> 4096 bytes linux-0.11-lab/1/linux/include/._new.h | Bin 0 -> 4096 bytes linux-0.11-lab/1/linux/include/._unistd.h | Bin 0 -> 4096 bytes linux-0.11-lab/1/linux/include/a.out.h | 220 ++++ linux-0.11-lab/1/linux/include/asm/io.h | 24 + linux-0.11-lab/1/linux/include/asm/memory.h | 15 + linux-0.11-lab/1/linux/include/asm/segment.h | 65 + linux-0.11-lab/1/linux/include/asm/system.h | 66 + linux-0.11-lab/1/linux/include/const.h | 15 + linux-0.11-lab/1/linux/include/ctype.h | 34 + linux-0.11-lab/1/linux/include/errno.h | 60 + linux-0.11-lab/1/linux/include/fcntl.h | 55 + linux-0.11-lab/1/linux/include/linux/._sys.h | Bin 0 -> 4096 bytes linux-0.11-lab/1/linux/include/linux/config.h | 48 + linux-0.11-lab/1/linux/include/linux/fdreg.h | 71 ++ linux-0.11-lab/1/linux/include/linux/fs.h | 202 +++ linux-0.11-lab/1/linux/include/linux/hdreg.h | 65 + linux-0.11-lab/1/linux/include/linux/head.h | 20 + linux-0.11-lab/1/linux/include/linux/kernel.h | 22 + linux-0.11-lab/1/linux/include/linux/mm.h | 10 + linux-0.11-lab/1/linux/include/linux/sched.h | 239 ++++ linux-0.11-lab/1/linux/include/linux/sys.h | 117 ++ linux-0.11-lab/1/linux/include/linux/tty.h | 77 ++ linux-0.11-lab/1/linux/include/new.h | 30 + linux-0.11-lab/1/linux/include/signal.h | 68 + linux-0.11-lab/1/linux/include/stdarg.h | 28 + linux-0.11-lab/1/linux/include/stddef.h | 19 + linux-0.11-lab/1/linux/include/string.h | 405 ++++++ linux-0.11-lab/1/linux/include/sys/stat.h | 60 + linux-0.11-lab/1/linux/include/sys/times.h | 15 + linux-0.11-lab/1/linux/include/sys/types.h | 46 + linux-0.11-lab/1/linux/include/sys/utsname.h | 16 + linux-0.11-lab/1/linux/include/sys/wait.h | 23 + linux-0.11-lab/1/linux/include/termios.h | 228 ++++ linux-0.11-lab/1/linux/include/time.h | 42 + linux-0.11-lab/1/linux/include/unistd.h | 278 +++++ linux-0.11-lab/1/linux/include/utime.h | 13 + linux-0.11-lab/1/linux/init/main.c | 216 ++++ linux-0.11-lab/1/linux/init/main.c.rej | 12 + linux-0.11-lab/1/linux/init/main.o | Bin 0 -> 12220 bytes linux-0.11-lab/1/linux/kernel/Makefile | 83 ++ linux-0.11-lab/1/linux/kernel/asm.o | Bin 0 -> 1740 bytes linux-0.11-lab/1/linux/kernel/asm.s | 146 +++ .../1/linux/kernel/blk_drv/Makefile | 58 + linux-0.11-lab/1/linux/kernel/blk_drv/blk.h | 140 +++ .../1/linux/kernel/blk_drv/blk_drv.a | Bin 0 -> 52212 bytes .../1/linux/kernel/blk_drv/floppy.c | 463 +++++++ .../1/linux/kernel/blk_drv/floppy.o | Bin 0 -> 16612 bytes linux-0.11-lab/1/linux/kernel/blk_drv/hd.c | 351 ++++++ linux-0.11-lab/1/linux/kernel/blk_drv/hd.o | Bin 0 -> 15520 bytes .../1/linux/kernel/blk_drv/ll_rw_blk.c | 165 +++ .../1/linux/kernel/blk_drv/ll_rw_blk.o | Bin 0 -> 8740 bytes .../1/linux/kernel/blk_drv/ramdisk.c | 126 ++ .../1/linux/kernel/blk_drv/ramdisk.o | Bin 0 -> 10664 bytes .../1/linux/kernel/chr_drv/Makefile | 68 + .../1/linux/kernel/chr_drv/chr_drv.a | Bin 0 -> 68902 bytes .../1/linux/kernel/chr_drv/console.c | 710 +++++++++++ .../1/linux/kernel/chr_drv/console.o | Bin 0 -> 20896 bytes .../1/linux/kernel/chr_drv/keyboard.2.o | Bin 0 -> 6024 bytes .../1/linux/kernel/chr_drv/keyboard.2.s | 466 +++++++ .../1/linux/kernel/chr_drv/keyboard.S | 588 +++++++++ linux-0.11-lab/1/linux/kernel/chr_drv/rs_io.o | Bin 0 -> 1320 bytes linux-0.11-lab/1/linux/kernel/chr_drv/rs_io.s | 147 +++ .../1/linux/kernel/chr_drv/serial.c | 59 + .../1/linux/kernel/chr_drv/serial.o | Bin 0 -> 6752 bytes .../1/linux/kernel/chr_drv/tty_io.c | 349 ++++++ .../1/linux/kernel/chr_drv/tty_io.o | Bin 0 -> 22504 bytes .../1/linux/kernel/chr_drv/tty_ioctl.c | 204 +++ .../1/linux/kernel/chr_drv/tty_ioctl.o | Bin 0 -> 10648 bytes linux-0.11-lab/1/linux/kernel/exit.c | 197 +++ linux-0.11-lab/1/linux/kernel/exit.o | Bin 0 -> 11164 bytes linux-0.11-lab/1/linux/kernel/fork.c | 148 +++ linux-0.11-lab/1/linux/kernel/fork.o | Bin 0 -> 9640 bytes linux-0.11-lab/1/linux/kernel/kernel.o | Bin 0 -> 84402 bytes linux-0.11-lab/1/linux/kernel/math/Makefile | 43 + linux-0.11-lab/1/linux/kernel/math/math.a | Bin 0 -> 6628 bytes .../1/linux/kernel/math/math_emulate.c | 42 + .../1/linux/kernel/math/math_emulate.o | Bin 0 -> 6464 bytes linux-0.11-lab/1/linux/kernel/mktime.c | 58 + linux-0.11-lab/1/linux/kernel/mktime.o | Bin 0 -> 2872 bytes linux-0.11-lab/1/linux/kernel/panic.c | 24 + linux-0.11-lab/1/linux/kernel/panic.o | Bin 0 -> 5424 bytes linux-0.11-lab/1/linux/kernel/printk.c | 41 + linux-0.11-lab/1/linux/kernel/printk.o | Bin 0 -> 2424 bytes linux-0.11-lab/1/linux/kernel/sched.c | 412 ++++++ linux-0.11-lab/1/linux/kernel/sched.o | Bin 0 -> 22944 bytes linux-0.11-lab/1/linux/kernel/signal.c | 129 ++ linux-0.11-lab/1/linux/kernel/signal.o | Bin 0 -> 8960 bytes linux-0.11-lab/1/linux/kernel/sys.c | 292 +++++ linux-0.11-lab/1/linux/kernel/sys.o | Bin 0 -> 13088 bytes linux-0.11-lab/1/linux/kernel/system_call.o | Bin 0 -> 2640 bytes linux-0.11-lab/1/linux/kernel/system_call.s | 298 +++++ linux-0.11-lab/1/linux/kernel/traps.c | 208 ++++ linux-0.11-lab/1/linux/kernel/traps.o | Bin 0 -> 12972 bytes linux-0.11-lab/1/linux/kernel/vsprintf.c | 233 ++++ linux-0.11-lab/1/linux/kernel/vsprintf.o | Bin 0 -> 6156 bytes linux-0.11-lab/1/linux/mm/Makefile | 38 + linux-0.11-lab/1/linux/mm/memory.c | 470 +++++++ linux-0.11-lab/1/linux/mm/memory.o | Bin 0 -> 13828 bytes linux-0.11-lab/1/linux/mm/mm.o | Bin 0 -> 13954 bytes linux-0.11-lab/1/linux/mm/page.o | Bin 0 -> 640 bytes linux-0.11-lab/1/linux/mm/page.s | 40 + linux-0.11-lab/1/linux/tools/build | Bin 0 -> 15144 bytes linux-0.11-lab/1/linux/tools/build.c | 171 +++ linux-0.11-lab/1/linux/tools/system | Bin 0 -> 300866 bytes 175 files changed, 16170 insertions(+) create mode 100755 linux-0.11-lab/1/.DS_Store create mode 100755 linux-0.11-lab/1/._.DS_Store create mode 100644 linux-0.11-lab/1/README create mode 100644 linux-0.11-lab/1/Source-Insight/Linux-0.11.IAB create mode 100644 linux-0.11-lab/1/Source-Insight/Linux-0.11.IAD create mode 100644 linux-0.11-lab/1/Source-Insight/Linux-0.11.IMB create mode 100644 linux-0.11-lab/1/Source-Insight/Linux-0.11.IMD create mode 100644 linux-0.11-lab/1/Source-Insight/Linux-0.11.PFI create mode 100644 linux-0.11-lab/1/Source-Insight/Linux-0.11.PO create mode 100644 linux-0.11-lab/1/Source-Insight/Linux-0.11.PR create mode 100755 linux-0.11-lab/1/Source-Insight/Linux-0.11.PRI create mode 100644 linux-0.11-lab/1/Source-Insight/Linux-0.11.PS create mode 100644 linux-0.11-lab/1/Source-Insight/Linux-0.11.SearchResults create mode 100755 linux-0.11-lab/1/Source-Insight/Linux-0.11.WK3 create mode 100755 linux-0.11-lab/1/linux/.DS_Store create mode 100755 linux-0.11-lab/1/linux/._.DS_Store create mode 100755 linux-0.11-lab/1/linux/._execve2.patch create mode 100644 linux-0.11-lab/1/linux/Image create mode 100644 linux-0.11-lab/1/linux/Image.bkp create mode 100644 linux-0.11-lab/1/linux/Makefile create mode 100644 linux-0.11-lab/1/linux/System.map create mode 100644 linux-0.11-lab/1/linux/System.map.2 create mode 100755 linux-0.11-lab/1/linux/boot/bootsect create mode 100644 linux-0.11-lab/1/linux/boot/bootsect.o create mode 100644 linux-0.11-lab/1/linux/boot/bootsect.s create mode 100644 linux-0.11-lab/1/linux/boot/head.o create mode 100644 linux-0.11-lab/1/linux/boot/head.s create mode 100755 linux-0.11-lab/1/linux/boot/setup create mode 100644 linux-0.11-lab/1/linux/boot/setup.o create mode 100644 linux-0.11-lab/1/linux/boot/setup.s create mode 100755 linux-0.11-lab/1/linux/execve2.patch create mode 100644 linux-0.11-lab/1/linux/fs/Makefile create mode 100644 linux-0.11-lab/1/linux/fs/bitmap.c create mode 100644 linux-0.11-lab/1/linux/fs/bitmap.o create mode 100644 linux-0.11-lab/1/linux/fs/block_dev.c create mode 100644 linux-0.11-lab/1/linux/fs/block_dev.o create mode 100644 linux-0.11-lab/1/linux/fs/buffer.c create mode 100644 linux-0.11-lab/1/linux/fs/buffer.o create mode 100644 linux-0.11-lab/1/linux/fs/char_dev.c create mode 100644 linux-0.11-lab/1/linux/fs/char_dev.o create mode 100755 linux-0.11-lab/1/linux/fs/exec.c create mode 100644 linux-0.11-lab/1/linux/fs/exec.o create mode 100644 linux-0.11-lab/1/linux/fs/fcntl.c create mode 100644 linux-0.11-lab/1/linux/fs/fcntl.o create mode 100644 linux-0.11-lab/1/linux/fs/file_dev.c create mode 100644 linux-0.11-lab/1/linux/fs/file_dev.o create mode 100644 linux-0.11-lab/1/linux/fs/file_table.c create mode 100644 linux-0.11-lab/1/linux/fs/file_table.o create mode 100644 linux-0.11-lab/1/linux/fs/fs.o create mode 100644 linux-0.11-lab/1/linux/fs/inode.c create mode 100644 linux-0.11-lab/1/linux/fs/inode.o create mode 100644 linux-0.11-lab/1/linux/fs/ioctl.c create mode 100644 linux-0.11-lab/1/linux/fs/ioctl.o create mode 100755 linux-0.11-lab/1/linux/fs/namei.c create mode 100644 linux-0.11-lab/1/linux/fs/namei.o create mode 100644 linux-0.11-lab/1/linux/fs/open.c create mode 100644 linux-0.11-lab/1/linux/fs/open.o create mode 100644 linux-0.11-lab/1/linux/fs/pipe.c create mode 100644 linux-0.11-lab/1/linux/fs/pipe.o create mode 100644 linux-0.11-lab/1/linux/fs/read_write.c create mode 100644 linux-0.11-lab/1/linux/fs/read_write.o create mode 100644 linux-0.11-lab/1/linux/fs/select.c create mode 100644 linux-0.11-lab/1/linux/fs/select.o create mode 100644 linux-0.11-lab/1/linux/fs/stat.c create mode 100644 linux-0.11-lab/1/linux/fs/stat.o create mode 100644 linux-0.11-lab/1/linux/fs/super.c create mode 100644 linux-0.11-lab/1/linux/fs/super.o create mode 100644 linux-0.11-lab/1/linux/fs/truncate.c create mode 100644 linux-0.11-lab/1/linux/fs/truncate.o create mode 100755 linux-0.11-lab/1/linux/include/.DS_Store create mode 100755 linux-0.11-lab/1/linux/include/._.DS_Store create mode 100755 linux-0.11-lab/1/linux/include/._new.h create mode 100755 linux-0.11-lab/1/linux/include/._unistd.h create mode 100755 linux-0.11-lab/1/linux/include/a.out.h create mode 100755 linux-0.11-lab/1/linux/include/asm/io.h create mode 100755 linux-0.11-lab/1/linux/include/asm/memory.h create mode 100755 linux-0.11-lab/1/linux/include/asm/segment.h create mode 100755 linux-0.11-lab/1/linux/include/asm/system.h create mode 100755 linux-0.11-lab/1/linux/include/const.h create mode 100755 linux-0.11-lab/1/linux/include/ctype.h create mode 100755 linux-0.11-lab/1/linux/include/errno.h create mode 100755 linux-0.11-lab/1/linux/include/fcntl.h create mode 100755 linux-0.11-lab/1/linux/include/linux/._sys.h create mode 100755 linux-0.11-lab/1/linux/include/linux/config.h create mode 100755 linux-0.11-lab/1/linux/include/linux/fdreg.h create mode 100755 linux-0.11-lab/1/linux/include/linux/fs.h create mode 100755 linux-0.11-lab/1/linux/include/linux/hdreg.h create mode 100755 linux-0.11-lab/1/linux/include/linux/head.h create mode 100755 linux-0.11-lab/1/linux/include/linux/kernel.h create mode 100755 linux-0.11-lab/1/linux/include/linux/mm.h create mode 100755 linux-0.11-lab/1/linux/include/linux/sched.h create mode 100755 linux-0.11-lab/1/linux/include/linux/sys.h create mode 100755 linux-0.11-lab/1/linux/include/linux/tty.h create mode 100755 linux-0.11-lab/1/linux/include/new.h create mode 100755 linux-0.11-lab/1/linux/include/signal.h create mode 100755 linux-0.11-lab/1/linux/include/stdarg.h create mode 100755 linux-0.11-lab/1/linux/include/stddef.h create mode 100755 linux-0.11-lab/1/linux/include/string.h create mode 100755 linux-0.11-lab/1/linux/include/sys/stat.h create mode 100755 linux-0.11-lab/1/linux/include/sys/times.h create mode 100755 linux-0.11-lab/1/linux/include/sys/types.h create mode 100755 linux-0.11-lab/1/linux/include/sys/utsname.h create mode 100755 linux-0.11-lab/1/linux/include/sys/wait.h create mode 100755 linux-0.11-lab/1/linux/include/termios.h create mode 100755 linux-0.11-lab/1/linux/include/time.h create mode 100755 linux-0.11-lab/1/linux/include/unistd.h create mode 100755 linux-0.11-lab/1/linux/include/utime.h create mode 100644 linux-0.11-lab/1/linux/init/main.c create mode 100644 linux-0.11-lab/1/linux/init/main.c.rej create mode 100644 linux-0.11-lab/1/linux/init/main.o create mode 100644 linux-0.11-lab/1/linux/kernel/Makefile create mode 100644 linux-0.11-lab/1/linux/kernel/asm.o create mode 100644 linux-0.11-lab/1/linux/kernel/asm.s create mode 100644 linux-0.11-lab/1/linux/kernel/blk_drv/Makefile create mode 100644 linux-0.11-lab/1/linux/kernel/blk_drv/blk.h create mode 100644 linux-0.11-lab/1/linux/kernel/blk_drv/blk_drv.a create mode 100644 linux-0.11-lab/1/linux/kernel/blk_drv/floppy.c create mode 100644 linux-0.11-lab/1/linux/kernel/blk_drv/floppy.o create mode 100644 linux-0.11-lab/1/linux/kernel/blk_drv/hd.c create mode 100644 linux-0.11-lab/1/linux/kernel/blk_drv/hd.o create mode 100644 linux-0.11-lab/1/linux/kernel/blk_drv/ll_rw_blk.c create mode 100644 linux-0.11-lab/1/linux/kernel/blk_drv/ll_rw_blk.o create mode 100644 linux-0.11-lab/1/linux/kernel/blk_drv/ramdisk.c create mode 100644 linux-0.11-lab/1/linux/kernel/blk_drv/ramdisk.o create mode 100644 linux-0.11-lab/1/linux/kernel/chr_drv/Makefile create mode 100644 linux-0.11-lab/1/linux/kernel/chr_drv/chr_drv.a create mode 100644 linux-0.11-lab/1/linux/kernel/chr_drv/console.c create mode 100644 linux-0.11-lab/1/linux/kernel/chr_drv/console.o create mode 100644 linux-0.11-lab/1/linux/kernel/chr_drv/keyboard.2.o create mode 100644 linux-0.11-lab/1/linux/kernel/chr_drv/keyboard.2.s create mode 100644 linux-0.11-lab/1/linux/kernel/chr_drv/keyboard.S create mode 100644 linux-0.11-lab/1/linux/kernel/chr_drv/rs_io.o create mode 100644 linux-0.11-lab/1/linux/kernel/chr_drv/rs_io.s create mode 100644 linux-0.11-lab/1/linux/kernel/chr_drv/serial.c create mode 100644 linux-0.11-lab/1/linux/kernel/chr_drv/serial.o create mode 100644 linux-0.11-lab/1/linux/kernel/chr_drv/tty_io.c create mode 100644 linux-0.11-lab/1/linux/kernel/chr_drv/tty_io.o create mode 100644 linux-0.11-lab/1/linux/kernel/chr_drv/tty_ioctl.c create mode 100644 linux-0.11-lab/1/linux/kernel/chr_drv/tty_ioctl.o create mode 100644 linux-0.11-lab/1/linux/kernel/exit.c create mode 100644 linux-0.11-lab/1/linux/kernel/exit.o create mode 100644 linux-0.11-lab/1/linux/kernel/fork.c create mode 100644 linux-0.11-lab/1/linux/kernel/fork.o create mode 100644 linux-0.11-lab/1/linux/kernel/kernel.o create mode 100644 linux-0.11-lab/1/linux/kernel/math/Makefile create mode 100644 linux-0.11-lab/1/linux/kernel/math/math.a create mode 100644 linux-0.11-lab/1/linux/kernel/math/math_emulate.c create mode 100644 linux-0.11-lab/1/linux/kernel/math/math_emulate.o create mode 100644 linux-0.11-lab/1/linux/kernel/mktime.c create mode 100644 linux-0.11-lab/1/linux/kernel/mktime.o create mode 100644 linux-0.11-lab/1/linux/kernel/panic.c create mode 100644 linux-0.11-lab/1/linux/kernel/panic.o create mode 100644 linux-0.11-lab/1/linux/kernel/printk.c create mode 100644 linux-0.11-lab/1/linux/kernel/printk.o create mode 100644 linux-0.11-lab/1/linux/kernel/sched.c create mode 100644 linux-0.11-lab/1/linux/kernel/sched.o create mode 100644 linux-0.11-lab/1/linux/kernel/signal.c create mode 100644 linux-0.11-lab/1/linux/kernel/signal.o create mode 100644 linux-0.11-lab/1/linux/kernel/sys.c create mode 100644 linux-0.11-lab/1/linux/kernel/sys.o create mode 100644 linux-0.11-lab/1/linux/kernel/system_call.o create mode 100755 linux-0.11-lab/1/linux/kernel/system_call.s create mode 100644 linux-0.11-lab/1/linux/kernel/traps.c create mode 100644 linux-0.11-lab/1/linux/kernel/traps.o create mode 100644 linux-0.11-lab/1/linux/kernel/vsprintf.c create mode 100644 linux-0.11-lab/1/linux/kernel/vsprintf.o create mode 100644 linux-0.11-lab/1/linux/mm/Makefile create mode 100755 linux-0.11-lab/1/linux/mm/memory.c create mode 100644 linux-0.11-lab/1/linux/mm/memory.o create mode 100644 linux-0.11-lab/1/linux/mm/mm.o create mode 100644 linux-0.11-lab/1/linux/mm/page.o create mode 100644 linux-0.11-lab/1/linux/mm/page.s create mode 100755 linux-0.11-lab/1/linux/tools/build create mode 100644 linux-0.11-lab/1/linux/tools/build.c create mode 100755 linux-0.11-lab/1/linux/tools/system diff --git a/linux-0.11-lab/1/.DS_Store b/linux-0.11-lab/1/.DS_Store new file mode 100755 index 0000000000000000000000000000000000000000..e0e0a4e63f9c13035761a9aec92441548944640d GIT binary patch literal 8196 zcmeHMU2GIp6u#e5=!^_>z|z)n3o8{0SYd0SEyT+9&x(c6*uQP5mff8x9huJ5o!M<^ zDJcfyi-{;keK5gj)CUs(f{$R-2aWn-BqBWcV0c%i@!1ti;V^9n0!+T+=fhdm!ltwxF zf3aaz&AG;72CZf0jW$}5mRifL9USM&xP3;}C9F!sg@f|B)#cH9Hf`Inb9YnAr4n_` z+B-`XWso9hd*+B~WP2w}-5VW9xf#ROP5VfH-gM2hW%SsoF=GvCWZBoMxJ%QLxwQFI z&h(C{Rg&b7R<75SA)R({z|r|?y84kM=5JiDX@|I^HEU3-2MU|3HKoU;2&k!G;(axW z(sPttjmj59VyuDHS2Lwhyt32t_O z%JmM88#Zm}i@BNEFo&IF&#|-Y zJiEXyvM<@U><9J}`;}c|f3m;W-(Zlj7NuB+GHgH%wqpn4*o}5Pj1F|67yU?L0BIb7 zi6?Os9;R>{GdO`~@jPC@i#UVV@D|?2J9r--;}d*}&+s+A!)1JrEBFz=;5Ym(b{Q#< zcz?kGf%t>)x~G DHSqoW3!MqdtkZ-tr{AvRW{AU0Hc-)3)t(jZH0ccYeX`o=3;) z8R*ka@XF^~flvNDzeN1LJ6fr1DA0f5W6?_tH6|tgK&ZuH_QvSF5|K-l{7a=ex>Y9n zs}R!a=>3wUMuaRLeLyD0tILFJm(m~+x7FoBx<`3XCibgELb_LJmWbr)3L&jj+GSZ~ zOS1J}x%v&e%6?|o5J53k5l1!R=N95-JrX`QA4Mk)ppW=DfI$qwzz9Z(qnx2Rf= zwjBEijTX2)Um?7@c@bD9Ojq#yzkTWN|2J=gq2(|FVFdp32%xB~yRC)HEcJ@!xps`| zVXD0Fd9wn26>9u+oX}6l3FrPWq<)O1a-BqgvjS;^%K!c$V8PGg@ca+Yf1ilAS@RDI C0tyWP literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/._.DS_Store b/linux-0.11-lab/1/._.DS_Store new file mode 100755 index 0000000000000000000000000000000000000000..e7e1f8ca7a8bfcad31be4fb370b8c45f3a3824bc GIT binary patch literal 4096 zcmZQz6=P>$Vqox1Ojhs@R)|o50+1L3ClDJkFz{^v(m+1nBL)UWIhYCu0iY;W;207T z#31Cp9HN7v0;{4?!O;*H4S~@R7!85Z5Eu=C(GVC7fzc2c4S~@R7!85Z5TJ4hFapg3 zVK9&j$;d2LC`v8PFD*(=RY=P(%2vqCD@n~O$;{77%*m-#$Vp8rQAo;3%*zILb)mY3 QG==JaxL0HtcSMX~>L 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 X+E}E5VH>Ng(M~HVI#}YIPA>QZN3SCK literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/Source-Insight/Linux-0.11.PO b/linux-0.11-lab/1/Source-Insight/Linux-0.11.PO new file mode 100644 index 0000000000000000000000000000000000000000..de8db453c6bceca6363a1974df88a64caed7c9e8 GIT binary patch literal 776 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 >LdwT?$NcJnp;7Il?Z10x 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 ZnP<(9Ox^sRyj^ZyQ^(&fr!Q^I{{xPUk!%0} literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/Source-Insight/Linux-0.11.PS b/linux-0.11-lab/1/Source-Insight/Linux-0.11.PS new file mode 100644 index 0000000000000000000000000000000000000000..2c515c4dd3f2da9176ef09bd338843664bd433cf GIT binary patch literal 623496 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

gTMo^M<*{ia#Sx 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 Cri=yv literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/Makefile b/linux-0.11-lab/1/linux/Makefile new file mode 100644 index 0000000..ecbcf30 --- /dev/null +++ b/linux-0.11-lab/1/linux/Makefile @@ -0,0 +1,125 @@ +# +# if you want the ram-disk device, define this to be the +# size in blocks. +# +RAMDISK = #-DRAMDISK=512 + +AS86 =as86 -0 -a +LD86 =ld86 -0 + +AS =as +LD =ld +LDFLAGS =-m elf_i386 -Ttext 0 -e startup_32 -Map=System.map.2 -N +CC =gcc -march=i386 $(RAMDISK) +CFLAGS =-w -g -fstrength-reduce -fomit-frame-pointer -fno-stack-protector -mcld +CPP =cpp -nostdinc -Iinclude + +# +# ROOT_DEV specifies the default root-device when making the image. +# This can be either FLOPPY, /dev/xxxx or empty, in which case the +# default of /dev/hd6 is used by 'build'. +# +ROOT_DEV= + +ARCHIVES=kernel/kernel.o mm/mm.o fs/fs.o +DRIVERS =kernel/blk_drv/blk_drv.a kernel/chr_drv/chr_drv.a +MATH =kernel/math/math.a +LIBS =lib/lib.a + +.c.s: + $(CC) $(CFLAGS) \ + -nostdinc -Iinclude -S -o $*.s $< +.s.o: + $(AS) -o $*.o $< +.c.o: + $(CC) $(CFLAGS) \ + -nostdinc -Iinclude -c -o $*.o $< + +all: Image + +Image: boot/bootsect boot/setup tools/system tools/build + cp -f tools/system system.tmp + strip system.tmp + tools/build boot/bootsect boot/setup system.tmp $(ROOT_DEV) > Image + rm -f system.tmp + sync + +disk: Image + dd bs=8192 if=Image of=/dev/PS0 + +tools/build: tools/build.c + $(CC) $(CFLAGS) \ + -o tools/build tools/build.c + +boot/head.o: boot/head.s + +tools/system: boot/head.o init/main.o \ + $(ARCHIVES) $(DRIVERS) $(MATH) $(LIBS) + $(LD) $(LDFLAGS) boot/head.o init/main.o \ + $(ARCHIVES) \ + $(DRIVERS) \ + $(MATH) \ + $(LIBS) \ + -o tools/system + nm tools/system | grep -v '\(compiled\)\|\(\.o$$\)\|\( [aUw]\)\|\(\.\.ng$$\)\|\(LASH[RL]DI\)' | sort >System.map + +kernel/math/math.a: FORCE + (cd kernel/math; make) + +kernel/blk_drv/blk_drv.a: FORCE + (cd kernel/blk_drv; make) + +kernel/chr_drv/chr_drv.a: FORCE + (cd kernel/chr_drv; make) + +kernel/kernel.o: FORCE + (cd kernel; make) + +mm/mm.o: FORCE + (cd mm; make) + +fs/fs.o: FORCE + (cd fs; make) + +lib/lib.a: FORCE + (cd lib; make) + +FORCE: + +boot/setup: boot/setup.s + $(AS86) -o boot/setup.o boot/setup.s + $(LD86) -s -o boot/setup boot/setup.o + +boot/bootsect: boot/bootsect.s + $(AS86) -o boot/bootsect.o boot/bootsect.s + $(LD86) -s -o boot/bootsect boot/bootsect.o + +tmp.s: boot/bootsect.s tools/system + (echo -n "SYSSIZE = (";ls -l tools/system | grep system \ + | cut -c25-31 | tr '\012' ' '; echo "+ 15 ) / 16") > tmp.s + cat boot/bootsect.s >> tmp.s + +clean: + rm -f Image System.map tmp_make core System.map.2 + rm -f boot/bootsect boot/setup + rm -f init/*.o tools/system tools/build boot/*.o + (cd mm;make clean) + (cd fs;make clean) + (cd kernel;make clean) + (cd lib;make clean) + +dep: + sed '/\#\#\# Dependencies/q' < Makefile > tmp_make + (for i in init/*.c;do echo -n "init/";$(CPP) -M $$i;done) >> tmp_make + cp tmp_make Makefile + (cd fs; make dep) + (cd kernel; make dep) + (cd mm; make dep) + +### Dependencies: +init/main.o : init/main.c include/unistd.h include/sys/stat.h \ + include/sys/types.h include/sys/times.h include/sys/utsname.h \ + include/utime.h include/time.h include/linux/tty.h include/termios.h \ + include/linux/sched.h include/linux/head.h include/linux/fs.h \ + include/linux/mm.h include/signal.h include/asm/system.h include/asm/io.h \ + include/stddef.h include/stdarg.h include/fcntl.h diff --git a/linux-0.11-lab/1/linux/System.map b/linux-0.11-lab/1/linux/System.map new file mode 100644 index 0000000..3b587ae --- /dev/null +++ b/linux-0.11-lab/1/linux/System.map @@ -0,0 +1,589 @@ +00000000 T pg_dir +00000000 T startup_32 +0000005a t check_x87 +00000073 t setup_idt +00000090 t rp_sidt +000000a3 t setup_gdt +00001000 t pg0 +00002000 t pg1 +00003000 t pg2 +00004000 t pg3 +00005000 T tmp_floppy_area +00005412 t L6 +00005414 t int_msg +00005428 t ignore_int +00005450 t setup_paging +000054ae t idt_descr +000054b6 t gdt_descr +000054c0 T idt +00005cc0 T gdt +000064c0 T fork +000064ef T pause +0000651e T setup +00006555 T sync +00006584 t time_init +00006799 T main +0000690c t printf +0000695b T init +00006bd3 T print_nr +00006c04 T show_task +00006c89 T show_stat +00006ccf T math_state_restore +00006d2d T schedule +00006edf T sys_pause +00006ef5 T sleep_on +00006f54 T interruptible_sleep_on +0000700f T ticks_to_floppy_on +000070da T floppy_on +00007109 T floppy_off +00007119 T do_floppy_timer +00007311 T do_timer +00007400 T sys_alarm +0000747f T sys_getpid +0000748b T sys_getppid +00007497 T sys_getuid +000074a6 T sys_geteuid +000074b6 T sys_getgid +000074c6 T sys_getegid +000074d5 T sys_nice +00007500 T sched_init +00007690 t bad_sys_call +00007698 t reschedule +000076a4 T system_call +000076df t ret_from_sys_call +00007728 T coprocessor_error +0000774a T device_not_available +00007784 T timer_interrupt +000077bc T sys_execve +000077cc T sys_execve2 +000077dc T sys_fork +000077f4 T hd_interrupt +00007830 T floppy_interrupt +00007866 T parallel_interrupt +0000786d t _get_base +0000789f t die +00007a81 T do_double_fault +00007aa4 T do_general_protection +00007ac7 T do_divide_error +00007aea T do_int3 +00007bb2 T do_nmi +00007bd5 T do_debug +00007bf8 T do_overflow +00007c1b T do_bounds +00007c3e T do_invalid_op +00007c61 T do_device_not_available +00007c84 T do_coprocessor_segment_overrun +00007ca7 T do_invalid_TSS +00007cca T do_segment_not_present +00007ced T do_stack_segment +00007d10 T do_coprocessor_error +00007d44 T do_reserved +00007d67 T trap_init +0000804b T divide_error +00008050 t no_error_code +00008080 T debug +00008087 T nmi +0000808e T int3 +00008095 T overflow +0000809c T bounds +000080a3 T invalid_op +000080aa T coprocessor_segment_overrun +000080b1 T reserved +000080b8 T irq13 +000080cd T double_fault +000080d2 t error_code +00008104 T invalid_TSS +0000810b T segment_not_present +00008112 T stack_segment +00008119 T general_protection +00008120 t _get_base +00008152 T verify_area +000081b9 T copy_mem +00008313 T copy_process +000087c0 T find_empty_process +00008854 T panic +0000888f T printk +000088e0 t skip_atoi +0000893b t number +00008bac T vsprintf +00009038 t get_fs_long +0000904e t put_fs_byte +00009066 t put_fs_long +00009072 T sys_ftime +00009078 T sys_break +0000907e T sys_ptrace +00009084 T sys_stty +0000908a T sys_gtty +00009090 T sys_rename +00009096 T sys_prof +0000909c T sys_setregid +00009155 T sys_setgid +000091ec T sys_acct +000091f2 T sys_phys +000091f8 T sys_lock +000091fe T sys_mpx +00009204 T sys_ulimit +0000920a T sys_time +00009266 T sys_setreuid +00009348 T sys_setuid +000093dd T sys_stime +00009433 T sys_times +000094d3 T sys_brk +00009515 T sys_setpgid +000095ee T sys_getpgrp +000095fa T sys_setsid +00009674 T sys_getgroups +0000967a T sys_setgroups +00009680 T sys_uname +000096e9 T sys_sethostname +000096ef T sys_getrlimit +000096f5 T sys_setrlimit +000096fb T sys_getrusage +00009701 T sys_gettimeofday +00009707 T sys_settimeofday +0000970d T sys_umask +00009740 t _get_base +00009772 t put_fs_long +0000977e T release +000097e2 t send_sig +00009861 t kill_session +000098bb T sys_kill +00009a6b t tell_father +00009af5 T do_exit +00009d29 T sys_exit +00009d42 T sys_waitpid +00009f68 t get_fs_byte +00009f76 t put_fs_byte +00009f8e t put_fs_long +00009f9a T sys_sgetmask +00009fa6 T sys_ssetmask +00009fd2 T sys_sigpending +00009fd8 T sys_sigsuspend +00009fde t save_old +0000a031 t get_new +0000a071 T sys_signal +0000a0f5 T sys_sigaction +0000a1ff T do_signal +0000a3eb T kernel_mktime +0000a530 t oom +0000a54f T get_free_page +0000a58b T free_page +0000a5fa T free_page_tables +0000a6f9 T copy_page_tables +0000a87a T put_page +0000a966 T un_wp_page +0000aa1e T do_wp_page +0000aaa9 T get_empty_page +0000aae9 t try_to_share +0000ac7b t share_page +0000ad2f T do_no_page +0000aec4 T do_no_page_my +0000b026 T mem_init +0000b09a T calc_mem +0000b18f T page_fault +0000b1c6 t get_fs_long +0000b1dc T sys_ustat +0000b1e2 T sys_utime +0000b28f T sys_access +0000b36b T sys_chdir +0000b3df T sys_chroot +0000b453 T sys_chmod +0000b4ed T sys_chown +0000b568 T sys_open +0000b80b T sys_creat +0000b82e T sys_close +0000b8fd T sys_lseek +0000ba14 T sys_read +0000bc07 T sys_write +0000bdb5 t lock_inode +0000bde2 t unlock_inode +0000be00 T invalidate_inodes +0000be6f T sync_inodes +0000bec6 t _bmap +0000c2b2 T bmap +0000c2d5 T create_block +0000c2f8 T iput +0000c467 T get_empty_inode +0000c5bc T get_pipe_inode +0000c631 T iget +0000c7f6 t read_inode +0000ca2c T sys_sync +0000ca8f T sync_dev +0000cb88 T invalidate_buffers +0000cbfa T check_disk_change +0000cca4 t remove_from_queues +0000cd9b t insert_into_queues +0000ce60 t find_buffer +0000cec8 T get_hash_table +0000cf4a T getblk +0000d0e8 T brelse +0000d131 T bread +0000d1b6 T bread_page +0000d2d8 T breada +0000d3cd T buffer_init +0000d4fc t lock_super +0000d529 t free_super +0000d56e T get_super +0000d5dd T put_super +0000d6b0 t read_super +0000d9f3 T sys_umount +0000db54 T sys_mount +0000dcc5 T mount_root +0000ded3 t get_fs_byte +0000dee1 t put_fs_byte +0000def9 T block_write +0000e04b T block_read +0000e176 t get_fs_byte +0000e184 t put_fs_byte +0000e19c t rw_ttyx +0000e1e4 t rw_tty +0000e234 t rw_ram +0000e23a t rw_mem +0000e240 t rw_kmem +0000e246 t rw_port +0000e2e0 t rw_memory +0000e3b6 T rw_char +0000e420 t get_fs_byte +0000e42e t put_fs_byte +0000e446 T file_read +0000e5f1 T file_write +0000e7eb t put_fs_byte +0000e803 t cp_stat +0000e8da T sys_stat +0000e924 T sys_lstat +0000e93f T sys_fstat +0000e99c T sys_readlink +0000e9a2 t _get_base +0000e9d4 t get_fs_byte +0000e9e2 t get_fs_long +0000e9f8 t put_fs_byte +0000ea10 t put_fs_long +0000ea1c t get_fs +0000ea30 t get_ds +0000ea44 t set_fs +0000ea4b T sys_uselib +0000ea51 t create_tables +0000eb9c t count +0000ebdb t copy_strings +0000ed97 t change_ldt +0000ef1a T do_execve +0000f99c T do_execve2 +00010480 t get_fs_byte +0001048e t put_fs_byte +000104a6 t put_fs_long +000104b2 T read_pipe +00010787 T sys_pipe +00010989 t get_fs_byte +00010997 t permission +00010a38 t match +00010aa0 t match_kernel +00010b08 t find_entry +00010d3f T find_entry_kernel +0001118d t get_dir +0001137a T get_dir_kernel +0001155b t dir_namei +000115da T namei +000116f0 T open_namei +00011a43 T sys_mknod +00011c73 T sys_mkdir +00012024 t empty_dir +00012202 T sys_rmdir +0001255a T sys_unlink +000127fb T sys_symlink +00012801 T sys_link +00012a5b T free_block +00012bcd T new_block +00012d71 T free_inode +00012ed8 T new_inode +000130b2 t dupfd +0001318c T sys_dup2 +000131b3 T sys_dup +000131ce T sys_fcntl +0001330d T sys_ioctl +000133de t free_ind +0001347d t free_dind +0001351c T truncate +00013651 T sys_select +00013657 t lock_buffer +00013684 t unlock_buffer +00013876 t make_request +00013a1a T ll_rw_block +00013a73 T blk_dev_init +00013ac1 t unlock_buffer +00013af6 t end_request +00013ba7 T floppy_deselect +00013bde T floppy_change +00013c64 t setup_DMA +00013d1a t output_byte +00013d90 t result +00013e4d t bad_flp_intr +00013eac t rw_interrupt +00013f9b T setup_rw_floppy +0001405c t seek_interrupt +000140b5 t transfer +000141ea t recal_interrupt +00014234 T unexpected_floppy_interrupt +00014279 t recalibrate_floppy +000142db t reset_interrupt +00014320 t reset_floppy +0001439d t floppy_on_interrupt +00014408 t do_fd_request +0001460c T floppy_init +0001465e t unlock_buffer +00014693 t end_request +00014732 T sys_setup +00014ae5 t controller_ready +00014b79 t hd_out +00014c66 t drive_busy +00014ccc t reset_controller +00014d49 t reset_hd +00014de1 T unexpected_hd_interrupt +00014df4 t bad_rw_intr +00014e32 t read_intr +00014f58 t recal_intr +00014f72 t do_hd_request +00015273 T hd_init +000152ed t unlock_buffer +00015322 t end_request +000153c1 t do_rd_request +000154f7 T rd_init +0001554d T rd_load +000157f9 t get_fs_byte +00015807 t put_fs_byte +0001581f T tty_init +00015830 T tty_intr +000158a4 t sleep_if_empty +000158dc t sleep_if_full +00015950 T copy_to_cooked +00015f0b T tty_read +00016279 T tty_write +0001648b T do_tty_interrupt +000164b3 T chr_dev_init +000164b4 t gotoxy +00016502 t set_origin +00016568 t scrup +00016758 t scrdown +0001684f t lf +00016885 t ri +000168bb t cr +000168dc t del +0001690e t csi_J +0001699f t csi_K +00016a51 T csi_m +00016ab8 t set_cursor +00016b1e t respond +00016b76 t insert_char +00016bd9 t insert_line +00016c1d t delete_char +00016c7b t delete_line +00016cbf t csi_at +00016cfd t csi_L +00016d3b t csi_P +00016d79 t csi_M +00016db7 t save_cur +00016dcc t restore_cur +00016deb T con_write +00017479 T con_init +000176b0 T sysbeepstop +000176d9 t sysbeep +00017737 t mode +00017738 t leds +00017739 t e0 +0001773a T keyboard_interrupt +00017763 t e0_e1 +0001778e t set_e0 +00017797 t set_e1 +000177a0 t put_queue +000177d9 t ctrl +000177f1 t unctrl +000177f5 t unalt +0001780b t lshift +00017813 t unlshift +0001781b t rshift +00017823 t unrshift +0001782b t caps +0001784d t set_leds +00017863 t uncaps +0001786b t scroll +00017874 t num +0001787d t cursor +0001789d t cur2 +000178c6 t cur +000178d2 t ok_cur +000178e0 t num_table +000178ed t cur_table +000178fa t func +00017917 t ok_func +0001792a t end_func +0001792b t func_table +0001795b t key_map +000179bc t shift_map +00017a7e t do_self +00017ae6 t none +00017ae7 t minus +00017afc t key_table +00017efc t kb_wait +00017f05 t reboot +00017f17 t die +00017f19 t init +00017f8e T rs_init +00018011 T rs_write +00018060 T rs1_interrupt +00018068 T rs2_interrupt +0001806d t rs_int +00018084 t rep_int +000180a1 t end +000180af t jmp_table +000180c0 t modem_status +000180c8 t line_status +000180d0 t read_char +00018157 t get_fs_byte +00018165 t get_fs_long +0001817b t put_fs_byte +00018193 t put_fs_long +0001819f t change_speed +0001821d t flush +0001822f t send_break +00018230 t get_termios +0001828c t set_termios +000182dc t get_termio +000183a4 t set_termio +00018468 T tty_ioctl +00018766 t get_fs_byte +00018774 T math_emulate +00018857 T math_error +00018877 T _exit +00018887 T open +000188d0 T close +00018944 T dup +0001897b T setsid +000189aa T execve +00018a47 T strcpy +00018a63 T strncpy +00018a88 T strcat +00018ab3 T strncat +00018ae8 T strcmp +00018b0f T strncmp +00018b3d T strchr +00018b6a T strrchr +00018b99 T strspn +00018bd6 T strcspn +00018c13 T strpbrk +00018c4a T strstr +00018c83 T strlen +00018ca6 T strtok +00018d29 T memcpy +00018d49 T memmove +00018d9d T memcmp +00018dc7 T memchr +00018dff T memset +00018e23 t put_fs_byte +00018e3b t put_fs_long +00018e47 T sys_getdents +00018fea T sys_pipe2 +000191fd T sys_sleep +00019236 T sys_getcwd +0001d5c8 d envp_rc +0001d5dc d envp +0001d600 D sys_call_table +0001d770 D NR_syscalls +0001d780 d init_task +0001e780 D current +0001e7a0 D task +0001e8a0 D stack_start +0001e8a8 D current_DOR +0001e8c0 d thisname.1955 +0001e900 d month +0001e940 d last_inode.1935 +0001e944 D start_buffer +0001e960 d crw_table +0001e980 d ioctl_table +0001e9a0 d floppy_type +0001ea60 d cur_spec1 +0001ea64 d cur_rate +0001ea68 d floppy +0001ea6c d current_track +0001ea70 d callable.1844 +0001ea80 D tty_table +00020fa0 D table_list +00020fc0 d quotient +00020fe0 D _ctype +000210e1 B __bss_start +000210e1 D _edata +00021100 b printbuf +00021500 b memory_end +00021504 b buffer_memory_end +00021508 b main_memory_start +00021520 B jiffies +00021524 B startup_time +00021528 B last_task_used_math +0002153c b mon_timer +0002154c b moff_timer +00021560 b timer_list +00021860 b next_timer +00021864 B last_pid +00021880 b buf +00021c80 b HIGH_MEMORY +00021ca0 b mem_map +00022ba0 B inode_table +000232a0 B nr_buffers +000232a4 b free_list +000232a8 b buffer_wait +000232ac B ROOT_DEV +000232e0 B blk_dev +00023318 B do_floppy +0002331c B selected +00023324 b recalibrate +00023328 b reset +0002332c b seek +00023330 b reply_buffer +00023337 b current_drive +00023338 b sector +00023339 b head +0002333a b track +0002333b b seek_track +0002333c b command +00023340 B do_hd +00023360 B hd_info +00023390 b recalibrate +00023394 b reset +00023398 b NR_HD +000233a0 b hd +000233f0 B rd_length +000233f4 b cr_flag.1923 +00023400 B beepcount +00023404 b video_type +00023408 b video_num_columns +0002340c b video_size_row +00023410 b video_num_lines +00023414 b video_page +00023418 b video_mem_start +0002341c b video_mem_end +00023420 b video_port_reg +00023422 b video_port_val +00023424 b video_erase_char +00023428 b origin +0002342c b scr_end +00023430 b pos +00023434 b x +00023438 b y +0002343c b top +00023440 b bottom +00023444 b state +00023448 b npar +00023460 b par +000234a0 b ques +000234a4 b saved_x +000234a8 b saved_y +000234c0 B drive_info +000234e0 B user_stack +000244e0 B hash_table +000249c0 B super_block +00024d20 B file_table +00025120 B request +000255a0 B rd_start +000255a4 B _ctmp +000255a8 B errno +000255ac B ___strtok +000255b0 B end +000255b0 B _end diff --git a/linux-0.11-lab/1/linux/System.map.2 b/linux-0.11-lab/1/linux/System.map.2 new file mode 100644 index 0000000..54a21c2 --- /dev/null +++ b/linux-0.11-lab/1/linux/System.map.2 @@ -0,0 +1,1100 @@ +Archive member included to satisfy reference by file (symbol) + +kernel/blk_drv/blk_drv.a(ll_rw_blk.o) + fs/fs.o (ll_rw_block) +kernel/blk_drv/blk_drv.a(floppy.o) + kernel/kernel.o (do_floppy) +kernel/blk_drv/blk_drv.a(hd.o) + kernel/kernel.o (do_hd) +kernel/blk_drv/blk_drv.a(ramdisk.o) + kernel/blk_drv/blk_drv.a(hd.o) (rd_load) +kernel/chr_drv/chr_drv.a(tty_io.o) + kernel/kernel.o (tty_table) +kernel/chr_drv/chr_drv.a(console.o) + kernel/chr_drv/chr_drv.a(tty_io.o) (con_write) +kernel/chr_drv/chr_drv.a(keyboard.2.o) + kernel/chr_drv/chr_drv.a(console.o) (keyboard_interrupt) +kernel/chr_drv/chr_drv.a(serial.o) + kernel/chr_drv/chr_drv.a(tty_io.o) (rs_init) +kernel/chr_drv/chr_drv.a(rs_io.o) + kernel/chr_drv/chr_drv.a(serial.o) (rs1_interrupt) +kernel/chr_drv/chr_drv.a(tty_ioctl.o) + fs/fs.o (tty_ioctl) +kernel/math/math.a(math_emulate.o) + kernel/kernel.o (math_emulate) +lib/lib.a(ctype.o) kernel/chr_drv/chr_drv.a(tty_io.o) (_ctmp) +lib/lib.a(_exit.o) init/main.o (_exit) +lib/lib.a(open.o) init/main.o (open) +lib/lib.a(close.o) init/main.o (close) +lib/lib.a(errno.o) init/main.o (errno) +lib/lib.a(write.o) init/main.o (write) +lib/lib.a(dup.o) init/main.o (dup) +lib/lib.a(setsid.o) init/main.o (setsid) +lib/lib.a(execve.o) init/main.o (execve) +lib/lib.a(wait.o) init/main.o (wait) +lib/lib.a(string.o) fs/fs.o (strncpy) +lib/lib.a(update.o) kernel/kernel.o (sys_getdents) + +分配公共符号 +公共符号 大小 文件 + +errno 0x4 lib/lib.a(errno.o) +hash_table 0x4cc fs/fs.o +___strtok 0x4 lib/lib.a(string.o) +rd_start 0x4 kernel/blk_drv/blk_drv.a(ramdisk.o) +request 0x480 kernel/blk_drv/blk_drv.a(ll_rw_blk.o) +user_stack 0x1000 kernel/kernel.o +_ctmp 0x1 lib/lib.a(ctype.o) +super_block 0x360 fs/fs.o +drive_info 0x20 init/main.o +file_table 0x400 fs/fs.o + +Discarded input sections + + .note.GNU-stack + 0x0000000000000000 0x0 init/main.o + .note.GNU-stack + 0x0000000000000000 0x0 kernel/kernel.o + .note.GNU-stack + 0x0000000000000000 0x0 mm/mm.o + .note.GNU-stack + 0x0000000000000000 0x0 fs/fs.o + .note.GNU-stack + 0x0000000000000000 0x0 kernel/blk_drv/blk_drv.a(ll_rw_blk.o) + .note.GNU-stack + 0x0000000000000000 0x0 kernel/blk_drv/blk_drv.a(floppy.o) + .note.GNU-stack + 0x0000000000000000 0x0 kernel/blk_drv/blk_drv.a(hd.o) + .note.GNU-stack + 0x0000000000000000 0x0 kernel/blk_drv/blk_drv.a(ramdisk.o) + .note.GNU-stack + 0x0000000000000000 0x0 kernel/chr_drv/chr_drv.a(tty_io.o) + .note.GNU-stack + 0x0000000000000000 0x0 kernel/chr_drv/chr_drv.a(console.o) + .note.GNU-stack + 0x0000000000000000 0x0 kernel/chr_drv/chr_drv.a(serial.o) + .note.GNU-stack + 0x0000000000000000 0x0 kernel/chr_drv/chr_drv.a(tty_ioctl.o) + .note.GNU-stack + 0x0000000000000000 0x0 kernel/math/math.a(math_emulate.o) + .note.GNU-stack + 0x0000000000000000 0x0 lib/lib.a(ctype.o) + .note.GNU-stack + 0x0000000000000000 0x0 lib/lib.a(_exit.o) + .note.GNU-stack + 0x0000000000000000 0x0 lib/lib.a(open.o) + .note.GNU-stack + 0x0000000000000000 0x0 lib/lib.a(close.o) + .note.GNU-stack + 0x0000000000000000 0x0 lib/lib.a(errno.o) + .note.GNU-stack + 0x0000000000000000 0x0 lib/lib.a(write.o) + .note.GNU-stack + 0x0000000000000000 0x0 lib/lib.a(dup.o) + .note.GNU-stack + 0x0000000000000000 0x0 lib/lib.a(setsid.o) + .note.GNU-stack + 0x0000000000000000 0x0 lib/lib.a(execve.o) + .note.GNU-stack + 0x0000000000000000 0x0 lib/lib.a(wait.o) + .note.GNU-stack + 0x0000000000000000 0x0 lib/lib.a(string.o) + .note.GNU-stack + 0x0000000000000000 0x0 lib/lib.a(update.o) + +内存配置 + +名称 来源 长度 属性 +*default* 0x0000000000000000 0xffffffffffffffff + +Linker script and memory map + +段 .text 的地址设置为 0x0 +LOAD boot/head.o +LOAD init/main.o +LOAD kernel/kernel.o +LOAD mm/mm.o +LOAD fs/fs.o +LOAD kernel/blk_drv/blk_drv.a +LOAD kernel/chr_drv/chr_drv.a +LOAD kernel/math/math.a +LOAD lib/lib.a + 0x0000000008048000 PROVIDE (__executable_start, 0x8048000) + 0x0000000008048074 . = (0x8048000 + SIZEOF_HEADERS) + +.interp + *(.interp) + +.note.gnu.build-id + *(.note.gnu.build-id) + +.hash + *(.hash) + +.gnu.hash + *(.gnu.hash) + +.dynsym + *(.dynsym) + +.dynstr + *(.dynstr) + +.gnu.version + *(.gnu.version) + +.gnu.version_d + *(.gnu.version_d) + +.gnu.version_r + *(.gnu.version_r) + +.rel.init + *(.rel.init) + +.rel.text 0x0000000008048074 0x0 + *(.rel.text .rel.text.* .rel.gnu.linkonce.t.*) + .rel.text 0x0000000000000000 0x0 boot/head.o + +.rel.fini + *(.rel.fini) + +.rel.rodata + *(.rel.rodata .rel.rodata.* .rel.gnu.linkonce.r.*) + +.rel.data.rel.ro + *(.rel.data.rel.ro .rel.data.rel.ro.* .rel.gnu.linkonce.d.rel.ro.*) + +.rel.data 0x0000000008048074 0x0 + *(.rel.data .rel.data.* .rel.gnu.linkonce.d.*) + .rel.data 0x0000000000000000 0x0 boot/head.o + +.rel.tdata + *(.rel.tdata .rel.tdata.* .rel.gnu.linkonce.td.*) + +.rel.tbss + *(.rel.tbss .rel.tbss.* .rel.gnu.linkonce.tb.*) + +.rel.ctors + *(.rel.ctors) + +.rel.dtors + *(.rel.dtors) + +.rel.got + *(.rel.got) + +.rel.bss + *(.rel.bss .rel.bss.* .rel.gnu.linkonce.b.*) + +.rel.ifunc + *(.rel.ifunc) + +.rel.plt 0x0000000008048074 0x0 + *(.rel.plt) + 0x0000000008048074 PROVIDE (__rel_iplt_start, .) + *(.rel.iplt) + .rel.iplt 0x0000000000000000 0x0 boot/head.o + 0x0000000008048074 PROVIDE (__rel_iplt_end, .) + +.init + *(SORT(.init)) + +.plt 0x0000000008048080 0x0 + *(.plt) + *(.iplt) + .iplt 0x0000000000000000 0x0 boot/head.o + +.text 0x0000000000000000 0x195a8 + *(.text.unlikely .text.*_unlikely .text.unlikely.*) + *(.text.exit .text.exit.*) + *(.text.startup .text.startup.*) + *(.text.hot .text.hot.*) + *(.text .stub .text.* .gnu.linkonce.t.*) + .text 0x0000000000000000 0x64c0 boot/head.o + 0x0000000000000000 startup_32 + 0x0000000000000000 pg_dir + 0x0000000000005000 tmp_floppy_area + 0x00000000000054c0 idt + 0x0000000000005cc0 gdt + .text 0x00000000000064c0 0x744 init/main.o + 0x00000000000064c0 fork + 0x00000000000064ef pause + 0x000000000000651e setup + 0x0000000000006555 sync + 0x0000000000006799 main + 0x000000000000695b init + 0x0000000000006bd3 print_nr + .text 0x0000000000006c04 0x392c kernel/kernel.o + 0x0000000000006c04 show_task + 0x0000000000006c89 show_stat + 0x0000000000006ccf math_state_restore + 0x0000000000006d2d schedule + 0x0000000000006edf sys_pause + 0x0000000000006ef5 sleep_on + 0x0000000000006f54 interruptible_sleep_on + 0x0000000000006fe7 wake_up + 0x000000000000700f ticks_to_floppy_on + 0x00000000000070da floppy_on + 0x0000000000007109 floppy_off + 0x0000000000007119 do_floppy_timer + 0x00000000000071ed add_timer + 0x0000000000007311 do_timer + 0x0000000000007400 sys_alarm + 0x000000000000747f sys_getpid + 0x000000000000748b sys_getppid + 0x0000000000007497 sys_getuid + 0x00000000000074a6 sys_geteuid + 0x00000000000074b6 sys_getgid + 0x00000000000074c6 sys_getegid + 0x00000000000074d5 sys_nice + 0x0000000000007500 sched_init + 0x00000000000076a4 system_call + 0x0000000000007728 coprocessor_error + 0x000000000000774a device_not_available + 0x0000000000007784 timer_interrupt + 0x00000000000077bc sys_execve + 0x00000000000077cc sys_execve2 + 0x00000000000077dc sys_fork + 0x00000000000077f4 hd_interrupt + 0x0000000000007830 floppy_interrupt + 0x0000000000007866 parallel_interrupt + 0x0000000000007a81 do_double_fault + 0x0000000000007aa4 do_general_protection + 0x0000000000007ac7 do_divide_error + 0x0000000000007aea do_int3 + 0x0000000000007bb2 do_nmi + 0x0000000000007bd5 do_debug + 0x0000000000007bf8 do_overflow + 0x0000000000007c1b do_bounds + 0x0000000000007c3e do_invalid_op + 0x0000000000007c61 do_device_not_available + 0x0000000000007c84 do_coprocessor_segment_overrun + 0x0000000000007ca7 do_invalid_TSS + 0x0000000000007cca do_segment_not_present + 0x0000000000007ced do_stack_segment + 0x0000000000007d10 do_coprocessor_error + 0x0000000000007d44 do_reserved + 0x0000000000007d67 trap_init + 0x000000000000804b divide_error + 0x0000000000008080 debug + 0x0000000000008087 nmi + 0x000000000000808e int3 + 0x0000000000008095 overflow + 0x000000000000809c bounds + 0x00000000000080a3 invalid_op + 0x00000000000080aa coprocessor_segment_overrun + 0x00000000000080b1 reserved + 0x00000000000080b8 irq13 + 0x00000000000080cd double_fault + 0x0000000000008104 invalid_TSS + 0x000000000000810b segment_not_present + 0x0000000000008112 stack_segment + 0x0000000000008119 general_protection + 0x0000000000008152 verify_area + 0x00000000000081b9 copy_mem + 0x0000000000008313 copy_process + 0x00000000000087c0 find_empty_process + 0x0000000000008854 panic + 0x000000000000888f printk + 0x0000000000008bac vsprintf + 0x0000000000009072 sys_ftime + 0x0000000000009078 sys_break + 0x000000000000907e sys_ptrace + 0x0000000000009084 sys_stty + 0x000000000000908a sys_gtty + 0x0000000000009090 sys_rename + 0x0000000000009096 sys_prof + 0x000000000000909c sys_setregid + 0x0000000000009155 sys_setgid + 0x00000000000091ec sys_acct + 0x00000000000091f2 sys_phys + 0x00000000000091f8 sys_lock + 0x00000000000091fe sys_mpx + 0x0000000000009204 sys_ulimit + 0x000000000000920a sys_time + 0x0000000000009266 sys_setreuid + 0x0000000000009348 sys_setuid + 0x00000000000093dd sys_stime + 0x0000000000009433 sys_times + 0x00000000000094d3 sys_brk + 0x0000000000009515 sys_setpgid + 0x00000000000095ee sys_getpgrp + 0x00000000000095fa sys_setsid + 0x0000000000009674 sys_getgroups + 0x000000000000967a sys_setgroups + 0x0000000000009680 sys_uname + 0x00000000000096e9 sys_sethostname + 0x00000000000096ef sys_getrlimit + 0x00000000000096f5 sys_setrlimit + 0x00000000000096fb sys_getrusage + 0x0000000000009701 sys_gettimeofday + 0x0000000000009707 sys_settimeofday + 0x000000000000970d sys_umask + 0x000000000000977e release + 0x00000000000098bb sys_kill + 0x0000000000009af5 do_exit + 0x0000000000009d29 sys_exit + 0x0000000000009d42 sys_waitpid + 0x0000000000009f9a sys_sgetmask + 0x0000000000009fa6 sys_ssetmask + 0x0000000000009fd2 sys_sigpending + 0x0000000000009fd8 sys_sigsuspend + 0x000000000000a071 sys_signal + 0x000000000000a0f5 sys_sigaction + 0x000000000000a1ff do_signal + 0x000000000000a3eb kernel_mktime + .text 0x000000000000a530 0xc96 mm/mm.o + 0x000000000000a54f get_free_page + 0x000000000000a58b free_page + 0x000000000000a5fa free_page_tables + 0x000000000000a6f9 copy_page_tables + 0x000000000000a87a put_page + 0x000000000000a966 un_wp_page + 0x000000000000aa1e do_wp_page + 0x000000000000aa50 write_verify + 0x000000000000aaa9 get_empty_page + 0x000000000000ad2f do_no_page + 0x000000000000aec4 do_no_page_my + 0x000000000000b026 mem_init + 0x000000000000b09a calc_mem + 0x000000000000b18f page_fault + .text 0x000000000000b1c6 0x8491 fs/fs.o + 0x000000000000b1dc sys_ustat + 0x000000000000b1e2 sys_utime + 0x000000000000b28f sys_access + 0x000000000000b36b sys_chdir + 0x000000000000b3df sys_chroot + 0x000000000000b453 sys_chmod + 0x000000000000b4ed sys_chown + 0x000000000000b568 sys_open + 0x000000000000b80b sys_creat + 0x000000000000b82e sys_close + 0x000000000000b8fd sys_lseek + 0x000000000000ba14 sys_read + 0x000000000000bc07 sys_write + 0x000000000000be00 invalidate_inodes + 0x000000000000be6f sync_inodes + 0x000000000000c2b2 bmap + 0x000000000000c2d5 create_block + 0x000000000000c2f8 iput + 0x000000000000c467 get_empty_inode + 0x000000000000c5bc get_pipe_inode + 0x000000000000c631 iget + 0x000000000000ca2c sys_sync + 0x000000000000ca8f sync_dev + 0x000000000000cb88 invalidate_buffers + 0x000000000000cbfa check_disk_change + 0x000000000000cec8 get_hash_table + 0x000000000000cf4a getblk + 0x000000000000d0e8 brelse + 0x000000000000d131 bread + 0x000000000000d1b6 bread_page + 0x000000000000d2d8 breada + 0x000000000000d3cd buffer_init + 0x000000000000d56e get_super + 0x000000000000d5dd put_super + 0x000000000000d9f3 sys_umount + 0x000000000000db54 sys_mount + 0x000000000000dcc5 mount_root + 0x000000000000def9 block_write + 0x000000000000e04b block_read + 0x000000000000e3b6 rw_char + 0x000000000000e446 file_read + 0x000000000000e5f1 file_write + 0x000000000000e8da sys_stat + 0x000000000000e924 sys_lstat + 0x000000000000e93f sys_fstat + 0x000000000000e99c sys_readlink + 0x000000000000ea4b sys_uselib + 0x000000000000ef1a do_execve + 0x000000000000f99c do_execve2 + 0x00000000000104b2 read_pipe + 0x0000000000010608 write_pipe + 0x0000000000010787 sys_pipe + 0x0000000000010d3f find_entry_kernel + 0x000000000001137a get_dir_kernel + 0x00000000000115da namei + 0x00000000000116f0 open_namei + 0x0000000000011a43 sys_mknod + 0x0000000000011c73 sys_mkdir + 0x0000000000012202 sys_rmdir + 0x000000000001255a sys_unlink + 0x00000000000127fb sys_symlink + 0x0000000000012801 sys_link + 0x0000000000012a5b free_block + 0x0000000000012bcd new_block + 0x0000000000012d71 free_inode + 0x0000000000012ed8 new_inode + 0x000000000001318c sys_dup2 + 0x00000000000131b3 sys_dup + 0x00000000000131ce sys_fcntl + 0x000000000001330d sys_ioctl + 0x000000000001351c truncate + 0x0000000000013651 sys_select + .text 0x0000000000013657 0x46a kernel/blk_drv/blk_drv.a(ll_rw_blk.o) + 0x0000000000013a1a ll_rw_block + 0x0000000000013a73 blk_dev_init + .text 0x0000000000013ac1 0xb9d kernel/blk_drv/blk_drv.a(floppy.o) + 0x0000000000013ba7 floppy_deselect + 0x0000000000013bde floppy_change + 0x0000000000013f9b setup_rw_floppy + 0x0000000000014234 unexpected_floppy_interrupt + 0x000000000001460c floppy_init + .text 0x000000000001465e 0xc8f kernel/blk_drv/blk_drv.a(hd.o) + 0x0000000000014732 sys_setup + 0x0000000000014de1 unexpected_hd_interrupt + 0x0000000000015273 hd_init + .text 0x00000000000152ed 0x50c kernel/blk_drv/blk_drv.a(ramdisk.o) + 0x00000000000154f7 rd_init + 0x000000000001554d rd_load + .text 0x00000000000157f9 0xcbb kernel/chr_drv/chr_drv.a(tty_io.o) + 0x000000000001581f tty_init + 0x0000000000015830 tty_intr + 0x000000000001593d wait_for_keypress + 0x0000000000015950 copy_to_cooked + 0x0000000000015f0b tty_read + 0x0000000000016279 tty_write + 0x000000000001648b do_tty_interrupt + 0x00000000000164b3 chr_dev_init + .text 0x00000000000164b4 0x1283 kernel/chr_drv/chr_drv.a(console.o) + 0x0000000000016a51 csi_m + 0x0000000000016deb con_write + 0x0000000000017479 con_init + 0x00000000000176b0 sysbeepstop + .text 0x0000000000017737 0x7e2 kernel/chr_drv/chr_drv.a(keyboard.2.o) + 0x000000000001773a keyboard_interrupt + .text 0x0000000000017f19 0x145 kernel/chr_drv/chr_drv.a(serial.o) + 0x0000000000017f8e rs_init + 0x0000000000018011 rs_write + *fill* 0x000000000001805e 0x2 + .text 0x0000000000018060 0xf7 kernel/chr_drv/chr_drv.a(rs_io.o) + 0x0000000000018060 rs1_interrupt + 0x0000000000018068 rs2_interrupt + .text 0x0000000000018157 0x60f kernel/chr_drv/chr_drv.a(tty_ioctl.o) + 0x0000000000018468 tty_ioctl + .text 0x0000000000018766 0x111 kernel/math/math.a(math_emulate.o) + 0x0000000000018774 math_emulate + 0x0000000000018857 math_error + .text 0x0000000000018877 0x0 lib/lib.a(ctype.o) + .text 0x0000000000018877 0x10 lib/lib.a(_exit.o) + 0x0000000000018877 _exit + .text 0x0000000000018887 0x49 lib/lib.a(open.o) + 0x0000000000018887 open + .text 0x00000000000188d0 0x37 lib/lib.a(close.o) + 0x00000000000188d0 close + .text 0x0000000000018907 0x0 lib/lib.a(errno.o) + .text 0x0000000000018907 0x3d lib/lib.a(write.o) + 0x0000000000018907 write + .text 0x0000000000018944 0x37 lib/lib.a(dup.o) + 0x0000000000018944 dup + .text 0x000000000001897b 0x2f lib/lib.a(setsid.o) + 0x000000000001897b setsid + .text 0x00000000000189aa 0x3d lib/lib.a(execve.o) + 0x00000000000189aa execve + .text 0x00000000000189e7 0x60 lib/lib.a(wait.o) + 0x00000000000189e7 waitpid + 0x0000000000018a24 wait + .text 0x0000000000018a47 0x3dc lib/lib.a(string.o) + 0x0000000000018a47 strcpy + 0x0000000000018a63 strncpy + 0x0000000000018a88 strcat + 0x0000000000018ab3 strncat + 0x0000000000018ae8 strcmp + 0x0000000000018b0f strncmp + 0x0000000000018b3d strchr + 0x0000000000018b6a strrchr + 0x0000000000018b99 strspn + 0x0000000000018bd6 strcspn + 0x0000000000018c13 strpbrk + 0x0000000000018c4a strstr + 0x0000000000018c83 strlen + 0x0000000000018ca6 strtok + 0x0000000000018d29 memcpy + 0x0000000000018d49 memmove + 0x0000000000018d9d memcmp + 0x0000000000018dc7 memchr + 0x0000000000018dff memset + .text 0x0000000000018e23 0x785 lib/lib.a(update.o) + 0x0000000000018e47 sys_getdents + 0x0000000000018fea sys_pipe2 + 0x00000000000191fd sys_sleep + 0x0000000000019236 sys_getcwd + *(.gnu.warning) + +.fini + *(SORT(.fini)) + 0x00000000000195a8 PROVIDE (__etext, .) + 0x00000000000195a8 PROVIDE (_etext, .) + 0x00000000000195a8 PROVIDE (etext, .) + +.rodata 0x00000000000195a8 0x1422 + *(.rodata .rodata.* .gnu.linkonce.r.*) + .rodata 0x00000000000195a8 0xc9 init/main.o + *fill* 0x0000000000019671 0x3 + .rodata 0x0000000000019674 0x438 kernel/kernel.o + .rodata 0x0000000000019aac 0x1b5 mm/mm.o + *fill* 0x0000000000019c61 0x3 + .rodata 0x0000000000019c64 0x640 fs/fs.o + .rodata 0x000000000001a2a4 0x7a kernel/blk_drv/blk_drv.a(ll_rw_blk.o) + *fill* 0x000000000001a31e 0x2 + .rodata 0x000000000001a320 0x133 kernel/blk_drv/blk_drv.a(floppy.o) + *fill* 0x000000000001a453 0x1 + .rodata 0x000000000001a454 0x19b kernel/blk_drv/blk_drv.a(hd.o) + *fill* 0x000000000001a5ef 0x1 + .rodata 0x000000000001a5f0 0x188 kernel/blk_drv/blk_drv.a(ramdisk.o) + .rodata 0x000000000001a778 0x17d kernel/chr_drv/chr_drv.a(console.o) + *fill* 0x000000000001a8f5 0x3 + .rodata 0x000000000001a8f8 0x80 kernel/chr_drv/chr_drv.a(tty_ioctl.o) + .rodata 0x000000000001a978 0x52 kernel/math/math.a(math_emulate.o) + +.rodata1 + *(.rodata1) + +.eh_frame_hdr + *(.eh_frame_hdr) + +.eh_frame 0x000000000001a9cc 0x2be8 + *(.eh_frame) + .eh_frame 0x000000000001a9cc 0x108 init/main.o + .eh_frame 0x000000000001aad4 0xb04 kernel/kernel.o + 0xbf4 (size before relaxing) + .eh_frame 0x000000000001b5d8 0x1b0 mm/mm.o + 0x1c8 (size before relaxing) + .eh_frame 0x000000000001b788 0xe78 fs/fs.o + 0x1010 (size before relaxing) + .eh_frame 0x000000000001c600 0x98 kernel/blk_drv/blk_drv.a(ll_rw_blk.o) + 0xb0 (size before relaxing) + .eh_frame 0x000000000001c698 0x23c kernel/blk_drv/blk_drv.a(floppy.o) + 0x254 (size before relaxing) + .eh_frame 0x000000000001c8d4 0x1e8 kernel/blk_drv/blk_drv.a(hd.o) + 0x200 (size before relaxing) + .eh_frame 0x000000000001cabc 0xac kernel/blk_drv/blk_drv.a(ramdisk.o) + 0xc4 (size before relaxing) + .eh_frame 0x000000000001cb68 0x12c kernel/chr_drv/chr_drv.a(tty_io.o) + 0x144 (size before relaxing) + .eh_frame 0x000000000001cc94 0x2c0 kernel/chr_drv/chr_drv.a(console.o) + 0x2d8 (size before relaxing) + .eh_frame 0x000000000001cf54 0x54 kernel/chr_drv/chr_drv.a(serial.o) + 0x6c (size before relaxing) + .eh_frame 0x000000000001cfa8 0x148 kernel/chr_drv/chr_drv.a(tty_ioctl.o) + 0x160 (size before relaxing) + .eh_frame 0x000000000001d0f0 0x5c kernel/math/math.a(math_emulate.o) + 0x74 (size before relaxing) + .eh_frame 0x000000000001d14c 0x1c lib/lib.a(_exit.o) + 0x34 (size before relaxing) + .eh_frame 0x000000000001d168 0x24 lib/lib.a(open.o) + 0x3c (size before relaxing) + .eh_frame 0x000000000001d18c 0x20 lib/lib.a(close.o) + 0x38 (size before relaxing) + .eh_frame 0x000000000001d1ac 0x20 lib/lib.a(write.o) + 0x38 (size before relaxing) + .eh_frame 0x000000000001d1cc 0x20 lib/lib.a(dup.o) + 0x38 (size before relaxing) + .eh_frame 0x000000000001d1ec 0x18 lib/lib.a(setsid.o) + 0x30 (size before relaxing) + .eh_frame 0x000000000001d204 0x20 lib/lib.a(execve.o) + 0x38 (size before relaxing) + .eh_frame 0x000000000001d224 0x38 lib/lib.a(wait.o) + 0x50 (size before relaxing) + .eh_frame 0x000000000001d25c 0x2b0 lib/lib.a(string.o) + 0x2c8 (size before relaxing) + .eh_frame 0x000000000001d50c 0xa8 lib/lib.a(update.o) + 0xc0 (size before relaxing) + +.gcc_except_table + *(.gcc_except_table .gcc_except_table.*) + +.exception_ranges + *(.exception_ranges .exception_ranges*) + 0x000000000001d5b4 . = . + +.eh_frame + *(.eh_frame) + +.gcc_except_table + *(.gcc_except_table .gcc_except_table.*) + +.exception_ranges + *(.exception_ranges .exception_ranges*) + +.tdata + *(.tdata .tdata.* .gnu.linkonce.td.*) + +.tbss + *(.tbss .tbss.* .gnu.linkonce.tb.*) + *(.tcommon) + +.preinit_array 0x000000000001d5b4 0x0 + 0x000000000001d5b4 PROVIDE (__preinit_array_start, .) + *(.preinit_array) + 0x000000000001d5b4 PROVIDE (__preinit_array_end, .) + +.init_array 0x000000000001d5b4 0x0 + 0x000000000001d5b4 PROVIDE (__init_array_start, .) + *(SORT(.init_array.*) SORT(.ctors.*)) + *(.init_array EXCLUDE_FILE(*crtend?.o *crtend.o *crtbegin?.o *crtbegin.o) .ctors) + 0x000000000001d5b4 PROVIDE (__init_array_end, .) + +.fini_array 0x000000000001d5b4 0x0 + 0x000000000001d5b4 PROVIDE (__fini_array_start, .) + *(SORT(.fini_array.*) SORT(.dtors.*)) + *(.fini_array EXCLUDE_FILE(*crtend?.o *crtend.o *crtbegin?.o *crtbegin.o) .dtors) + 0x000000000001d5b4 PROVIDE (__fini_array_end, .) + +.ctors + *crtbegin.o(.ctors) + *crtbegin?.o(.ctors) + *(EXCLUDE_FILE(*crtend?.o *crtend.o) .ctors) + *(SORT(.ctors.*)) + *(.ctors) + +.dtors + *crtbegin.o(.dtors) + *crtbegin?.o(.dtors) + *(EXCLUDE_FILE(*crtend?.o *crtend.o) .dtors) + *(SORT(.dtors.*)) + *(.dtors) + +.jcr + *(.jcr) + +.data.rel.ro + *(.data.rel.ro.local* .gnu.linkonce.d.rel.ro.local.*) + *(.data.rel.ro .data.rel.ro.* .gnu.linkonce.d.rel.ro.*) + +.dynamic + *(.dynamic) + +.got + *(.got) + *(.igot) + +.got.plt 0x000000000001d5b4 0x0 + *(.got.plt) + *(.igot.plt) + .igot.plt 0x0000000000000000 0x0 boot/head.o + +.data 0x000000000001d5c0 0x3b21 + *(.data .data.* .gnu.linkonce.d.*) + .data 0x000000000001d5c0 0x0 boot/head.o + .data 0x000000000001d5c0 0x28 init/main.o + *fill* 0x000000000001d5e8 0x18 + .data 0x000000000001d600 0x1330 kernel/kernel.o + 0x000000000001d600 sys_call_table + 0x000000000001d770 NR_syscalls + 0x000000000001e780 current + 0x000000000001e7a0 task + 0x000000000001e8a0 stack_start + 0x000000000001e8a8 current_DOR + .data 0x000000000001e930 0x0 mm/mm.o + *fill* 0x000000000001e930 0x10 + .data 0x000000000001e940 0x60 fs/fs.o + 0x000000000001e944 start_buffer + .data 0x000000000001e9a0 0x0 kernel/blk_drv/blk_drv.a(ll_rw_blk.o) + .data 0x000000000001e9a0 0xcd kernel/blk_drv/blk_drv.a(floppy.o) + *fill* 0x000000000001ea6d 0x3 + .data 0x000000000001ea70 0x4 kernel/blk_drv/blk_drv.a(hd.o) + .data 0x000000000001ea74 0x0 kernel/blk_drv/blk_drv.a(ramdisk.o) + *fill* 0x000000000001ea74 0xc + .data 0x000000000001ea80 0x2538 kernel/chr_drv/chr_drv.a(tty_io.o) + 0x000000000001ea80 tty_table + 0x0000000000020fa0 table_list + .data 0x0000000000020fb8 0x1 kernel/chr_drv/chr_drv.a(console.o) + .data 0x0000000000020fb9 0x0 kernel/chr_drv/chr_drv.a(keyboard.2.o) + .data 0x0000000000020fb9 0x0 kernel/chr_drv/chr_drv.a(serial.o) + .data 0x0000000000020fb9 0x0 kernel/chr_drv/chr_drv.a(rs_io.o) + *fill* 0x0000000000020fb9 0x7 + .data 0x0000000000020fc0 0x20 kernel/chr_drv/chr_drv.a(tty_ioctl.o) + .data 0x0000000000020fe0 0x0 kernel/math/math.a(math_emulate.o) + .data 0x0000000000020fe0 0x101 lib/lib.a(ctype.o) + 0x0000000000020fe0 _ctype + .data 0x00000000000210e1 0x0 lib/lib.a(_exit.o) + .data 0x00000000000210e1 0x0 lib/lib.a(open.o) + .data 0x00000000000210e1 0x0 lib/lib.a(close.o) + .data 0x00000000000210e1 0x0 lib/lib.a(errno.o) + .data 0x00000000000210e1 0x0 lib/lib.a(write.o) + .data 0x00000000000210e1 0x0 lib/lib.a(dup.o) + .data 0x00000000000210e1 0x0 lib/lib.a(setsid.o) + .data 0x00000000000210e1 0x0 lib/lib.a(execve.o) + .data 0x00000000000210e1 0x0 lib/lib.a(wait.o) + .data 0x00000000000210e1 0x0 lib/lib.a(string.o) + .data 0x00000000000210e1 0x0 lib/lib.a(update.o) + +.data1 + *(.data1) + 0x00000000000210e1 _edata = . + 0x00000000000210e1 PROVIDE (edata, .) + 0x00000000000210e1 . = . + 0x00000000000210e1 __bss_start = . + +.bss 0x0000000000021100 0x44b0 + *(.dynbss) + *(.bss .bss.* .gnu.linkonce.b.*) + .bss 0x0000000000021100 0x0 boot/head.o + .bss 0x0000000000021100 0x40c init/main.o + *fill* 0x000000000002150c 0x14 + .bss 0x0000000000021520 0x760 kernel/kernel.o + 0x0000000000021520 jiffies + 0x0000000000021524 startup_time + 0x0000000000021528 last_task_used_math + 0x0000000000021864 last_pid + .bss 0x0000000000021c80 0xf20 mm/mm.o + .bss 0x0000000000022ba0 0x710 fs/fs.o + 0x0000000000022ba0 inode_table + 0x00000000000232a0 nr_buffers + 0x00000000000232ac ROOT_DEV + *fill* 0x00000000000232b0 0x10 + .bss 0x00000000000232c0 0x58 kernel/blk_drv/blk_drv.a(ll_rw_blk.o) + 0x00000000000232c0 wait_for_request + 0x00000000000232e0 blk_dev + .bss 0x0000000000023318 0x25 kernel/blk_drv/blk_drv.a(floppy.o) + 0x0000000000023318 do_floppy + 0x000000000002331c selected + 0x0000000000023320 wait_on_floppy_select + *fill* 0x000000000002333d 0x3 + .bss 0x0000000000023340 0xb0 kernel/blk_drv/blk_drv.a(hd.o) + 0x0000000000023340 do_hd + 0x0000000000023360 hd_info + .bss 0x00000000000233f0 0x4 kernel/blk_drv/blk_drv.a(ramdisk.o) + 0x00000000000233f0 rd_length + .bss 0x00000000000233f4 0x4 kernel/chr_drv/chr_drv.a(tty_io.o) + *fill* 0x00000000000233f8 0x8 + .bss 0x0000000000023400 0xac kernel/chr_drv/chr_drv.a(console.o) + 0x0000000000023400 beepcount + .bss 0x00000000000234ac 0x0 kernel/chr_drv/chr_drv.a(keyboard.2.o) + .bss 0x00000000000234ac 0x0 kernel/chr_drv/chr_drv.a(serial.o) + .bss 0x00000000000234ac 0x0 kernel/chr_drv/chr_drv.a(rs_io.o) + .bss 0x00000000000234ac 0x0 kernel/chr_drv/chr_drv.a(tty_ioctl.o) + .bss 0x00000000000234ac 0x0 kernel/math/math.a(math_emulate.o) + .bss 0x00000000000234ac 0x0 lib/lib.a(ctype.o) + .bss 0x00000000000234ac 0x0 lib/lib.a(_exit.o) + .bss 0x00000000000234ac 0x0 lib/lib.a(open.o) + .bss 0x00000000000234ac 0x0 lib/lib.a(close.o) + .bss 0x00000000000234ac 0x0 lib/lib.a(errno.o) + .bss 0x00000000000234ac 0x0 lib/lib.a(write.o) + .bss 0x00000000000234ac 0x0 lib/lib.a(dup.o) + .bss 0x00000000000234ac 0x0 lib/lib.a(setsid.o) + .bss 0x00000000000234ac 0x0 lib/lib.a(execve.o) + .bss 0x00000000000234ac 0x0 lib/lib.a(wait.o) + .bss 0x00000000000234ac 0x0 lib/lib.a(string.o) + .bss 0x00000000000234ac 0x0 lib/lib.a(update.o) + *(COMMON) + *fill* 0x00000000000234ac 0x14 + COMMON 0x00000000000234c0 0x20 init/main.o + 0x00000000000234c0 drive_info + COMMON 0x00000000000234e0 0x1000 kernel/kernel.o + 0x00000000000234e0 user_stack + COMMON 0x00000000000244e0 0xc40 fs/fs.o + 0x00000000000244e0 hash_table + 0x00000000000249c0 super_block + 0x0000000000024d20 file_table + COMMON 0x0000000000025120 0x480 kernel/blk_drv/blk_drv.a(ll_rw_blk.o) + 0x0000000000025120 request + COMMON 0x00000000000255a0 0x4 kernel/blk_drv/blk_drv.a(ramdisk.o) + 0x00000000000255a0 rd_start + COMMON 0x00000000000255a4 0x1 lib/lib.a(ctype.o) + 0x00000000000255a4 _ctmp + *fill* 0x00000000000255a5 0x3 + COMMON 0x00000000000255a8 0x4 lib/lib.a(errno.o) + 0x00000000000255a8 errno + COMMON 0x00000000000255ac 0x4 lib/lib.a(string.o) + 0x00000000000255ac ___strtok + 0x00000000000255b0 . = ALIGN ((. != 0x0)?0x4:0x1) + 0x00000000000255b0 . = ALIGN (0x4) + 0x00000000000255b0 . = SEGMENT_START ("ldata-segment", .) + 0x00000000000255b0 . = ALIGN (0x4) + 0x00000000000255b0 _end = . + 0x00000000000255b0 PROVIDE (end, .) + +.stab + *(.stab) + +.stabstr + *(.stabstr) + +.stab.excl + *(.stab.excl) + +.stab.exclstr + *(.stab.exclstr) + +.stab.index + *(.stab.index) + +.stab.indexstr + *(.stab.indexstr) + +.comment 0x0000000000000000 0x29 + *(.comment) + .comment 0x0000000000000000 0x29 init/main.o + 0x2a (size before relaxing) + .comment 0x0000000000000000 0x1a4 kernel/kernel.o + .comment 0x0000000000000000 0x2a mm/mm.o + .comment 0x0000000000000000 0x2f4 fs/fs.o + .comment 0x0000000000000000 0x2a kernel/blk_drv/blk_drv.a(ll_rw_blk.o) + .comment 0x0000000000000000 0x2a kernel/blk_drv/blk_drv.a(floppy.o) + .comment 0x0000000000000000 0x2a kernel/blk_drv/blk_drv.a(hd.o) + .comment 0x0000000000000000 0x2a kernel/blk_drv/blk_drv.a(ramdisk.o) + .comment 0x0000000000000000 0x2a kernel/chr_drv/chr_drv.a(tty_io.o) + .comment 0x0000000000000000 0x2a kernel/chr_drv/chr_drv.a(console.o) + .comment 0x0000000000000000 0x2a kernel/chr_drv/chr_drv.a(serial.o) + .comment 0x0000000000000000 0x2a kernel/chr_drv/chr_drv.a(tty_ioctl.o) + .comment 0x0000000000000000 0x2a kernel/math/math.a(math_emulate.o) + .comment 0x0000000000000000 0x2a lib/lib.a(ctype.o) + .comment 0x0000000000000000 0x2a lib/lib.a(_exit.o) + .comment 0x0000000000000000 0x2a lib/lib.a(open.o) + .comment 0x0000000000000000 0x2a lib/lib.a(close.o) + .comment 0x0000000000000000 0x2a lib/lib.a(errno.o) + .comment 0x0000000000000000 0x2a lib/lib.a(write.o) + .comment 0x0000000000000000 0x2a lib/lib.a(dup.o) + .comment 0x0000000000000000 0x2a lib/lib.a(setsid.o) + .comment 0x0000000000000000 0x2a lib/lib.a(execve.o) + .comment 0x0000000000000000 0x2a lib/lib.a(wait.o) + .comment 0x0000000000000000 0x2a lib/lib.a(string.o) + .comment 0x0000000000000000 0x2a lib/lib.a(update.o) + +.debug + *(.debug) + +.line + *(.line) + +.debug_srcinfo + *(.debug_srcinfo) + +.debug_sfnames + *(.debug_sfnames) + +.debug_aranges 0x0000000000000000 0x648 + *(.debug_aranges) + .debug_aranges + 0x0000000000000000 0x20 init/main.o + .debug_aranges + 0x0000000000000020 0x140 kernel/kernel.o + .debug_aranges + 0x0000000000000160 0x20 mm/mm.o + .debug_aranges + 0x0000000000000180 0x238 fs/fs.o + .debug_aranges + 0x00000000000003b8 0x20 kernel/blk_drv/blk_drv.a(ll_rw_blk.o) + .debug_aranges + 0x00000000000003d8 0x20 kernel/blk_drv/blk_drv.a(floppy.o) + .debug_aranges + 0x00000000000003f8 0x20 kernel/blk_drv/blk_drv.a(hd.o) + .debug_aranges + 0x0000000000000418 0x20 kernel/blk_drv/blk_drv.a(ramdisk.o) + .debug_aranges + 0x0000000000000438 0x20 kernel/chr_drv/chr_drv.a(tty_io.o) + .debug_aranges + 0x0000000000000458 0x20 kernel/chr_drv/chr_drv.a(console.o) + .debug_aranges + 0x0000000000000478 0x20 kernel/chr_drv/chr_drv.a(serial.o) + .debug_aranges + 0x0000000000000498 0x20 kernel/chr_drv/chr_drv.a(tty_ioctl.o) + .debug_aranges + 0x00000000000004b8 0x20 kernel/math/math.a(math_emulate.o) + .debug_aranges + 0x00000000000004d8 0x18 lib/lib.a(ctype.o) + .debug_aranges + 0x00000000000004f0 0x20 lib/lib.a(_exit.o) + .debug_aranges + 0x0000000000000510 0x20 lib/lib.a(open.o) + .debug_aranges + 0x0000000000000530 0x20 lib/lib.a(close.o) + .debug_aranges + 0x0000000000000550 0x18 lib/lib.a(errno.o) + .debug_aranges + 0x0000000000000568 0x20 lib/lib.a(write.o) + .debug_aranges + 0x0000000000000588 0x20 lib/lib.a(dup.o) + .debug_aranges + 0x00000000000005a8 0x20 lib/lib.a(setsid.o) + .debug_aranges + 0x00000000000005c8 0x20 lib/lib.a(execve.o) + .debug_aranges + 0x00000000000005e8 0x20 lib/lib.a(wait.o) + .debug_aranges + 0x0000000000000608 0x20 lib/lib.a(string.o) + .debug_aranges + 0x0000000000000628 0x20 lib/lib.a(update.o) + +.debug_pubnames + *(.debug_pubnames) + +.debug_info 0x0000000000000000 0x1821a + *(.debug_info .gnu.linkonce.wi.*) + .debug_info 0x0000000000000000 0xb73 init/main.o + .debug_info 0x0000000000000b73 0x4cb6 kernel/kernel.o + .debug_info 0x0000000000005829 0xba8 mm/mm.o + .debug_info 0x00000000000063d1 0xa628 fs/fs.o + .debug_info 0x00000000000109f9 0x932 kernel/blk_drv/blk_drv.a(ll_rw_blk.o) + .debug_info 0x000000000001132b 0xc9f kernel/blk_drv/blk_drv.a(floppy.o) + .debug_info 0x0000000000011fca 0xd5f kernel/blk_drv/blk_drv.a(hd.o) + .debug_info 0x0000000000012d29 0xad5 kernel/blk_drv/blk_drv.a(ramdisk.o) + .debug_info 0x00000000000137fe 0xacd kernel/chr_drv/chr_drv.a(tty_io.o) + .debug_info 0x00000000000142cb 0xdb0 kernel/chr_drv/chr_drv.a(console.o) + .debug_info 0x000000000001507b 0x85c kernel/chr_drv/chr_drv.a(serial.o) + .debug_info 0x00000000000158d7 0xb47 kernel/chr_drv/chr_drv.a(tty_ioctl.o) + .debug_info 0x000000000001641e 0x7b5 kernel/math/math.a(math_emulate.o) + .debug_info 0x0000000000016bd3 0x66 lib/lib.a(ctype.o) + .debug_info 0x0000000000016c39 0x77 lib/lib.a(_exit.o) + .debug_info 0x0000000000016cb0 0xd0 lib/lib.a(open.o) + .debug_info 0x0000000000016d80 0x97 lib/lib.a(close.o) + .debug_info 0x0000000000016e17 0x36 lib/lib.a(errno.o) + .debug_info 0x0000000000016e4d 0xc9 lib/lib.a(write.o) + .debug_info 0x0000000000016f16 0x97 lib/lib.a(dup.o) + .debug_info 0x0000000000016fad 0x95 lib/lib.a(setsid.o) + .debug_info 0x0000000000017042 0xcb lib/lib.a(execve.o) + .debug_info 0x000000000001710d 0xed lib/lib.a(wait.o) + .debug_info 0x00000000000171fa 0x55e lib/lib.a(string.o) + .debug_info 0x0000000000017758 0xac2 lib/lib.a(update.o) + +.debug_abbrev 0x0000000000000000 0x4625 + *(.debug_abbrev) + .debug_abbrev 0x0000000000000000 0x237 init/main.o + .debug_abbrev 0x0000000000000237 0xf63 kernel/kernel.o + .debug_abbrev 0x000000000000119a 0x20b mm/mm.o + .debug_abbrev 0x00000000000013a5 0x1a6e fs/fs.o + .debug_abbrev 0x0000000000002e13 0x169 kernel/blk_drv/blk_drv.a(ll_rw_blk.o) + .debug_abbrev 0x0000000000002f7c 0x27d kernel/blk_drv/blk_drv.a(floppy.o) + .debug_abbrev 0x00000000000031f9 0x23c kernel/blk_drv/blk_drv.a(hd.o) + .debug_abbrev 0x0000000000003435 0x1a8 kernel/blk_drv/blk_drv.a(ramdisk.o) + .debug_abbrev 0x00000000000035dd 0x279 kernel/chr_drv/chr_drv.a(tty_io.o) + .debug_abbrev 0x0000000000003856 0x26b kernel/chr_drv/chr_drv.a(console.o) + .debug_abbrev 0x0000000000003ac1 0x175 kernel/chr_drv/chr_drv.a(serial.o) + .debug_abbrev 0x0000000000003c36 0x18d kernel/chr_drv/chr_drv.a(tty_ioctl.o) + .debug_abbrev 0x0000000000003dc3 0x163 kernel/math/math.a(math_emulate.o) + .debug_abbrev 0x0000000000003f26 0x3e lib/lib.a(ctype.o) + .debug_abbrev 0x0000000000003f64 0x51 lib/lib.a(_exit.o) + .debug_abbrev 0x0000000000003fb5 0x97 lib/lib.a(open.o) + .debug_abbrev 0x000000000000404c 0x75 lib/lib.a(close.o) + .debug_abbrev 0x00000000000040c1 0x2c lib/lib.a(errno.o) + .debug_abbrev 0x00000000000040ed 0xa1 lib/lib.a(write.o) + .debug_abbrev 0x000000000000418e 0x75 lib/lib.a(dup.o) + .debug_abbrev 0x0000000000004203 0x73 lib/lib.a(setsid.o) + .debug_abbrev 0x0000000000004276 0x85 lib/lib.a(execve.o) + .debug_abbrev 0x00000000000042fb 0xb6 lib/lib.a(wait.o) + .debug_abbrev 0x00000000000043b1 0xe9 lib/lib.a(string.o) + .debug_abbrev 0x000000000000449a 0x18b lib/lib.a(update.o) + +.debug_line 0x0000000000000000 0x4a3f + *(.debug_line .debug_line.* .debug_line_end) + .debug_line 0x0000000000000000 0x1e5 init/main.o + .debug_line 0x00000000000001e5 0xe86 kernel/kernel.o + .debug_line 0x000000000000106b 0x2b4 mm/mm.o + .debug_line 0x000000000000131f 0x1e98 fs/fs.o + .debug_line 0x00000000000031b7 0x197 kernel/blk_drv/blk_drv.a(ll_rw_blk.o) + .debug_line 0x000000000000334e 0x24c kernel/blk_drv/blk_drv.a(floppy.o) + .debug_line 0x000000000000359a 0x2bf kernel/blk_drv/blk_drv.a(hd.o) + .debug_line 0x0000000000003859 0x160 kernel/blk_drv/blk_drv.a(ramdisk.o) + .debug_line 0x00000000000039b9 0x33b kernel/chr_drv/chr_drv.a(tty_io.o) + .debug_line 0x0000000000003cf4 0x3ab kernel/chr_drv/chr_drv.a(console.o) + .debug_line 0x000000000000409f 0xd9 kernel/chr_drv/chr_drv.a(serial.o) + .debug_line 0x0000000000004178 0x1db kernel/chr_drv/chr_drv.a(tty_ioctl.o) + .debug_line 0x0000000000004353 0xe1 kernel/math/math.a(math_emulate.o) + .debug_line 0x0000000000004434 0x28 lib/lib.a(ctype.o) + .debug_line 0x000000000000445c 0x39 lib/lib.a(_exit.o) + .debug_line 0x0000000000004495 0x62 lib/lib.a(open.o) + .debug_line 0x00000000000044f7 0x5c lib/lib.a(close.o) + .debug_line 0x0000000000004553 0x28 lib/lib.a(errno.o) + .debug_line 0x000000000000457b 0x76 lib/lib.a(write.o) + .debug_line 0x00000000000045f1 0x5a lib/lib.a(dup.o) + .debug_line 0x000000000000464b 0x77 lib/lib.a(setsid.o) + .debug_line 0x00000000000046c2 0x5d lib/lib.a(execve.o) + .debug_line 0x000000000000471f 0x7a lib/lib.a(wait.o) + .debug_line 0x0000000000004799 0xc6 lib/lib.a(string.o) + .debug_line 0x000000000000485f 0x1e0 lib/lib.a(update.o) + +.debug_frame + *(.debug_frame) + +.debug_str 0x0000000000000000 0x2232 + *(.debug_str) + .debug_str 0x0000000000000000 0x3c8 init/main.o + 0x46b (size before relaxing) + .debug_str 0x00000000000003c8 0x8ff kernel/kernel.o + 0x2339 (size before relaxing) + .debug_str 0x0000000000000cc7 0x19a mm/mm.o + 0x4f5 (size before relaxing) + .debug_str 0x0000000000000e61 0x975 fs/fs.o + 0x4a0c (size before relaxing) + .debug_str 0x00000000000017d6 0xf0 kernel/blk_drv/blk_drv.a(ll_rw_blk.o) + 0x491 (size before relaxing) + .debug_str 0x00000000000018c6 0x1cf kernel/blk_drv/blk_drv.a(floppy.o) + 0x673 (size before relaxing) + .debug_str 0x0000000000001a95 0x15e kernel/blk_drv/blk_drv.a(hd.o) + 0x5e8 (size before relaxing) + .debug_str 0x0000000000001bf3 0x43 kernel/blk_drv/blk_drv.a(ramdisk.o) + 0x58a (size before relaxing) + .debug_str 0x0000000000001c36 0xfb kernel/chr_drv/chr_drv.a(tty_io.o) + 0x4e3 (size before relaxing) + .debug_str 0x0000000000001d31 0x1b9 kernel/chr_drv/chr_drv.a(console.o) + 0x5b7 (size before relaxing) + .debug_str 0x0000000000001eea 0x1a kernel/chr_drv/chr_drv.a(serial.o) + 0x3fc (size before relaxing) + .debug_str 0x0000000000001f04 0x8b kernel/chr_drv/chr_drv.a(tty_ioctl.o) + 0x4a7 (size before relaxing) + .debug_str 0x0000000000001f8f 0x70 kernel/math/math.a(math_emulate.o) + 0x392 (size before relaxing) + .debug_str 0x0000000000001fff 0x8d lib/lib.a(ctype.o) + 0xb6 (size before relaxing) + .debug_str 0x000000000000208c 0x3c lib/lib.a(_exit.o) + 0xe9 (size before relaxing) + .debug_str 0x0000000000000000 0x3c lib/lib.a(open.o) + 0xf9 (size before relaxing) + .debug_str 0x00000000000020c8 0x8 lib/lib.a(close.o) + 0xeb (size before relaxing) + .debug_str 0x00000000000020d0 0x8 lib/lib.a(errno.o) + 0x93 (size before relaxing) + .debug_str 0x0000000000000000 0x8 lib/lib.a(write.o) + 0xf7 (size before relaxing) + .debug_str 0x00000000000020d8 0x6 lib/lib.a(dup.o) + 0xe3 (size before relaxing) + .debug_str 0x00000000000020de 0x9 lib/lib.a(setsid.o) + 0xf3 (size before relaxing) + .debug_str 0x00000000000020e7 0x9 lib/lib.a(execve.o) + 0xfc (size before relaxing) + .debug_str 0x00000000000020f0 0x11 lib/lib.a(wait.o) + 0x109 (size before relaxing) + .debug_str 0x0000000000002101 0x93 lib/lib.a(string.o) + 0x147 (size before relaxing) + .debug_str 0x0000000000002194 0x9e lib/lib.a(update.o) + 0x4e6 (size before relaxing) + +.debug_loc + *(.debug_loc) + +.debug_macinfo + *(.debug_macinfo) + +.debug_weaknames + *(.debug_weaknames) + +.debug_funcnames + *(.debug_funcnames) + +.debug_typenames + *(.debug_typenames) + +.debug_varnames + *(.debug_varnames) + +.debug_pubtypes + *(.debug_pubtypes) + +.debug_ranges 0x0000000000000000 0x18 + *(.debug_ranges) + .debug_ranges 0x0000000000000000 0x18 init/main.o + +.debug_macro + *(.debug_macro) + +.gnu.attributes + *(.gnu.attributes) + +/DISCARD/ + *(.note.GNU-stack) + *(.gnu_debuglink) + *(.gnu.lto_*) +OUTPUT(tools/system elf32-i386) diff --git a/linux-0.11-lab/1/linux/boot/bootsect b/linux-0.11-lab/1/linux/boot/bootsect new file mode 100755 index 0000000000000000000000000000000000000000..4fbb8f823afe23687f1887d48deeb19fdcf83049 GIT binary patch literal 544 zcmZQ%7GP0e00JfufdrZ$>>UT#`)=%Dn9z4%Cj+DAH_iW_m%fre~uHUSwNXN9*i=ymehGJ;Ln!ff#WtiVnQ zhTZH8d+ix_Fbba)*ufysci@E)!;7N~dJF$B+A=VditBaD0d;UNHUH)>;o2bsq=ibD zUjNfu{D<)s1B1c@RhzFW-(_8 zyWs)N8wX!-zAym_G6SXbtl4ZCONDkYGHA2SVkl+#&o+l)@hk?z1B+)cfHa*h-qdq| z733tt+pm`g1P2Cni_Kx^=9|Ib*m1R6Y!*YuwM`6-j~E!Y0DW7;8WkBGaTw@dps&vg zgE+6x1nv67yn*3e)L{k&UM`>f#FWgubcN!|;*!){1wB1IUM^lPq<|j0Og84wRRH+h BgWdoD literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/boot/bootsect.o b/linux-0.11-lab/1/linux/boot/bootsect.o new file mode 100644 index 0000000000000000000000000000000000000000..e35422ec017a165928bfcbec5f9f0363b4a9e75c GIT binary patch literal 923 zcmYjPe@GKy7=FH+PB$=@gOrLGSb;@HGl?KZQ#V8qHK&qRjLn^EOg*`~_2a*bAQEj2 z`bR7R8DjO1Ax5YD;D!W64T2~X>5mFT9P~#*1c~eYW`BB3fn$y+MeVjqc)FB7D{5ZwQc zlnx;W9UDX^enV$llvLXoyfYO9Z}$=84ic;$V`O7tS=LmkPeZ`p+0`EKHzCjy2sHQl zw}lpeD-uHysXwTY5sDOw1Y=|-4_TXAn>%^rd%=iw84Yc11;O9ydW>fq~$ltjP-a7_y>584mLI>~!sq4M`D5Ly@qm@(>AWA%vwU zr%{<_+X|nde;^cvTBwf1Bxp*gFV1T;>8i$^g?NcKSG5q0@!xcE+`au;IbOSyoY+a~ z{!PR`f4ixx+SO^8CCMcNsiZj%R`aVSzcIBg=v7dW8hevmN}95U=#^i zr)no|09j{lb(WIStn(?vkzMq|I|{AlEXVU%$9xr@m*6E`j|&EKW*r6`Npr0hYp)?r zZZZ#$s1!#JP?cts3OD|gYj$Hl#R^TxZHehkwhp*b#dJ@BG4oNrJhA0o88bcbDr`}l zq`HQqR(%{jBbm%s8(UUwT8Z1NS<0;0*6J{lvGC1C@wAnkO^FJFf$S6TC5rM^{XXi` zL>k>@nq232gLmrem|4t+bg$&5+XH7iM)#1fVRRQc{Pnj!5uJed*5_GV{{}WkC!rMg z_MAVrNM}JOl67*Dd*89})A9sAdKZB*dkfv2*ih7^UQ;z`&?SnZugqR%-#z8CTDl%r F<1c(7E-?TA literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/boot/bootsect.s b/linux-0.11-lab/1/linux/boot/bootsect.s new file mode 100644 index 0000000..711f103 --- /dev/null +++ b/linux-0.11-lab/1/linux/boot/bootsect.s @@ -0,0 +1,260 @@ +! +! SYS_SIZE is the number of clicks (16 bytes) to be loaded. +! 0x3000 is 0x30000 bytes = 196kB, more than enough for current +! versions of linux +! +SYSSIZE = 0x3000 +! +! bootsect.s (C) 1991 Linus Torvalds +! +! bootsect.s is loaded at 0x7c00 by the bios-startup routines, and moves +! iself out of the way to address 0x90000, and jumps there. +! +! It then loads 'setup' directly after itself (0x90200), and the system +! at 0x10000, using BIOS interrupts. +! +! NOTE! currently system is at most 8*65536 bytes long. This should be no +! problem, even in the future. I want to keep it simple. This 512 kB +! kernel size should be enough, especially as this doesn't contain the +! buffer cache as in minix +! +! The loader has been made as simple as possible, and continuos +! read errors will result in a unbreakable loop. Reboot by hand. It +! loads pretty fast by getting whole sectors at a time whenever possible. + +.globl begtext, begdata, begbss, endtext, enddata, endbss +.text +begtext: +.data +begdata: +.bss +begbss: +.text + +SETUPLEN = 4 ! nr of setup-sectors +BOOTSEG = 0x07c0 ! original address of boot-sector +INITSEG = 0x9000 ! we move boot here - out of the way +SETUPSEG = 0x9020 ! setup starts here +SYSSEG = 0x1000 ! system loaded at 0x10000 (65536). +ENDSEG = SYSSEG + SYSSIZE ! where to stop loading + +! ROOT_DEV: 0x000 - same type of floppy as boot. +! 0x301 - first partition on first drive etc +ROOT_DEV = 0x306 + +entry start +start: + mov ax,#BOOTSEG + mov ds,ax + mov ax,#INITSEG + mov es,ax + mov cx,#256 + sub si,si + sub di,di + rep + movw + jmpi go,INITSEG +go: mov ax,cs + mov ds,ax + mov es,ax +! put stack at 0x9ff00. + mov ss,ax + mov sp,#0xFF00 ! arbitrary value >>512 + +! load the setup-sectors directly after the bootblock. +! Note that 'es' is already set up. + +load_setup: + mov dx,#0x0000 ! drive 0, head 0 + mov cx,#0x0002 ! sector 2, track 0 + mov bx,#0x0200 ! address = 512, in INITSEG + mov ax,#0x0200+SETUPLEN ! service 2, nr of sectors + int 0x13 ! read it + jnc ok_load_setup ! ok - continue + mov dx,#0x0000 + mov ax,#0x0000 ! reset the diskette + int 0x13 + j load_setup + +ok_load_setup: + +! Get disk drive parameters, specifically nr of sectors/track + + mov dl,#0x00 + mov ax,#0x0800 ! AH=8 is get drive parameters + int 0x13 + mov ch,#0x00 + seg cs + mov sectors,cx + mov ax,#INITSEG + mov es,ax + +! Print some inane message + + mov ah,#0x03 ! read cursor pos + xor bh,bh + int 0x10 + + mov cx,#24 + mov bx,#0x0007 ! page 0, attribute 7 (normal) + mov bp,#msg1 + mov ax,#0x1301 ! write string, move cursor + int 0x10 + +! ok, we've written the message, now +! we want to load the system (at 0x10000) + + mov ax,#SYSSEG + mov es,ax ! segment of 0x010000 + call read_it + call kill_motor + +! After that we check which root-device to use. If the device is +! defined (!= 0), nothing is done and the given device is used. +! Otherwise, either /dev/PS0 (2,28) or /dev/at0 (2,8), depending +! on the number of sectors that the BIOS reports currently. + + seg cs + mov ax,root_dev + cmp ax,#0 + jne root_defined + seg cs + mov bx,sectors + mov ax,#0x0208 ! /dev/ps0 - 1.2Mb + cmp bx,#15 + je root_defined + mov ax,#0x021c ! /dev/PS0 - 1.44Mb + cmp bx,#18 + je root_defined +undef_root: + jmp undef_root +root_defined: + seg cs + mov root_dev,ax + +! after that (everyting loaded), we jump to +! the setup-routine loaded directly after +! the bootblock: + + jmpi 0,SETUPSEG + +! This routine loads the system at address 0x10000, making sure +! no 64kB boundaries are crossed. We try to load it as fast as +! possible, loading whole tracks whenever we can. +! +! in: es - starting address segment (normally 0x1000) +! +sread: .word 1+SETUPLEN ! sectors read of current track +head: .word 0 ! current head +track: .word 0 ! current track + +read_it: + mov ax,es + test ax,#0x0fff +die: jne die ! es must be at 64kB boundary + xor bx,bx ! bx is starting address within segment +rp_read: + mov ax,es + cmp ax,#ENDSEG ! have we loaded all yet? + jb ok1_read + ret +ok1_read: + seg cs + mov ax,sectors + sub ax,sread + mov cx,ax + shl cx,#9 + add cx,bx + jnc ok2_read + je ok2_read + xor ax,ax + sub ax,bx + shr ax,#9 +ok2_read: + call read_track + mov cx,ax + add ax,sread + seg cs + cmp ax,sectors + jne ok3_read + mov ax,#1 + sub ax,head + jne ok4_read + inc track +ok4_read: + mov head,ax + xor ax,ax +ok3_read: + mov sread,ax + shl cx,#9 + add bx,cx + jnc rp_read + mov ax,es + add ax,#0x1000 + mov es,ax + xor bx,bx + jmp rp_read + +read_track: + push ax + push bx + push cx + push dx + mov dx,track + mov cx,sread + inc cx + mov ch,dl + mov dx,head + mov dh,dl + mov dl,#0 + and dx,#0x0100 + mov ah,#2 + int 0x13 + jc bad_rt + pop dx + pop cx + pop bx + pop ax + ret +bad_rt: mov ax,#0 + mov dx,#0 + int 0x13 + pop dx + pop cx + pop bx + pop ax + jmp read_track + +/* + * This procedure turns off the floppy drive motor, so + * that we enter the kernel in a known state, and + * don't have to worry about it later. + */ +kill_motor: + push dx + mov dx,#0x3f2 + mov al,#0 + outb + pop dx + ret + +sectors: + .word 0 + +msg1: + .byte 13,10 + .ascii "Loading system ..." + .byte 13,10,13,10 + +.org 508 +root_dev: + .word ROOT_DEV +boot_flag: + .word 0xAA55 + +.text +endtext: +.data +enddata: +.bss +endbss: diff --git a/linux-0.11-lab/1/linux/boot/head.o b/linux-0.11-lab/1/linux/boot/head.o new file mode 100644 index 0000000000000000000000000000000000000000..a4c55649c84336692e2f017e7d3b9dc5fd3082ba GIT binary patch literal 27012 zcmeI5O=ule7>2)-rn#v$OwS%uL!8 z6a%qn7P*Sc3jRisn&iB4& z&iUrdGdG*FIOn4m54>cIk-Qk$Ah(^!ke}VzorWRlmW`=8*Nf1++Dw|)n=8(lL2X<) zq}4H0_qtn3hEHg(eMrzN@gL4WGWd|l-26`+&h}(Q)Bb+)4UucVe)-Gw{Sx<}!~D%I z+*?{aEZ2TpTI?Ts6R8Drs4QHmT#)ACbDHqHPI#fPaIkZJx%=grzZ~<#59qk$nEtaG zwGRskkN^pg011!)36KB@kN^pg011!)36KB@kN^pg011!)36KB@kN^pg011!)36KB@ zkN^pg011!)36KB@kN^pg011!)36KB@kN^pg011!)36KB@kN^pg011!)36KB@kN^pg z011!)36KB@kN^pg011!)36KB@{I3YSFZx$|7#nQXbmBLjzwysojfuwek;Xv15&K~{ z6T}bn$jEE2Z|!ovS+gN%tq)^XR$HyssPk=M+o88dFJpht^U^0$N=mKOKTj>|UZ7II z4x`H(J5>#+>Q=Qw)n--0B9~TQ#eSfLn=SeK)YI5gR6e{_N}TOiv2kb*y3Aqg&{f?# zRHRiv)sBntlbK~r0wh2JBtQZrur3L-9K81NMAG<0vMw3$rAdGUNPq-LVBHWXMn|V& zZ%m3&9A>eWtI(e;#{O(9#j+QBQXGq-`^K^jJ@x#QE<0i`Vp6sSL02)fJdSHqsHM(blD3iP(3Pv78q7&_8 zM*5-k_?fI2(eEHwXv&I_5`-Qfll%P;pXV0YUx3zAW3po86$m{&CikN%^o7%6cM$*qTtc_Ysx=5yrWmz#Y0Wq@1&%*1%SXPY8K_u4qV*JPI(}(IbjC`7P zOl$R@sT#=|)qkDIv{wK99Ukv?m%n(Im&lK20=Hg{t*Sze*ZlDbcXsa{@hVv2a|5sH zyZGms^dqTP8`GihV(m}Dz>RbuF1PGQ!HL`fm@lJ4uYeu7y6z=u@~z6cI{M&Nu>=k<<%P!gh--%^>djmB1Ic# zG~x&OiAMa0zq0GKeRF1UbBAE`q28r)_-9Aob|_S NJgpJWKc}%z4Mb on a 4Mb machine). + * + * NOTE! Although all physical memory should be identity + * mapped by this routine, only the kernel page functions + * use the >1Mb addresses directly. All "normal" functions + * use just the lower 1Mb, or the local data space, which + * will be mapped to some other place - mm keeps track of + * that. + * + * For those with more memory than 16 Mb - tough luck. I've + * not got it, why should you :-) The source is here. Change + * it. (Seriously - it shouldn't be too difficult. Mostly + * change some constants etc. I left it at 16Mb, as my machine + * even cannot be extended past that (ok, but it was cheap :-) + * I've tried to show which constants to change by having + * some kind of marker at them (search for "16Mb"), but I + * won't guarantee that's all :-( ) + */ +.align 4 +setup_paging: + movl $1024*5,%ecx /* 5 pages - pg_dir+4 page tables */ + xorl %eax,%eax + xorl %edi,%edi /* pg_dir is at 0x000 */ + cld;rep;stosl + movl $pg0+7,pg_dir /* set present bit/user r/w */ + movl $pg1+7,pg_dir+4 /* --------- " " --------- */ + movl $pg2+7,pg_dir+8 /* --------- " " --------- */ + movl $pg3+7,pg_dir+12 /* --------- " " --------- */ + movl $pg3+4092,%edi + movl $0xfff007,%eax /* 16Mb - 4096 + 7 (r/w user,p) */ + std +1: stosl /* fill pages backwards - more efficient :-) */ + subl $0x1000,%eax + jge 1b + xorl %eax,%eax /* pg_dir is at 0x0000 */ + movl %eax,%cr3 /* cr3 - page directory start */ + movl %cr0,%eax + orl $0x80000000,%eax + movl %eax,%cr0 /* set paging (PG) bit */ + cld /* by wyj */ + ret /* this also flushes prefetch-queue */ + +.align 4 +.word 0 +idt_descr: + .word 256*8-1 # idt contains 256 entries + .long idt +.align 4 +.word 0 +gdt_descr: + .word 256*8-1 # so does gdt (not that that's any + .long gdt # magic number, but it works for me :^) + + .align 8 +idt: .fill 256,8,0 # idt is uninitialized + +gdt: .quad 0x0000000000000000 /* NULL descriptor */ + .quad 0x00c09a0000000fff /* 16Mb */ + .quad 0x00c0920000000fff /* 16Mb */ + .quad 0x0000000000000000 /* TEMPORARY - don't use */ + .fill 252,8,0 /* space for LDT's and TSS's etc */ diff --git a/linux-0.11-lab/1/linux/boot/setup b/linux-0.11-lab/1/linux/boot/setup new file mode 100755 index 0000000000000000000000000000000000000000..0e70f4846819f560fb2e22a8eb1e7186c7956ab0 GIT binary patch literal 344 zcmZQ%7GP0eU|_Id1QJNVq7lN`!7!ok#ujFS|7Qg{#TXd2bet7k%*3#TAIOzsVOY$@ zutjLIz*&LC91NXuTnwFjJPbP+82WA;HDh4}X+5yNfnlcr!{;SXQ3*l_<@!izwL4T8@UUNgLAc(wpUZcuop2&OfjEda<7{%Xg;=gL$t<~Tutazx3hbYqSrLZVca%ibUp9b?$HkVw;4TnF?Rz@46w`UObliF2LrIX1l zD$%Xa$Sgt^u2&7@|GQ@O1M(N{a&->*XRca94ek$5^Qt@KbHx4WGu-r2)9WkibQgy407%ZoGynhq literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/boot/setup.s b/linux-0.11-lab/1/linux/boot/setup.s new file mode 100644 index 0000000..2329d00 --- /dev/null +++ b/linux-0.11-lab/1/linux/boot/setup.s @@ -0,0 +1,231 @@ +! +! setup.s (C) 1991 Linus Torvalds +! +! setup.s is responsible for getting the system data from the BIOS, +! and putting them into the appropriate places in system memory. +! both setup.s and system has been loaded by the bootblock. +! +! This code asks the bios for memory/disk/other parameters, and +! puts them in a "safe" place: 0x90000-0x901FF, ie where the +! boot-block used to be. It is then up to the protected mode +! system to read them from there before the area is overwritten +! for buffer-blocks. +! + +! NOTE! These had better be the same as in bootsect.s! + +INITSEG = 0x9000 ! we move boot here - out of the way +SYSSEG = 0x1000 ! system loaded at 0x10000 (65536). +SETUPSEG = 0x9020 ! this is the current segment + +.globl begtext, begdata, begbss, endtext, enddata, endbss +.text +begtext: +.data +begdata: +.bss +begbss: +.text + +entry start +start: + +! ok, the read went well so we get current cursor position and save it for +! posterity. + + mov ax,#INITSEG ! this is done in bootsect already, but... + mov ds,ax + mov ah,#0x03 ! read cursor pos + xor bh,bh + int 0x10 ! save it in known place, con_init fetches + mov [0],dx ! it from 0x90000. + +! Get memory size (extended mem, kB) + + mov ah,#0x88 + int 0x15 + mov [2],ax + +! Get video-card data: + + mov ah,#0x0f + int 0x10 + mov [4],bx ! bh = display page + mov [6],ax ! al = video mode, ah = window width + +! check for EGA/VGA and some config parameters + + mov ah,#0x12 + mov bl,#0x10 + int 0x10 + mov [8],ax + mov [10],bx + mov [12],cx + +! Get hd0 data + + mov ax,#0x0000 + mov ds,ax + lds si,[4*0x41] + mov ax,#INITSEG + mov es,ax + mov di,#0x0080 + mov cx,#0x10 + rep + movsb + +! Get hd1 data + + mov ax,#0x0000 + mov ds,ax + lds si,[4*0x46] + mov ax,#INITSEG + mov es,ax + mov di,#0x0090 + mov cx,#0x10 + rep + movsb + +! Check that there IS a hd1 :-) + + mov ax,#0x01500 + mov dl,#0x81 + int 0x13 + jc no_disk1 + cmp ah,#3 + je is_disk1 +no_disk1: + mov ax,#INITSEG + mov es,ax + mov di,#0x0090 + mov cx,#0x10 + mov ax,#0x00 + rep + stosb +is_disk1: + +! now we want to move to protected mode ... + + cli ! no interrupts allowed ! + +! first we move the system to it's rightful place + + mov ax,#0x0000 + cld ! 'direction'=0, movs moves forward +do_move: + mov es,ax ! destination segment + add ax,#0x1000 + cmp ax,#0x9000 + jz end_move + mov ds,ax ! source segment + sub di,di + sub si,si + mov cx,#0x8000 + rep + movsw + jmp do_move + +! then we load the segment descriptors + +end_move: + mov ax,#SETUPSEG ! right, forgot this at first. didn't work :-) + mov ds,ax + lidt idt_48 ! load idt with 0,0 + lgdt gdt_48 ! load gdt with whatever appropriate + +! that was painless, now we enable A20 + + call empty_8042 + mov al,#0xD1 ! command write + out #0x64,al + call empty_8042 + mov al,#0xDF ! A20 on + out #0x60,al + call empty_8042 + +! well, that went ok, I hope. Now we have to reprogram the interrupts :-( +! we put them right after the intel-reserved hardware interrupts, at +! int 0x20-0x2F. There they won't mess up anything. Sadly IBM really +! messed this up with the original PC, and they haven't been able to +! rectify it afterwards. Thus the bios puts interrupts at 0x08-0x0f, +! which is used for the internal hardware interrupts as well. We just +! have to reprogram the 8259's, and it isn't fun. + + mov al,#0x11 ! initialization sequence + out #0x20,al ! send it to 8259A-1 + .word 0x00eb,0x00eb ! jmp $+2, jmp $+2 + out #0xA0,al ! and to 8259A-2 + .word 0x00eb,0x00eb + mov al,#0x20 ! start of hardware int's (0x20) + out #0x21,al + .word 0x00eb,0x00eb + mov al,#0x28 ! start of hardware int's 2 (0x28) + out #0xA1,al + .word 0x00eb,0x00eb + mov al,#0x04 ! 8259-1 is master + out #0x21,al + .word 0x00eb,0x00eb + mov al,#0x02 ! 8259-2 is slave + out #0xA1,al + .word 0x00eb,0x00eb + mov al,#0x01 ! 8086 mode for both + out #0x21,al + .word 0x00eb,0x00eb + out #0xA1,al + .word 0x00eb,0x00eb + mov al,#0xFF ! mask off all interrupts for now + out #0x21,al + .word 0x00eb,0x00eb + out #0xA1,al + +! well, that certainly wasn't fun :-(. Hopefully it works, and we don't +! need no steenking BIOS anyway (except for the initial loading :-). +! The BIOS-routine wants lots of unnecessary data, and it's less +! "interesting" anyway. This is how REAL programmers do it. +! +! Well, now's the time to actually move into protected mode. To make +! things as simple as possible, we do no register set-up or anything, +! we let the gnu-compiled 32-bit programs do that. We just jump to +! absolute address 0x00000, in 32-bit protected mode. + + mov ax,#0x0001 ! protected mode (PE) bit + lmsw ax ! This is it! + jmpi 0,8 ! jmp offset 0 of segment 8 (cs) + +! This routine checks that the keyboard command queue is empty +! No timeout is used - if this hangs there is something wrong with +! the machine, and we probably couldn't proceed anyway. +empty_8042: + .word 0x00eb,0x00eb + in al,#0x64 ! 8042 status port + test al,#2 ! is input buffer full? + jnz empty_8042 ! yes - loop + ret + +gdt: + .word 0,0,0,0 ! dummy + + .word 0x07FF ! 8Mb - limit=2047 (2048*4096=8Mb) + .word 0x0000 ! base address=0 + .word 0x9A00 ! code read/exec + .word 0x00C0 ! granularity=4096, 386 + + .word 0x07FF ! 8Mb - limit=2047 (2048*4096=8Mb) + .word 0x0000 ! base address=0 + .word 0x9200 ! data read/write + .word 0x00C0 ! granularity=4096, 386 + +idt_48: + .word 0 ! idt limit=0 + .word 0,0 ! idt base=0L + +gdt_48: + .word 0x800 ! gdt limit=2048, 256 GDT entries + .word 512+gdt,0x9 ! gdt base = 0X9xxxx + +.text +endtext: +.data +enddata: +.bss +endbss: diff --git a/linux-0.11-lab/1/linux/execve2.patch b/linux-0.11-lab/1/linux/execve2.patch new file mode 100755 index 0000000..7d99d4f --- /dev/null +++ b/linux-0.11-lab/1/linux/execve2.patch @@ -0,0 +1,41 @@ +diff -Naur 0/linux/init/main.c 4/linux/init/main.c +--- 0/linux/init/main.c 2016-08-08 09:40:13.000000000 +0800 ++++ 4/linux/init/main.c 2021-07-06 14:16:56.000000000 +0800 +@@ -208,3 +208,9 @@ + } + _exit(0); /* NOTE! _exit, not exit() */ + } ++ ++void print_nr(int sid) ++{ ++ if (sid > 86) ++ printk(" --syscall: sid=%d, pid=%d\n", sid, current->pid); ++} +diff -Naur 0/linux/kernel/system_call.s 4/linux/kernel/system_call.s +--- 0/linux/kernel/system_call.s 2015-09-03 20:21:09.000000000 +0800 ++++ 4/linux/kernel/system_call.s 2021-07-06 14:18:56.000000000 +0800 +@@ -91,6 +91,11 @@ + mov %dx,%es + movl $0x17,%edx # fs points to local data space + mov %dx,%fs ++ ++ pushl %eax #by wyj ++ call print_nr ++ popl %eax ++ + call sys_call_table(,%eax,4) + pushl %eax + movl current,%eax +diff -Naur 0/linux/mm/memory.c 4/linux/mm/memory.c +--- 0/linux/mm/memory.c 2015-09-04 15:24:20.000000000 +0800 ++++ 4/linux/mm/memory.c 2021-07-06 14:21:45.000000000 +0800 +@@ -370,6 +370,9 @@ + unsigned long page; + int block,i; + ++ if (current->pid > 5) ++ printk(" --do_no_page: address=%x, pid=%d\n", address, current->pid); ++ + address &= 0xfffff000; + tmp = address - current->start_code; + if (!current->executable || tmp >= current->end_data) { diff --git a/linux-0.11-lab/1/linux/fs/Makefile b/linux-0.11-lab/1/linux/fs/Makefile new file mode 100644 index 0000000..970acd4 --- /dev/null +++ b/linux-0.11-lab/1/linux/fs/Makefile @@ -0,0 +1,101 @@ +AR =ar +AS =as +LD =ld +LDFLAGS =-s -x +CC =gcc -march=i386 +CFLAGS =-w -g -fstrength-reduce -fomit-frame-pointer -mcld \ + -finline-functions -nostdinc -fno-stack-protector -I../include +CPP =gcc -E -nostdinc -I../include + +.c.s: + $(CC) $(CFLAGS) \ + -S -o $*.s $< +.c.o: + $(CC) $(CFLAGS) \ + -c -o $*.o $< +.s.o: + $(AS) -o $*.o $< + +OBJS= open.o read_write.o inode.o file_table.o buffer.o super.o \ + block_dev.o char_dev.o file_dev.o stat.o exec.o pipe.o namei.o \ + bitmap.o fcntl.o ioctl.o truncate.o select.o + +fs.o: $(OBJS) + $(LD) -r -o fs.o $(OBJS) + +clean: + rm -f core *.o *.a tmp_make + for i in *.c;do rm -f `basename $$i .c`.s;done + +dep: + sed '/\#\#\# Dependencies/q' < Makefile > tmp_make + (for i in *.c;do $(CPP) -M $$i;done) >> tmp_make + cp tmp_make Makefile + +### Dependencies: +bitmap.o : bitmap.c ../include/string.h ../include/linux/sched.h \ + ../include/linux/head.h ../include/linux/fs.h ../include/sys/types.h \ + ../include/linux/mm.h ../include/signal.h ../include/linux/kernel.h +block_dev.o : block_dev.c ../include/errno.h ../include/linux/sched.h \ + ../include/linux/head.h ../include/linux/fs.h ../include/sys/types.h \ + ../include/linux/mm.h ../include/signal.h ../include/linux/kernel.h \ + ../include/asm/segment.h ../include/asm/system.h +buffer.o : buffer.c ../include/stdarg.h ../include/linux/config.h \ + ../include/linux/sched.h ../include/linux/head.h ../include/linux/fs.h \ + ../include/sys/types.h ../include/linux/mm.h ../include/signal.h \ + ../include/linux/kernel.h ../include/asm/system.h ../include/asm/io.h +char_dev.o : char_dev.c ../include/errno.h ../include/sys/types.h \ + ../include/linux/sched.h ../include/linux/head.h ../include/linux/fs.h \ + ../include/linux/mm.h ../include/signal.h ../include/linux/kernel.h \ + ../include/asm/segment.h ../include/asm/io.h +exec.o : exec.c ../include/errno.h ../include/string.h \ + ../include/sys/stat.h ../include/sys/types.h ../include/a.out.h \ + ../include/linux/fs.h ../include/linux/sched.h ../include/linux/head.h \ + ../include/linux/mm.h ../include/signal.h ../include/linux/kernel.h \ + ../include/asm/segment.h +fcntl.o : fcntl.c ../include/string.h ../include/errno.h \ + ../include/linux/sched.h ../include/linux/head.h ../include/linux/fs.h \ + ../include/sys/types.h ../include/linux/mm.h ../include/signal.h \ + ../include/linux/kernel.h ../include/asm/segment.h ../include/fcntl.h \ + ../include/sys/stat.h +file_dev.o : file_dev.c ../include/errno.h ../include/fcntl.h \ + ../include/sys/types.h ../include/linux/sched.h ../include/linux/head.h \ + ../include/linux/fs.h ../include/linux/mm.h ../include/signal.h \ + ../include/linux/kernel.h ../include/asm/segment.h +file_table.o : file_table.c ../include/linux/fs.h ../include/sys/types.h +inode.o : inode.c ../include/string.h ../include/sys/stat.h \ + ../include/sys/types.h ../include/linux/sched.h ../include/linux/head.h \ + ../include/linux/fs.h ../include/linux/mm.h ../include/signal.h \ + ../include/linux/kernel.h ../include/asm/system.h +ioctl.o : ioctl.c ../include/string.h ../include/errno.h \ + ../include/sys/stat.h ../include/sys/types.h ../include/linux/sched.h \ + ../include/linux/head.h ../include/linux/fs.h ../include/linux/mm.h \ + ../include/signal.h +namei.o : namei.c ../include/linux/sched.h ../include/linux/head.h \ + ../include/linux/fs.h ../include/sys/types.h ../include/linux/mm.h \ + ../include/signal.h ../include/linux/kernel.h ../include/asm/segment.h \ + ../include/string.h ../include/fcntl.h ../include/errno.h \ + ../include/const.h ../include/sys/stat.h +open.o : open.c ../include/string.h ../include/errno.h ../include/fcntl.h \ + ../include/sys/types.h ../include/utime.h ../include/sys/stat.h \ + ../include/linux/sched.h ../include/linux/head.h ../include/linux/fs.h \ + ../include/linux/mm.h ../include/signal.h ../include/linux/tty.h \ + ../include/termios.h ../include/linux/kernel.h ../include/asm/segment.h +pipe.o : pipe.c ../include/signal.h ../include/sys/types.h \ + ../include/linux/sched.h ../include/linux/head.h ../include/linux/fs.h \ + ../include/linux/mm.h ../include/asm/segment.h +read_write.o : read_write.c ../include/sys/stat.h ../include/sys/types.h \ + ../include/errno.h ../include/linux/kernel.h ../include/linux/sched.h \ + ../include/linux/head.h ../include/linux/fs.h ../include/linux/mm.h \ + ../include/signal.h ../include/asm/segment.h +stat.o : stat.c ../include/errno.h ../include/sys/stat.h \ + ../include/sys/types.h ../include/linux/fs.h ../include/linux/sched.h \ + ../include/linux/head.h ../include/linux/mm.h ../include/signal.h \ + ../include/linux/kernel.h ../include/asm/segment.h +super.o : super.c ../include/linux/config.h ../include/linux/sched.h \ + ../include/linux/head.h ../include/linux/fs.h ../include/sys/types.h \ + ../include/linux/mm.h ../include/signal.h ../include/linux/kernel.h \ + ../include/asm/system.h ../include/errno.h ../include/sys/stat.h +truncate.o : truncate.c ../include/linux/sched.h ../include/linux/head.h \ + ../include/linux/fs.h ../include/sys/types.h ../include/linux/mm.h \ + ../include/signal.h ../include/sys/stat.h diff --git a/linux-0.11-lab/1/linux/fs/bitmap.c b/linux-0.11-lab/1/linux/fs/bitmap.c new file mode 100644 index 0000000..73951a8 --- /dev/null +++ b/linux-0.11-lab/1/linux/fs/bitmap.c @@ -0,0 +1,168 @@ +/* + * linux/fs/bitmap.c + * + * (C) 1991 Linus Torvalds + */ + +/* bitmap.c contains the code that handles the inode and block bitmaps */ +#include + +#include +#include + +#define clear_block(addr) \ +__asm__ __volatile__ ("cld\n\t" \ + "rep\n\t" \ + "stosl" \ + ::"a" (0),"c" (BLOCK_SIZE/4),"D" ((long) (addr))) + +#define set_bit(nr,addr) ({\ +register int res __asm__("ax"); \ +__asm__ __volatile__("btsl %2,%3\n\tsetb %%al": \ +"=a" (res):"0" (0),"r" (nr),"m" (*(addr))); \ +res;}) + +#define clear_bit(nr,addr) ({\ +register int res __asm__("ax"); \ +__asm__ __volatile__("btrl %2,%3\n\tsetnb %%al": \ +"=a" (res):"0" (0),"r" (nr),"m" (*(addr))); \ +res;}) + +#define find_first_zero(addr) ({ \ +int __res; \ +__asm__ __volatile__ ("cld\n" \ + "1:\tlodsl\n\t" \ + "notl %%eax\n\t" \ + "bsfl %%eax,%%edx\n\t" \ + "je 2f\n\t" \ + "addl %%edx,%%ecx\n\t" \ + "jmp 3f\n" \ + "2:\taddl $32,%%ecx\n\t" \ + "cmpl $8192,%%ecx\n\t" \ + "jl 1b\n" \ + "3:" \ + :"=c" (__res):"c" (0),"S" (addr)); \ +__res;}) + +void free_block(int dev, int block) +{ + struct super_block * sb; + struct buffer_head * bh; + + if (!(sb = get_super(dev))) + panic("trying to free block on nonexistent device"); + if (block < sb->s_firstdatazone || block >= sb->s_nzones) + panic("trying to free block not in datazone"); + bh = get_hash_table(dev,block); + if (bh) { + if (bh->b_count != 1) { + printk("trying to free block (%04x:%d), count=%d\n", + dev,block,bh->b_count); + return; + } + bh->b_dirt=0; + bh->b_uptodate=0; + brelse(bh); + } + block -= sb->s_firstdatazone - 1 ; + if (clear_bit(block&8191,sb->s_zmap[block/8192]->b_data)) { + printk("block (%04x:%d) ",dev,block+sb->s_firstdatazone-1); + panic("free_block: bit already cleared"); + } + sb->s_zmap[block/8192]->b_dirt = 1; +} + +int new_block(int dev) +{ + struct buffer_head * bh; + struct super_block * sb; + int i,j; + + if (!(sb = get_super(dev))) + panic("trying to get new block from nonexistant device"); + j = 8192; + for (i=0 ; i<8 ; i++) + if (bh=sb->s_zmap[i]) + if ((j=find_first_zero(bh->b_data))<8192) + break; + if (i>=8 || !bh || j>=8192) + return 0; + if (set_bit(j,bh->b_data)) + panic("new_block: bit already set"); + bh->b_dirt = 1; + j += i*8192 + sb->s_firstdatazone-1; + if (j >= sb->s_nzones) + return 0; + if (!(bh=getblk(dev,j))) + panic("new_block: cannot get block"); + if (bh->b_count != 1) + panic("new block: count is != 1"); + clear_block(bh->b_data); + bh->b_uptodate = 1; + bh->b_dirt = 1; + brelse(bh); + return j; +} + +void free_inode(struct m_inode * inode) +{ + struct super_block * sb; + struct buffer_head * bh; + + if (!inode) + return; + if (!inode->i_dev) { + memset(inode,0,sizeof(*inode)); + return; + } + if (inode->i_count>1) { + printk("trying to free inode with count=%d\n",inode->i_count); + panic("free_inode"); + } + if (inode->i_nlinks) + panic("trying to free inode with links"); + if (!(sb = get_super(inode->i_dev))) + panic("trying to free inode on nonexistent device"); + if (inode->i_num < 1 || inode->i_num > sb->s_ninodes) + panic("trying to free inode 0 or nonexistant inode"); + if (!(bh=sb->s_imap[inode->i_num>>13])) + panic("nonexistent imap in superblock"); + if (clear_bit(inode->i_num&8191,bh->b_data)) + printk("free_inode: bit already cleared.\n\r"); + bh->b_dirt = 1; + memset(inode,0,sizeof(*inode)); +} + +struct m_inode * new_inode(int dev) +{ + struct m_inode * inode; + struct super_block * sb; + struct buffer_head * bh; + int i,j; + + if (!(inode=get_empty_inode())) + return NULL; + if (!(sb = get_super(dev))) + panic("new_inode with unknown device"); + j = 8192; + for (i=0 ; i<8 ; i++) + if (bh=sb->s_imap[i]) + if ((j=find_first_zero(bh->b_data))<8192) + break; + if (!bh || j >= 8192 || j+i*8192 > sb->s_ninodes) { + iput(inode); + return NULL; + } + if (set_bit(j,bh->b_data)) + panic("new_inode: bit already set"); + bh->b_dirt = 1; + inode->i_count=1; + inode->i_nlinks=1; + inode->i_dev=dev; + inode->i_uid=current->euid; + inode->i_gid=current->egid; + inode->i_dirt=1; + inode->i_num = j + i*8192; + inode->i_mtime = inode->i_atime = inode->i_ctime = CURRENT_TIME; + return inode; +} diff --git a/linux-0.11-lab/1/linux/fs/bitmap.o b/linux-0.11-lab/1/linux/fs/bitmap.o new file mode 100644 index 0000000000000000000000000000000000000000..501d3c5e3fb1a044792589a0bdde55cbb41cfaa2 GIT binary patch literal 10280 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 J@|j5fe*vQQ&y@fG literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/fs/block_dev.c b/linux-0.11-lab/1/linux/fs/block_dev.c new file mode 100644 index 0000000..a50ae3f --- /dev/null +++ b/linux-0.11-lab/1/linux/fs/block_dev.c @@ -0,0 +1,73 @@ +/* + * linux/fs/block_dev.c + * + * (C) 1991 Linus Torvalds + */ + +#include + +#include +#include +#include +#include + +int block_write(int dev, long * pos, char * buf, int count) +{ + int block = *pos >> BLOCK_SIZE_BITS; + int offset = *pos & (BLOCK_SIZE-1); + int chars; + int written = 0; + struct buffer_head * bh; + register char * p; + + while (count>0) { + chars = BLOCK_SIZE - offset; + if (chars > count) + chars=count; + if (chars == BLOCK_SIZE) + bh = getblk(dev,block); + else + bh = breada(dev,block,block+1,block+2,-1); + block++; + if (!bh) + return written?written:-EIO; + p = offset + bh->b_data; + offset = 0; + *pos += chars; + written += chars; + count -= chars; + while (chars-->0) + *(p++) = get_fs_byte(buf++); + bh->b_dirt = 1; + brelse(bh); + } + return written; +} + +int block_read(int dev, unsigned long * pos, char * buf, int count) +{ + int block = *pos >> BLOCK_SIZE_BITS; + int offset = *pos & (BLOCK_SIZE-1); + int chars; + int read = 0; + struct buffer_head * bh; + register char * p; + + while (count>0) { + chars = BLOCK_SIZE-offset; + if (chars > count) + chars = count; + if (!(bh = breada(dev,block,block+1,block+2,-1))) + return read?read:-EIO; + block++; + p = offset + bh->b_data; + offset = 0; + *pos += chars; + read += chars; + count -= chars; + while (chars-->0) + put_fs_byte(*(p++),buf++); + brelse(bh); + } + return read; +} diff --git a/linux-0.11-lab/1/linux/fs/block_dev.o b/linux-0.11-lab/1/linux/fs/block_dev.o new file mode 100644 index 0000000000000000000000000000000000000000..e5e9334ce9a4697061730271c4c9d92fcf4aa105 GIT binary patch literal 7296 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 + +#include +#include +#include +#include +#include + +extern void put_super(int dev); +extern void invalidate_inodes(int dev); + +extern int end; +struct buffer_head * start_buffer = (struct buffer_head *) &end; +struct buffer_head * hash_table[NR_HASH]; +static struct buffer_head * free_list; +static struct task_struct * buffer_wait = NULL; +int NR_BUFFERS = 0; + +static inline void wait_on_buffer(struct buffer_head * bh) +{ + cli(); + while (bh->b_lock) + sleep_on(&bh->b_wait); + sti(); +} + +int sys_sync(void) +{ + int i; + struct buffer_head * bh; + + sync_inodes(); /* write out inodes into buffers */ + bh = start_buffer; + for (i=0 ; ib_dirt) + ll_rw_block(WRITE,bh); + } + return 0; +} + +int sync_dev(int dev) +{ + int i; + struct buffer_head * bh; + + bh = start_buffer; + for (i=0 ; ib_dev != dev) + continue; + wait_on_buffer(bh); + if (bh->b_dev == dev && bh->b_dirt) + ll_rw_block(WRITE,bh); + } + sync_inodes(); + bh = start_buffer; + for (i=0 ; ib_dev != dev) + continue; + wait_on_buffer(bh); + if (bh->b_dev == dev && bh->b_dirt) + ll_rw_block(WRITE,bh); + } + return 0; +} + +void inline invalidate_buffers(int dev) +{ + int i; + struct buffer_head * bh; + + bh = start_buffer; + for (i=0 ; ib_dev != dev) + continue; + wait_on_buffer(bh); + if (bh->b_dev == dev) + bh->b_uptodate = bh->b_dirt = 0; + } +} + +/* + * This routine checks whether a floppy has been changed, and + * invalidates all buffer-cache-entries in that case. This + * is a relatively slow routine, so we have to try to minimize using + * it. Thus it is called only upon a 'mount' or 'open'. This + * is the best way of combining speed and utility, I think. + * People changing diskettes in the middle of an operation deserve + * to loose :-) + * + * NOTE! Although currently this is only for floppies, the idea is + * that any additional removable block-device will use this routine, + * and that mount/open needn't know that floppies/whatever are + * special. + */ +void check_disk_change(int dev) +{ + int i; + + if (MAJOR(dev) != 2) + return; + if (!floppy_change(dev & 0x03)) + return; + for (i=0 ; ib_next) + bh->b_next->b_prev = bh->b_prev; + if (bh->b_prev) + bh->b_prev->b_next = bh->b_next; + if (hash(bh->b_dev,bh->b_blocknr) == bh) + hash(bh->b_dev,bh->b_blocknr) = bh->b_next; +/* remove from free list */ + if (!(bh->b_prev_free) || !(bh->b_next_free)) + panic("Free block list corrupted"); + bh->b_prev_free->b_next_free = bh->b_next_free; + bh->b_next_free->b_prev_free = bh->b_prev_free; + if (free_list == bh) + free_list = bh->b_next_free; +} + +static inline void insert_into_queues(struct buffer_head * bh) +{ +/* put at end of free list */ + bh->b_next_free = free_list; + bh->b_prev_free = free_list->b_prev_free; + free_list->b_prev_free->b_next_free = bh; + free_list->b_prev_free = bh; +/* put the buffer in new hash-queue if it has a device */ + bh->b_prev = NULL; + bh->b_next = NULL; + if (!bh->b_dev) + return; + bh->b_next = hash(bh->b_dev,bh->b_blocknr); + hash(bh->b_dev,bh->b_blocknr) = bh; + bh->b_next->b_prev = bh; +} + +static struct buffer_head * find_buffer(int dev, int block) +{ + struct buffer_head * tmp; + + for (tmp = hash(dev,block) ; tmp != NULL ; tmp = tmp->b_next) + if (tmp->b_dev==dev && tmp->b_blocknr==block) + return tmp; + return NULL; +} + +/* + * Why like this, I hear you say... The reason is race-conditions. + * As we don't lock buffers (unless we are readint them, that is), + * something might happen to it while we sleep (ie a read-error + * will force it bad). This shouldn't really happen currently, but + * the code is ready. + */ +struct buffer_head * get_hash_table(int dev, int block) +{ + struct buffer_head * bh; + + for (;;) { + if (!(bh=find_buffer(dev,block))) + return NULL; + bh->b_count++; + wait_on_buffer(bh); + if (bh->b_dev == dev && bh->b_blocknr == block) + return bh; + bh->b_count--; + } +} + +/* + * Ok, this is getblk, and it isn't very clear, again to hinder + * race-conditions. Most of the code is seldom used, (ie repeating), + * so it should be much more efficient than it looks. + * + * The algoritm is changed: hopefully better, and an elusive bug removed. + */ +#define BADNESS(bh) (((bh)->b_dirt<<1)+(bh)->b_lock) +struct buffer_head * getblk(int dev,int block) +{ + struct buffer_head * tmp, * bh; + +repeat: + if (bh = get_hash_table(dev,block)) + return bh; + tmp = free_list; + do { + if (tmp->b_count) + continue; + if (!bh || BADNESS(tmp)b_next_free) != free_list); + if (!bh) { + sleep_on(&buffer_wait); + goto repeat; + } + wait_on_buffer(bh); + if (bh->b_count) + goto repeat; + while (bh->b_dirt) { + sync_dev(bh->b_dev); + wait_on_buffer(bh); + if (bh->b_count) + goto repeat; + } +/* NOTE!! While we slept waiting for this block, somebody else might */ +/* already have added "this" block to the cache. check it */ + if (find_buffer(dev,block)) + goto repeat; +/* OK, FINALLY we know that this buffer is the only one of it's kind, */ +/* and that it's unused (b_count=0), unlocked (b_lock=0), and clean */ + bh->b_count=1; + bh->b_dirt=0; + bh->b_uptodate=0; + remove_from_queues(bh); + bh->b_dev=dev; + bh->b_blocknr=block; + insert_into_queues(bh); + return bh; +} + +void brelse(struct buffer_head * buf) +{ + if (!buf) + return; + wait_on_buffer(buf); + if (!(buf->b_count--)) + panic("Trying to free free buffer"); + wake_up(&buffer_wait); +} + +/* + * bread() reads a specified block and returns the buffer that contains + * it. It returns NULL if the block was unreadable. + */ +struct buffer_head * bread(int dev,int block) +{ + struct buffer_head * bh; + + if (!(bh=getblk(dev,block))) + panic("bread: getblk returned NULL\n"); + if (bh->b_uptodate) + return bh; + ll_rw_block(READ,bh); + wait_on_buffer(bh); + if (bh->b_uptodate) + return bh; + brelse(bh); + return NULL; +} + +#define COPYBLK(from,to) \ +__asm__("cld\n\t" \ + "rep\n\t" \ + "movsl\n\t" \ + ::"c" (BLOCK_SIZE/4),"S" (from),"D" (to) \ + ) + +/* + * bread_page reads four buffers into memory at the desired address. It's + * a function of its own, as there is some speed to be got by reading them + * all at the same time, not waiting for one to be read, and then another + * etc. + */ +void bread_page(unsigned long address,int dev,int b[4]) +{ + struct buffer_head * bh[4]; + int i; + + for (i=0 ; i<4 ; i++) + if (b[i]) { + if (bh[i] = getblk(dev,b[i])) + if (!bh[i]->b_uptodate) + ll_rw_block(READ,bh[i]); + } else + bh[i] = NULL; + for (i=0 ; i<4 ; i++,address += BLOCK_SIZE) + if (bh[i]) { + wait_on_buffer(bh[i]); + if (bh[i]->b_uptodate) + COPYBLK((unsigned long) bh[i]->b_data,address); + brelse(bh[i]); + } +} + +/* + * Ok, breada can be used as bread, but additionally to mark other + * blocks for reading as well. End the argument list with a negative + * number. + */ +struct buffer_head * breada(int dev,int first, ...) +{ + va_list args; + struct buffer_head * bh, *tmp; + + va_start(args,first); + if (!(bh=getblk(dev,first))) + panic("bread: getblk returned NULL\n"); + if (!bh->b_uptodate) + ll_rw_block(READ,bh); + while ((first=va_arg(args,int))>=0) { + tmp=getblk(dev,first); + if (tmp) { + if (!tmp->b_uptodate) + ll_rw_block(READA,bh); + tmp->b_count--; + } + } + va_end(args); + wait_on_buffer(bh); + if (bh->b_uptodate) + return bh; + brelse(bh); + return (NULL); +} + +void buffer_init(long buffer_end) +{ + struct buffer_head * h = start_buffer; + void * b; + int i; + + if (buffer_end == 1<<20) + b = (void *) (640*1024); + else + b = (void *) buffer_end; + while ( (b -= BLOCK_SIZE) >= ((void *) (h+1)) ) { + h->b_dev = 0; + h->b_dirt = 0; + h->b_count = 0; + h->b_lock = 0; + h->b_uptodate = 0; + h->b_wait = NULL; + h->b_next = NULL; + h->b_prev = NULL; + h->b_data = (char *) b; + h->b_prev_free = h-1; + h->b_next_free = h+1; + h++; + NR_BUFFERS++; + if (b == (void *) 0x100000) + b = (void *) 0xA0000; + } + h--; + free_list = start_buffer; + free_list->b_prev_free = h; + h->b_next_free = free_list; + for (i=0;iQ6+~nZ1VPZCP{pdlWadpWGMO3Y4-glv z7*S%>7VB1P-Nm-HYhAN#)$LZ}w$ZB8+ONe=TerJ@TU$Tc(rCMCt$(}h?|0vMlL55d z-TBD;&N=s-bI(2Z+7+#v%)Y8<$Vn0Qxlw0+gse0E)BEQG}WjEUu%AUeDd(} zmdM~({gA)qw;vunc#!PP(MdOqm4E%g;8V@tAAGG<%fCd!q2(=2dzZH~lOFGaY7@;K zam|`;j@I5VRtjtJ@)rMIe+whf)(2rU2=x~2W+AxkPke`72A^tW7e{*kB;5>0?aBW# zwrF`vXUQC2Dk_?1`&sH_~Q^ zBE!+9onxg2A<;=>_`>i|H;W8y;fc1e+txJH-Q>2Ra`w5Df9}3V=c5!KWAyL5F|=>k zzmp{DDpKzF>)N{0rlGJla@CvBF>{R=B1l*WwN8(f6*L@ecH@Z*bw@o>}}W>g;;L1T%#Z!ZM5nT@P!r;g3l@Hj>bICzL{!MI0_q)qJ;~whNyu zTV%(Nc9oiFF}S@Yq{`3A`l;u}fz~cG(WY|<6}$s`1NdgBHmh=tRvq7f*5;d|p>s}-@+%ZnN3yp z_Hho3eR}ebWjkt>{p&!u1yA026=Ky9lp9dNHfly!@PXN~!ww-uKYP#J^pHP<95@g{ z+ju+t$u>wGIXLub@U_GAUzSZv@6P4DFgzq(`~H0JAQn^Lz$2pfOfYSxu>-vu&Vz3b{qYP(~38)nyOC=pqUm8Z#VWdyN|&&N!6A!QnM6kzMOB zFujD2^%78>j6wGhg#96L%QQ=&aRWHjvxX|FEr@Kfgqz3D<~K6W6Oqf(OP8*|t?#-O zSZ%=VPB*fX%4u=&CodX&trHt_E1ev;3184_y|uCg&o%Z9E97$1M~K-y#LI`g*;?Py zI<))_79-Zs4cyO8^=KVR`DBkhJo0g_p4PoEVjS4cTan~e-{jk}h}H{l-0{renMa!L zWeC0B_>La1=G{S`;584cp(nq?$ClyCTB1Ww4E=2A7azXGQ=($bgs{gQ%UhxfJEiXV z+B*iH>ipCdG42PqVwwiW{H$}>ebkJ(3scW`^^9RvVaCe(JUwE>>&7qm7;j-j5LP8_ zWntGt_4AL31bMTKW?gYm#P)%Qp=M497UhTNj#b>Xb8O%XKwasZ{^XXin<3Uw(>TjQ zHy%7Iw{-9Eg75*6PNXN3OKgs0(#29Fkt-C+`I3`V>k9+vY;UBLi=?Qdzk154lv7YW z1t*?7Bhu@XdNP|M1*cRlWSwN>{0(c?1l6e_#WCRHH-3U|<6GdK_i2fGJLsZ$0nq2~ z)ZeG!+izI6K`(FyXxsE(0kGoA43JP(k5GQ)_t&gPH34S9C18r?0z6r2{DE|~r2J;h z5QT>QXQ-Gjpv504!cAZ?_?E!((;>0vQ*aIgP<98@11s2--)^IPIb;B6eFX3jQ){TRN> zEH`U=srD(VtuTWrI?&9yX0Vg4HM80bK1b#VY*f&ES(4i{(1qcE$YMXWs%mbU;LjG6k#7W!sAd9ZY zE!gWI2_)Qty@Wc+mH4i+2QZXCiq#jfhp5v_+ZKBkZTm>iwhxd_v#(ZrCHuXSbi4f? z>CL1&?N>=>=zpI50O@|x^X*SFwk+u`dj;tn=~L|`r1PXtvmd4Zt4N=&0?jb450scs zdmEL?JJ6u)he>ZCZQ9dmu$8pmUc~`y)9Q8`J0AE9C>quMnC+T_zY1>{%`SqlO_U8=HgUn6Ho=@8wD6hA9DgM>gr9-sj&B2#msi#+tnm^=l=#FiznDR92Dn zCrJCP66ralZ7Y?|E31`s$Vw$p`fa4^tyC_jtaj32(2#eKZnBTUK&?)?Z&o3SxKi}s z8dcyvjOaycK6gF)Jp^KPQA64H)96&veydpQRMu&vZF_|B(@BRQpR23|r0ebb@NF$5 z9fo|Kvd$pgWF-pom9>a;v*j@GGf7A6KJ;rXCf#B=@omaFi}Y;ENqBUt+9Tv^LVo@+5(%So<5l*&4XWVe+Bxq{?+ zD+O{T$xEzWkmr)T%+lMgowUzq#?E^Uv)HFXcLKOQ>C{eFp%+2(Pg3pk zbK40mhT-o#si_*i4&IoBFEx|YJ(IAQru6hd#yT{yBRAH<&gfv}P$i+&_{1>e(xTb?>wS%RegQ*4vV_dug<11+6?^cZU zK`6!>tBo(M7`MU9D7}U62ek3;E5;?)K=-^wj8(%XYTfvED6Mz2e#23cgB!gZOnVZI z#$9(HB~NRWE>GnyPvz*XRQWpDjTn8OR@+83J?5`V&rNHY8sYrmQh#0<|LFSIrW!9| zaRK8^-g8xDZalctLz< zhr;w7a~=KtbOn5=V+Tkp#t8{FO;rKW_QBvw!W1;z&h&s)G0+qH?Yu-RjoryX_ zVmMx>!ejj>u!QQxO-3F22fCSKd;=~{)T8(%TpWKY1_mkjRuqBjagKQOAJ@Y+>Y2N3 z?XS)Fjpi;p0kzgHdKv71j6rX;@1R{T5ua+liQ_v*hwwaV=4~DM<+Wbq=Tstpno)SH ze|lsc(qpVNX6mRiy61CcBz-67IriA3n(;bE6EmK{ymsh;J%ApL{{mgc3@&U8>;&W@ zE*`d>fMN9*)G~LMIFN({l2<4CPx?87K8e{6_&}C<=6DQ!qD6lg?@Sm{O!>my) zEQ-K=KZa!HooF{^xW*vW%vH?#OlBtl2TGmnWRuE>RMIsISA$s&8gLDni4iE{#Ay(@ z%F1XkX4W;<`s$9WYcQr*^+zM*Y06i3M(v{7RgE}#CaYRa;O#+e?O9NSX`|t*tF5Jq z0TpYK^4YHb0z_CNiWrEE7V*TEqqJSXvkO+WVm4~4+<*-k#;QiTpEN_QYV3e{-Be@N zF_cUWK!P)5s+x6-QVs2hhCXKni8mlWj0|`Y&Vu1<0-CcJVZ6zb%^TJ zYSlv&rybtcoo-)8Pslyj($a(|Bn6D(n4qu?n9*Y^{R9q+{Wys|u&R+(&DDxt2Qtj# zr2|ntL53pibXcnhWQ;*%GpfD0!;@f7qyk)x zS$fVei+F-SLE#UN1^Sy`-hGtxVlALlLER*L>)(;M%G%pI(%D3&oOC)e>1=tM znh;cx9mRp7QtlnOJwca!xF@$`H7ZpsCF6x&(CDNzkavn8u|`rvHYfTVPcz+{jb~g< z6u6GqH_KQ&qeGc~A^H#^G=HIkN?9-*?VJLpI zTrA$QFY;7<4Xc-oZnQf(_L#F8%~R^Ne6_W8bhP`d5xWup%=SjJBdp~QS|g)&Bc!8i z!_V&D|MYQo8&0 z5j{4mWSI*a2kmF)+Pll6myV8X?67Byj?l;YN9^*a1_uX6M@L4_Tf4a2F>0STI=XI& z{nF@2ue}&wqZ@totFL_4?ln(u+;89RyZSNR_iF3mJ)>{!x1W7ovyWMSvpqUOD|_*I zcDW3o`~%-nc1b%~yZDYhJ1-vGxCfmLj*N`#dFiE%BYUXhyXtyhgMIzRJ)_TpH7PS+ zWrMZay4UohT#B*m)wwL5*!tqdzE~;VlW|lrmhO+|0X)8nrFfwf!*^n{>d_K>$4haQ zbczYc3*|&fVb64hTjDXkl2OHYER~7liLT)E=e9VpR3X&oR5$z;L7eMa)h9aHH^a)2>bD!OB8^uo}79CtY&wQ*fx(mf!X&LU7Q09_G9 zI7S6}zWFqQ_buK$CyH)3UMKyUO{EK1bMZ{P(62iBa{W$6wwx?=F{VhRZoZ z@Y!;|n*-KAUa_(OaVDsIZy~Q7J;Qoi@e+=z%M=~#4|yk!YUI4cvA__ATgxf~34&lm zdg?HNtRXiZ998ZlyXkPh;|L6!0xAP@#HHZwMQOKS`cWdR2rLFxGAi0#ve_;1Oq!Kc zsoxU3cnQZwhLxVo@C`C5u9VX?2Pp~wTLJ@g<4TEpoS00Jo)Yepx(u+R7R%UC-Q_Ly zt5aIY^jAj;tt9q8Xx283zf0mHjWGV z{kw1&Q?7s00nVhtvbspT&adTNBGbqFvbs()R_CYw8vO0TAFr#>?=;_byKO;pRX zu6#S>-X&AZzvjyCfZV%GvS0J9IzNATco2Wy4HBe|Wen(D7oi(Aldg|{gWS6UYTwt^ z`T6kmU-QcLUXo6Mzk zp&NZm>*@#n%j%-OCZn!?>G$hGOP{H;m+p0af+_;!???MB4*f+_21QYxp~lbVkAV0CP%ZjBds z_|TAkv=Wam&j9_Y_C&6~-@!rCp2g|aj&spH&0HI&54$Q(KqT^i`I!zq3|ZkOtUs)& z>IYG_@x!-;yd`;`a4T*acphZEQHOKKJK8D2>pK_dRy;UQJmOB!tmSHdE$yy7{n6I* z*8!S-J%63>hih8por2|&F_~$SC8XCjAI*Q97lubaa^RmS^=qk zbQ1Ok67um}SNF-L*YN6a3_(lW1&h5o8r z$yfJ4K2Vu!#$kYGOdOxbM?mw#bz~ml&r)1B-rmjjv%!0NHu(+Uz5V(~dsg_w$9G8P z86PWg;^RAHMY0`lL#jSLoyiG-PtQ^{KUu|v<@g%lAv@8mt@-veg1;X@p+UWQkoC%s zs~^yH=}O#rWBoBV3H(jLc<=Taft=T`9mYQdp0&+0llr4T@2n*MWANS?N&Xe^-iQ8v z?=e8~?;pndtEQao(+=aC!F%T<{m%jKosZ=CW4U)Gl3#e3{ZjDW*~s>l;Jq`E{Dt7X z^N##R@ZLE`e&YFS;sLAr5%I8V+DBafKH_=3`ZnM`*10bE_*{K4t-50rGmewT^ZLY7 ztA0?FXX#8PR@my@n<@{GM?UEtd7(>Xa{2s#cfG?yTjl|YY{9^J_G-In0TU6 ze@i@GsSkn1G^OTZOCp|6#Kv0-6HsT!7mGbOK?oE5xVrVLU5}ff5kLg zl*$3=?_I%qJcy8=3S^#E6LA(bU`t{g(}0ZQc=FIYk^C%-kB9|-0p-wJPab*$MC9ko z#FNnv5qk5XL;1r*$p1iu+`xuUdkaW=z8a?9Vj|jmg@2R?yB`8M5B=B@ng62T{Y1z| zh=}tc!S4zF2N8MU$H1Y3VJc&idnOy$AXq0vG-<^9MP*=aFlEY^jCYG7UnqE%U|g_I zFekW0@CLzQ!OseQQScuG9~S(c;B$g63BD@$2f+^nYgl)PyHRkuAonxM7YLpsxK8kL zLH=hG>Xik#2b1Uj&mewL@P5I67W|3e0l_~B>fdl+$7faAe?std!F7UH2yPbKCb(1Z zcELS@4+`>s3DEBgg0Bnm7kkQUd@hCs`M(?}PYUJ*w+rqPWB5I)ydkWi|h~SqBf1dEy3%^VF?+O33@Z6th|F-Z` zxbM&(5&ljUeu?mx2|pk>DDr!Se_W8y0JMKq_z?Fc_?<$8yh-@!!k;DlD&c#D-zj*D z$iFE3yMjL4v*>RI5&q{2ULoj6dr9~a!AFUxk?#usL*aiR{O<(+M8tmkf$%lB+;Bgh zO+ +#include + +#include +#include + +#include +#include + +extern int tty_read(unsigned minor,char * buf,int count); +extern int tty_write(unsigned minor,char * buf,int count); + +typedef (*crw_ptr)(int rw,unsigned minor,char * buf,int count,off_t * pos); + +static int rw_ttyx(int rw,unsigned minor,char * buf,int count,off_t * pos) +{ + return ((rw==READ)?tty_read(minor,buf,count): + tty_write(minor,buf,count)); +} + +static int rw_tty(int rw,unsigned minor,char * buf,int count, off_t * pos) +{ + if (current->tty<0) + return -EPERM; + return rw_ttyx(rw,current->tty,buf,count,pos); +} + +static int rw_ram(int rw,char * buf, int count, off_t *pos) +{ + return -EIO; +} + +static int rw_mem(int rw,char * buf, int count, off_t * pos) +{ + return -EIO; +} + +static int rw_kmem(int rw,char * buf, int count, off_t * pos) +{ + return -EIO; +} + +static int rw_port(int rw,char * buf, int count, off_t * pos) +{ + int i=*pos; + + while (count-->0 && i<65536) { + if (rw==READ) + put_fs_byte(inb(i),buf++); + else + outb(get_fs_byte(buf++),i); + i++; + } + i -= *pos; + *pos += i; + return i; +} + +static int rw_memory(int rw, unsigned minor, char * buf, int count, off_t * pos) +{ + switch(minor) { + case 0: + return rw_ram(rw,buf,count,pos); + case 1: + return rw_mem(rw,buf,count,pos); + case 2: + return rw_kmem(rw,buf,count,pos); + case 3: + return (rw==READ)?0:count; /* rw_null */ + case 4: + return rw_port(rw,buf,count,pos); + default: + return -EIO; + } +} + +#define NRDEVS ((sizeof (crw_table))/(sizeof (crw_ptr))) + +static crw_ptr crw_table[]={ + NULL, /* nodev */ + rw_memory, /* /dev/mem etc */ + NULL, /* /dev/fd */ + NULL, /* /dev/hd */ + rw_ttyx, /* /dev/ttyx */ + rw_tty, /* /dev/tty */ + NULL, /* /dev/lp */ + NULL}; /* unnamed pipes */ + +int rw_char(int rw,int dev, char * buf, int count, off_t * pos) +{ + crw_ptr call_addr; + + if (MAJOR(dev)>=NRDEVS) + return -ENODEV; + if (!(call_addr=crw_table[MAJOR(dev)])) + return -ENODEV; + return call_addr(rw,MINOR(dev),buf,count,pos); +} diff --git a/linux-0.11-lab/1/linux/fs/char_dev.o b/linux-0.11-lab/1/linux/fs/char_dev.o new file mode 100644 index 0000000000000000000000000000000000000000..2977060a7c0b215e10aa16a8395ed973d52837cd GIT binary patch literal 8288 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 O%Ys)0UlIH-!T$wZ8WjQn literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/fs/exec.c b/linux-0.11-lab/1/linux/fs/exec.c new file mode 100755 index 0000000..c3fcb61 --- /dev/null +++ b/linux-0.11-lab/1/linux/fs/exec.c @@ -0,0 +1,542 @@ +/* + * linux/fs/exec.c + * + * (C) 1991 Linus Torvalds + */ + +/* + * #!-checking implemented by tytso. + */ + +/* + * Demand-loading implemented 01.12.91 - no need to read anything but + * the header into memory. The inode of the executable is put into + * "current->executable", and page faults do the actual loading. Clean. + * + * Once more I can proudly say that linux stood up to being changed: it + * was less than 2 hours work to get demand-loading completely implemented. + */ + +#include +#include +#include +#include + +#include +#include +#include +#include +#include + +extern int sys_exit(int exit_code); +extern int sys_close(int fd); + +/* + * MAX_ARG_PAGES defines the number of pages allocated for arguments + * and envelope for the new program. 32 should suffice, this gives + * a maximum env+arg of 128kB ! + */ +#define MAX_ARG_PAGES 32 + + +int sys_uselib() +{ + return -ENOSYS; +} + +/* + * create_tables() parses the env- and arg-strings in new user + * memory and creates the pointer tables from them, and puts their + * addresses on the "stack", returning the new stack pointer value. + */ +static unsigned long * create_tables(char * p,int argc,int envc) +{ + unsigned long *argv,*envp; + unsigned long * sp; + + sp = (unsigned long *) (0xfffffffc & (unsigned long) p); + sp -= envc+1; + envp = sp; + sp -= argc+1; + argv = sp; + put_fs_long((unsigned long)envp,--sp); + put_fs_long((unsigned long)argv,--sp); + put_fs_long((unsigned long)argc,--sp); + while (argc-->0) { + put_fs_long((unsigned long) p,argv++); + while (get_fs_byte(p++)) /* nothing */ ; + } + put_fs_long(0,argv); + while (envc-->0) { + put_fs_long((unsigned long) p,envp++); + while (get_fs_byte(p++)) /* nothing */ ; + } + put_fs_long(0,envp); + return sp; +} + +/* + * count() counts the number of arguments/envelopes + */ +static int count(char ** argv) +{ + int i=0; + char ** tmp; + + if (tmp = argv) + while (get_fs_long((unsigned long *) (tmp++))) + i++; + + return i; +} + +/* + * 'copy_string()' copies argument/envelope strings from user + * memory to free pages in kernel mem. These are in a format ready + * to be put directly into the top of new user memory. + * + * Modified by TYT, 11/24/91 to add the from_kmem argument, which specifies + * whether the string and the string array are from user or kernel segments: + * + * from_kmem argv * argv ** + * 0 user space user space + * 1 kernel space user space + * 2 kernel space kernel space + * + * We do this by playing games with the fs segment register. Since it + * it is expensive to load a segment register, we try to avoid calling + * set_fs() unless we absolutely have to. + */ +static unsigned long copy_strings(int argc,char ** argv,unsigned long *page, + unsigned long p, int from_kmem) +{ + char *tmp, *pag; + int len, offset = 0; + unsigned long old_fs, new_fs; + + if (!p) + return 0; /* bullet-proofing */ + new_fs = get_ds(); + old_fs = get_fs(); + if (from_kmem==2) + set_fs(new_fs); + while (argc-- > 0) { + if (from_kmem == 1) + set_fs(new_fs); + if (!(tmp = (char *)get_fs_long(((unsigned long *)argv)+argc))) + panic("argc is wrong"); + if (from_kmem == 1) + set_fs(old_fs); + len=0; /* remember zero-padding */ + do { + len++; + } while (get_fs_byte(tmp++)); + if (p-len < 0) { /* this shouldn't happen - 128kB */ + set_fs(old_fs); + return 0; + } + while (len) { + --p; --tmp; --len; + if (--offset < 0) { + offset = p % PAGE_SIZE; + if (from_kmem==2) + set_fs(old_fs); + if (!(pag = (char *) page[p/PAGE_SIZE]) && + !(pag = (char *) (page[p/PAGE_SIZE] = + (unsigned long *) get_free_page()))) + return 0; + if (from_kmem==2) + set_fs(new_fs); + + } + *(pag + offset) = get_fs_byte(tmp); + } + } + if (from_kmem==2) + set_fs(old_fs); + return p; +} + +static unsigned long change_ldt(unsigned long text_size,unsigned long * page) +{ + unsigned long code_limit,data_limit,code_base,data_base; + int i; + + code_limit = text_size+PAGE_SIZE -1; + code_limit &= 0xFFFFF000; + data_limit = 0x4000000; + code_base = get_base(current->ldt[1]); + data_base = code_base; + set_base(current->ldt[1],code_base); + set_limit(current->ldt[1],code_limit); + set_base(current->ldt[2],data_base); + set_limit(current->ldt[2],data_limit); +/* make sure fs points to the NEW data segment */ + __asm__("pushl $0x17\n\tpop %%fs"::); + data_base += data_limit; + for (i=MAX_ARG_PAGES-1 ; i>=0 ; i--) { + data_base -= PAGE_SIZE; + if (page[i]) + put_page(page[i],data_base); + } + return data_limit; +} + +/* + * 'do_execve()' executes a new program. + */ +int do_execve(unsigned long * eip,long tmp,char * filename, + char ** argv, char ** envp) +{ + struct m_inode * inode; + struct buffer_head * bh; + struct exec ex; + unsigned long page[MAX_ARG_PAGES]; + int i,argc,envc; + int e_uid, e_gid; + int retval; + int sh_bang = 0; + unsigned long p=PAGE_SIZE*MAX_ARG_PAGES-4; + + if ((0xffff & eip[1]) != 0x000f) + panic("execve called from supervisor mode"); + for (i=0 ; ii_mode)) { /* must be regular file */ + retval = -EACCES; + goto exec_error2; + } + i = inode->i_mode; + e_uid = (i & S_ISUID) ? inode->i_uid : current->euid; + e_gid = (i & S_ISGID) ? inode->i_gid : current->egid; + if (current->euid == inode->i_uid) + i >>= 6; + else if (current->egid == inode->i_gid) + i >>= 3; + if (!(i & 1) && + !((inode->i_mode & 0111) && suser())) { + retval = -ENOEXEC; + goto exec_error2; + } + if (!(bh = bread(inode->i_dev,inode->i_zone[0]))) { + retval = -EACCES; + goto exec_error2; + } + ex = *((struct exec *) bh->b_data); /* read exec-header */ + if ((bh->b_data[0] == '#') && (bh->b_data[1] == '!') && (!sh_bang)) { + /* + * This section does the #! interpretation. + * Sorta complicated, but hopefully it will work. -TYT + */ + + char buf[1023], *cp, *interp, *i_name, *i_arg; + unsigned long old_fs; + + strncpy(buf, bh->b_data+2, 1022); + brelse(bh); + iput(inode); + buf[1022] = '\0'; + if (cp = strchr(buf, '\n')) { + *cp = '\0'; + for (cp = buf; (*cp == ' ') || (*cp == '\t'); cp++); + } + if (!cp || *cp == '\0') { + retval = -ENOEXEC; /* No interpreter name found */ + goto exec_error1; + } + interp = i_name = cp; + i_arg = 0; + for ( ; *cp && (*cp != ' ') && (*cp != '\t'); cp++) { + if (*cp == '/') + i_name = cp+1; + } + if (*cp) { + *cp++ = '\0'; + i_arg = cp; + } + /* + * OK, we've parsed out the interpreter name and + * (optional) argument. + */ + if (sh_bang++ == 0) { + p = copy_strings(envc, envp, page, p, 0); + p = copy_strings(--argc, argv+1, page, p, 0); + } + /* + * Splice in (1) the interpreter's name for argv[0] + * (2) (optional) argument to interpreter + * (3) filename of shell script + * + * This is done in reverse order, because of how the + * user environment and arguments are stored. + */ + p = copy_strings(1, &filename, page, p, 1); + argc++; + if (i_arg) { + p = copy_strings(1, &i_arg, page, p, 2); + argc++; + } + p = copy_strings(1, &i_name, page, p, 2); + argc++; + if (!p) { + retval = -ENOMEM; + goto exec_error1; + } + /* + * OK, now restart the process with the interpreter's inode. + */ + old_fs = get_fs(); + set_fs(get_ds()); + if (!(inode=namei(interp))) { /* get executables inode */ + set_fs(old_fs); + retval = -ENOENT; + goto exec_error1; + } + set_fs(old_fs); + goto restart_interp; + } + brelse(bh); + if (N_MAGIC(ex) != ZMAGIC || ex.a_trsize || ex.a_drsize || + ex.a_text+ex.a_data+ex.a_bss>0x3000000 || + inode->i_size < ex.a_text+ex.a_data+ex.a_syms+N_TXTOFF(ex)) { + retval = -ENOEXEC; + goto exec_error2; + } + if (N_TXTOFF(ex) != BLOCK_SIZE) { + printk("%s: N_TXTOFF != BLOCK_SIZE. See a.out.h.", filename); + retval = -ENOEXEC; + goto exec_error2; + } + if (!sh_bang) { + p = copy_strings(envc,envp,page,p,0); + p = copy_strings(argc,argv,page,p,0); + if (!p) { + retval = -ENOMEM; + goto exec_error2; + } + } +/* OK, This is the point of no return */ + if (current->executable) + iput(current->executable); + current->executable = inode; + for (i=0 ; i<32 ; i++) + current->sigaction[i].sa_handler = NULL; + for (i=0 ; iclose_on_exec>>i)&1) + sys_close(i); + current->close_on_exec = 0; + free_page_tables(get_base(current->ldt[1]),get_limit(0x0f)); + free_page_tables(get_base(current->ldt[2]),get_limit(0x17)); + if (last_task_used_math == current) + last_task_used_math = NULL; + current->used_math = 0; + p += change_ldt(ex.a_text,page)-MAX_ARG_PAGES*PAGE_SIZE; + p = (unsigned long) create_tables((char *)p,argc,envc); + current->brk = ex.a_bss + + (current->end_data = ex.a_data + + (current->end_code = ex.a_text)); + current->start_stack = p & 0xfffff000; + current->euid = e_uid; + current->egid = e_gid; + i = ex.a_text+ex.a_data; + while (i&0xfff) + put_fs_byte(0,(char *) (i++)); + eip[0] = ex.a_entry; /* eip, magic happens :-) */ + eip[3] = p; /* stack pointer */ + return 0; +exec_error2: + iput(inode); +exec_error1: + for (i=0 ; ii_mode)) { /* must be regular file */ + retval = -EACCES; + goto exec_error2; + } + i = inode->i_mode; + e_uid = (i & S_ISUID) ? inode->i_uid : current->euid; + e_gid = (i & S_ISGID) ? inode->i_gid : current->egid; + if (current->euid == inode->i_uid) + i >>= 6; + else if (current->egid == inode->i_gid) + i >>= 3; + if (!(i & 1) && + !((inode->i_mode & 0111) && suser())) { + retval = -ENOEXEC; + goto exec_error2; + } + if (!(bh = bread(inode->i_dev,inode->i_zone[0]))) { + retval = -EACCES; + goto exec_error2; + } + ex = *((struct exec *) bh->b_data); /* read exec-header */ + if ((bh->b_data[0] == '#') && (bh->b_data[1] == '!') && (!sh_bang)) { + /* + * This section does the #! interpretation. + * Sorta complicated, but hopefully it will work. -TYT + */ + + char buf[1023], *cp, *interp, *i_name, *i_arg; + unsigned long old_fs; + + strncpy(buf, bh->b_data+2, 1022); + brelse(bh); + iput(inode); + buf[1022] = '\0'; + if (cp = strchr(buf, '\n')) { + *cp = '\0'; + for (cp = buf; (*cp == ' ') || (*cp == '\t'); cp++); + } + if (!cp || *cp == '\0') { + retval = -ENOEXEC; /* No interpreter name found */ + goto exec_error1; + } + interp = i_name = cp; + i_arg = 0; + for ( ; *cp && (*cp != ' ') && (*cp != '\t'); cp++) { + if (*cp == '/') + i_name = cp+1; + } + if (*cp) { + *cp++ = '\0'; + i_arg = cp; + } + /* + * OK, we've parsed out the interpreter name and + * (optional) argument. + */ + if (sh_bang++ == 0) { + p = copy_strings(envc, envp, page, p, 0); + p = copy_strings(--argc, argv+1, page, p, 0); + } + /* + * Splice in (1) the interpreter's name for argv[0] + * (2) (optional) argument to interpreter + * (3) filename of shell script + * + * This is done in reverse order, because of how the + * user environment and arguments are stored. + */ + p = copy_strings(1, &filename, page, p, 1); + argc++; + if (i_arg) { + p = copy_strings(1, &i_arg, page, p, 2); + argc++; + } + p = copy_strings(1, &i_name, page, p, 2); + argc++; + if (!p) { + retval = -ENOMEM; + goto exec_error1; + } + /* + * OK, now restart the process with the interpreter's inode. + */ + old_fs = get_fs(); + set_fs(get_ds()); + if (!(inode=namei(interp))) { /* get executables inode */ + set_fs(old_fs); + retval = -ENOENT; + goto exec_error1; + } + set_fs(old_fs); + goto restart_interp; + } + brelse(bh); + if (N_MAGIC(ex) != ZMAGIC || ex.a_trsize || ex.a_drsize || + ex.a_text+ex.a_data+ex.a_bss>0x3000000 || + inode->i_size < ex.a_text+ex.a_data+ex.a_syms+N_TXTOFF(ex)) { + retval = -ENOEXEC; + goto exec_error2; + } + if (N_TXTOFF(ex) != BLOCK_SIZE) { + printk("%s: N_TXTOFF != BLOCK_SIZE. See a.out.h.", filename); + retval = -ENOEXEC; + goto exec_error2; + } + if (!sh_bang) { + p = copy_strings(envc,envp,page,p,0); + p = copy_strings(argc,argv,page,p,0); + if (!p) { + retval = -ENOMEM; + goto exec_error2; + } + } +/* OK, This is the point of no return */ + if (current->executable) + iput(current->executable); + current->executable = inode; + for (i=0 ; i<32 ; i++) + current->sigaction[i].sa_handler = NULL; + for (i=0 ; iclose_on_exec>>i)&1) + sys_close(i); + current->close_on_exec = 0; + free_page_tables(get_base(current->ldt[1]),get_limit(0x0f)); + free_page_tables(get_base(current->ldt[2]),get_limit(0x17)); + if (last_task_used_math == current) + last_task_used_math = NULL; + current->used_math = 0; + p += change_ldt(ex.a_text,page)-MAX_ARG_PAGES*PAGE_SIZE; + p = (unsigned long) create_tables((char *)p,argc,envc); + current->brk = ex.a_bss + + (current->end_data = ex.a_data + + (current->end_code = ex.a_text)); + current->start_stack = p & 0xfffff000; + current->euid = e_uid; + current->egid = e_gid; + /* printk("current->brk=%x, current->start_code=%x\n",current->brk,current->start_code); */ + /* by lzh */ + for (tmp1 = 0; tmp1 <= ((current->brk - 1) & 0xfffff000); tmp1 += 4096) + do_no_page_my(5, tmp1 + current->start_code); + /* by lzh */ + i = ex.a_text+ex.a_data; + while (i&0xfff) + put_fs_byte(0,(char *) (i++)); + eip[0] = ex.a_entry; /* eip, magic happens :-) */ + eip[3] = p; /* stack pointer */ + return 0; +exec_error2: + iput(inode); +exec_error1: + for (i=0 ; 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 OTEW?ZcMCov_`d+eDo{EA literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/fs/fcntl.c b/linux-0.11-lab/1/linux/fs/fcntl.c new file mode 100644 index 0000000..c201aa8 --- /dev/null +++ b/linux-0.11-lab/1/linux/fs/fcntl.c @@ -0,0 +1,75 @@ +/* + * linux/fs/fcntl.c + * + * (C) 1991 Linus Torvalds + */ + +#include +#include +#include +#include +#include + +#include +#include + +extern int sys_close(int fd); + +static int dupfd(unsigned int fd, unsigned int arg) +{ + if (fd >= NR_OPEN || !current->filp[fd]) + return -EBADF; + if (arg >= NR_OPEN) + return -EINVAL; + while (arg < NR_OPEN) + if (current->filp[arg]) + arg++; + else + break; + if (arg >= NR_OPEN) + return -EMFILE; + current->close_on_exec &= ~(1<filp[arg] = current->filp[fd])->f_count++; + return arg; +} + +int sys_dup2(unsigned int oldfd, unsigned int newfd) +{ + sys_close(newfd); + return dupfd(oldfd,newfd); +} + +int sys_dup(unsigned int fildes) +{ + return dupfd(fildes,0); +} + +int sys_fcntl(unsigned int fd, unsigned int cmd, unsigned long arg) +{ + struct file * filp; + + if (fd >= NR_OPEN || !(filp = current->filp[fd])) + return -EBADF; + switch (cmd) { + case F_DUPFD: + return dupfd(fd,arg); + case F_GETFD: + return (current->close_on_exec>>fd)&1; + case F_SETFD: + if (arg&1) + current->close_on_exec |= (1<close_on_exec &= ~(1<f_flags; + case F_SETFL: + filp->f_flags &= ~(O_APPEND | O_NONBLOCK); + filp->f_flags |= arg & (O_APPEND | O_NONBLOCK); + return 0; + case F_GETLK: case F_SETLK: case F_SETLKW: + return -1; + default: + return -1; + } +} diff --git a/linux-0.11-lab/1/linux/fs/fcntl.o b/linux-0.11-lab/1/linux/fs/fcntl.o new file mode 100644 index 0000000000000000000000000000000000000000..17a6ecacd50cb07b4337da65f94d880d02b367a8 GIT binary patch literal 6748 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 literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/fs/file_dev.c b/linux-0.11-lab/1/linux/fs/file_dev.c new file mode 100644 index 0000000..0c50eaa --- /dev/null +++ b/linux-0.11-lab/1/linux/fs/file_dev.c @@ -0,0 +1,90 @@ +/* + * linux/fs/file_dev.c + * + * (C) 1991 Linus Torvalds + */ + +#include +#include + +#include +#include +#include + +#define MIN(a,b) (((a)<(b))?(a):(b)) +#define MAX(a,b) (((a)>(b))?(a):(b)) + +int file_read(struct m_inode * inode, struct file * filp, char * buf, int count) +{ + int left,chars,nr; + struct buffer_head * bh; + + if ((left=count)<=0) + return 0; + while (left) { + if (nr = bmap(inode,(filp->f_pos)/BLOCK_SIZE)) { + if (!(bh=bread(inode->i_dev,nr))) + break; + } else + bh = NULL; + nr = filp->f_pos % BLOCK_SIZE; + chars = MIN( BLOCK_SIZE-nr , left ); + filp->f_pos += chars; + left -= chars; + if (bh) { + char * p = nr + bh->b_data; + while (chars-->0) + put_fs_byte(*(p++),buf++); + brelse(bh); + } else { + while (chars-->0) + put_fs_byte(0,buf++); + } + } + inode->i_atime = CURRENT_TIME; + return (count-left)?(count-left):-ERROR; +} + +int file_write(struct m_inode * inode, struct file * filp, char * buf, int count) +{ + off_t pos; + int block,c; + struct buffer_head * bh; + char * p; + int i=0; + +/* + * ok, append may not work when many processes are writing at the same time + * but so what. That way leads to madness anyway. + */ + if (filp->f_flags & O_APPEND) + pos = inode->i_size; + else + pos = filp->f_pos; + while (ii_dev,block))) + break; + c = pos % BLOCK_SIZE; + p = c + bh->b_data; + bh->b_dirt = 1; + c = BLOCK_SIZE-c; + if (c > count-i) c = count-i; + pos += c; + if (pos > inode->i_size) { + inode->i_size = pos; + inode->i_dirt = 1; + } + i += c; + while (c-->0) + *(p++) = get_fs_byte(buf++); + brelse(bh); + } + inode->i_mtime = CURRENT_TIME; + if (!(filp->f_flags & O_APPEND)) { + filp->f_pos = pos; + inode->i_ctime = CURRENT_TIME; + } + return (i?i:-1); +} diff --git a/linux-0.11-lab/1/linux/fs/file_dev.o b/linux-0.11-lab/1/linux/fs/file_dev.o new file mode 100644 index 0000000000000000000000000000000000000000..e1ba8a5aa9f848cbe07cc40a116357db631d2c89 GIT binary patch literal 7828 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 SclH@D3RwcTDjZc + +struct file file_table[NR_FILE]; diff --git a/linux-0.11-lab/1/linux/fs/file_table.o b/linux-0.11-lab/1/linux/fs/file_table.o new file mode 100644 index 0000000000000000000000000000000000000000..422bcb331f1423abef699440aa5b0f0ff3a8b671 GIT binary patch literal 2644 zcma)8ONbmr7_OR`-P!Hgo!w=9BnF`a8xkecvzttkb&W;|x+aF`!4(DLY)?=3Ogq!v zV?VOl_&SK&K#0s-B=xPW^?j%FhrbeTlMCJwT9?XVawWCSbyVX|l2jSv>;r0{YaW6k_^T zz^c43M3{C3LO#m~p?wD-+vFv!O1}9tWJUXp+$5jUK4*OA9`G6MD!D~It9?Y?9e~%h zNpi;q*R@lSvd7#dtx0>I{E+r8?Jnm!to=&<9J!$#WXynkS-U~|kmDcG>f|2zQB7xz zPu|k*q&*-%ra=ffB0sKOX3X>CC&cs`U|z-_!=_!MBjE%>dy4!bc}e?}e2cuIh2)nQ zKBe73zWo5~GpHxaSY_e9qLcMJC2H@1m#062oG8PB_yu{OzE~^Q_tocb$KXq%R=Xc6 z!W5mtG`ERzeXVwH?aU$)7onWoi!GZ&EG<G-(`FDL5GCjLkzBG)c>s!O5Yd43kpIj0J zL$ni?^gGLma)}S#8gV?s>Amp;_i=x>NJiF;9-MAS< z4d33%KD)7OtgJMKW~aHF8JbRnjKu9i4g+f-0>^2`Q2fM$^wI?~uoxN5N}`rr)!X zkOgp0bB?ivVFjLNqo#(BEj4ghvMo+e;Qti+cm>cWRebh7?!!!*IMC1w&2`!#>Rb)&9ZYkHg8gkiQ-5obM!ho&zcta4TOYQ7!kK zhn{n~t|E>PMc#7XSs04*p2N$^c{neB7xH;8faf`&;yT9LBvCE*xzNe^-E4CxbDRBJaN~jlSq|VjswDS1$X0~#=Lq&ga zCz+rAOpXJ}=@*Vw_-pAt>oj4i1@Xtt-Oowk-9QNMj)Y*HB&K4`iTsa2WPK#+q${0w zg!W?!)3XcxL8Yf>6#9nJ`D4X+Q{jsW-%$9r!fOgYRQQR)FBEb=InIv?e^L0SLLMmk uXB6&HxTJ7d;Yo#$D11WUrb18Qw!+sGzNPRTh3_l;TH*IZ6fvzQ&gs8hV_9GT literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/fs/fs.o b/linux-0.11-lab/1/linux/fs/fs.o new file mode 100644 index 0000000000000000000000000000000000000000..1aaa26b2b36db561de70122ad269128a00b937d3 GIT binary patch literal 149888 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 z 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 z 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 literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/fs/inode.c b/linux-0.11-lab/1/linux/fs/inode.c new file mode 100644 index 0000000..9bb10b3 --- /dev/null +++ b/linux-0.11-lab/1/linux/fs/inode.c @@ -0,0 +1,340 @@ +/* + * linux/fs/inode.c + * + * (C) 1991 Linus Torvalds + */ + +#include +#include + +#include +#include +#include +#include + +struct m_inode inode_table[NR_INODE]={{0,},}; + +static void read_inode(struct m_inode * inode); +static void write_inode(struct m_inode * inode); + +static inline void wait_on_inode(struct m_inode * inode) +{ + cli(); + while (inode->i_lock) + sleep_on(&inode->i_wait); + sti(); +} + +static inline void lock_inode(struct m_inode * inode) +{ + cli(); + while (inode->i_lock) + sleep_on(&inode->i_wait); + inode->i_lock=1; + sti(); +} + +static inline void unlock_inode(struct m_inode * inode) +{ + inode->i_lock=0; + wake_up(&inode->i_wait); +} + +void invalidate_inodes(int dev) +{ + int i; + struct m_inode * inode; + + inode = 0+inode_table; + for(i=0 ; ii_dev == dev) { + if (inode->i_count) + printk("inode in use on removed disk\n\r"); + inode->i_dev = inode->i_dirt = 0; + } + } +} + +void sync_inodes(void) +{ + int i; + struct m_inode * inode; + + inode = 0+inode_table; + for(i=0 ; ii_dirt && !inode->i_pipe) + write_inode(inode); + } +} + +static int _bmap(struct m_inode * inode,int block,int create) +{ + struct buffer_head * bh; + int i; + + if (block<0) + panic("_bmap: block<0"); + if (block >= 7+512+512*512) + panic("_bmap: block>big"); + if (block<7) { + if (create && !inode->i_zone[block]) + if (inode->i_zone[block]=new_block(inode->i_dev)) { + inode->i_ctime=CURRENT_TIME; + inode->i_dirt=1; + } + return inode->i_zone[block]; + } + block -= 7; + if (block<512) { + if (create && !inode->i_zone[7]) + if (inode->i_zone[7]=new_block(inode->i_dev)) { + inode->i_dirt=1; + inode->i_ctime=CURRENT_TIME; + } + if (!inode->i_zone[7]) + return 0; + if (!(bh = bread(inode->i_dev,inode->i_zone[7]))) + return 0; + i = ((unsigned short *) (bh->b_data))[block]; + if (create && !i) + if (i=new_block(inode->i_dev)) { + ((unsigned short *) (bh->b_data))[block]=i; + bh->b_dirt=1; + } + brelse(bh); + return i; + } + block -= 512; + if (create && !inode->i_zone[8]) + if (inode->i_zone[8]=new_block(inode->i_dev)) { + inode->i_dirt=1; + inode->i_ctime=CURRENT_TIME; + } + if (!inode->i_zone[8]) + return 0; + if (!(bh=bread(inode->i_dev,inode->i_zone[8]))) + return 0; + i = ((unsigned short *)bh->b_data)[block>>9]; + if (create && !i) + if (i=new_block(inode->i_dev)) { + ((unsigned short *) (bh->b_data))[block>>9]=i; + bh->b_dirt=1; + } + brelse(bh); + if (!i) + return 0; + if (!(bh=bread(inode->i_dev,i))) + return 0; + i = ((unsigned short *)bh->b_data)[block&511]; + if (create && !i) + if (i=new_block(inode->i_dev)) { + ((unsigned short *) (bh->b_data))[block&511]=i; + bh->b_dirt=1; + } + brelse(bh); + return i; +} + +int bmap(struct m_inode * inode,int block) +{ + return _bmap(inode,block,0); +} + +int create_block(struct m_inode * inode, int block) +{ + return _bmap(inode,block,1); +} + +void iput(struct m_inode * inode) +{ + if (!inode) + return; + wait_on_inode(inode); + if (!inode->i_count) + panic("iput: trying to free free inode"); + if (inode->i_pipe) { + wake_up(&inode->i_wait); + if (--inode->i_count) + return; + free_page(inode->i_size); + inode->i_count=0; + inode->i_dirt=0; + inode->i_pipe=0; + return; + } + if (!inode->i_dev) { + inode->i_count--; + return; + } + if (S_ISBLK(inode->i_mode)) { + sync_dev(inode->i_zone[0]); + wait_on_inode(inode); + } +repeat: + if (inode->i_count>1) { + inode->i_count--; + return; + } + if (!inode->i_nlinks) { + truncate(inode); + free_inode(inode); + return; + } + if (inode->i_dirt) { + write_inode(inode); /* we can sleep - so do again */ + wait_on_inode(inode); + goto repeat; + } + inode->i_count--; + return; +} + +struct m_inode * get_empty_inode(void) +{ + struct m_inode * inode; + static struct m_inode * last_inode = inode_table; + int i; + + do { + inode = NULL; + for (i = NR_INODE; i ; i--) { + if (++last_inode >= inode_table + NR_INODE) + last_inode = inode_table; + if (!last_inode->i_count) { + inode = last_inode; + if (!inode->i_dirt && !inode->i_lock) + break; + } + } + if (!inode) { + for (i=0 ; ii_dirt) { + write_inode(inode); + wait_on_inode(inode); + } + } while (inode->i_count); + memset(inode,0,sizeof(*inode)); + inode->i_count = 1; + return inode; +} + +struct m_inode * get_pipe_inode(void) +{ + struct m_inode * inode; + + if (!(inode = get_empty_inode())) + return NULL; + if (!(inode->i_size=get_free_page())) { + inode->i_count = 0; + return NULL; + } + inode->i_count = 2; /* sum of readers/writers */ + PIPE_HEAD(*inode) = PIPE_TAIL(*inode) = 0; + inode->i_pipe = 1; + return inode; +} + +struct m_inode * iget(int dev,int nr) +{ + struct m_inode * inode, * empty; + + if (!dev) + panic("iget with dev==0"); + empty = get_empty_inode(); + inode = inode_table; + while (inode < NR_INODE+inode_table) { + if (inode->i_dev != dev || inode->i_num != nr) { + inode++; + continue; + } + wait_on_inode(inode); + if (inode->i_dev != dev || inode->i_num != nr) { + inode = inode_table; + continue; + } + inode->i_count++; + if (inode->i_mount) { + int i; + + for (i = 0 ; i= NR_SUPER) { + printk("Mounted inode hasn't got sb\n"); + if (empty) + iput(empty); + return inode; + } + iput(inode); + dev = super_block[i].s_dev; + nr = ROOT_INO; + inode = inode_table; + continue; + } + if (empty) + iput(empty); + return inode; + } + if (!empty) + return (NULL); + inode=empty; + inode->i_dev = dev; + inode->i_num = nr; + read_inode(inode); + return inode; +} + +static void read_inode(struct m_inode * inode) +{ + struct super_block * sb; + struct buffer_head * bh; + int block; + + lock_inode(inode); + if (!(sb=get_super(inode->i_dev))) + panic("trying to read inode without dev"); + block = 2 + sb->s_imap_blocks + sb->s_zmap_blocks + + (inode->i_num-1)/INODES_PER_BLOCK; + if (!(bh=bread(inode->i_dev,block))) + panic("unable to read i-node block"); + __asm__ volatile ("cld"); /* by wyj */ + *(struct d_inode *)inode = + ((struct d_inode *)bh->b_data) + [(inode->i_num-1)%INODES_PER_BLOCK]; + brelse(bh); + unlock_inode(inode); +} + +static void write_inode(struct m_inode * inode) +{ + struct super_block * sb; + struct buffer_head * bh; + int block; + + lock_inode(inode); + if (!inode->i_dirt || !inode->i_dev) { + unlock_inode(inode); + return; + } + if (!(sb=get_super(inode->i_dev))) + panic("trying to write inode without device"); + block = 2 + sb->s_imap_blocks + sb->s_zmap_blocks + + (inode->i_num-1)/INODES_PER_BLOCK; + if (!(bh=bread(inode->i_dev,block))) + panic("unable to read i-node block"); + __asm__ volatile ("cld"); /* by wyj */ + ((struct d_inode *)bh->b_data) + [(inode->i_num-1)%INODES_PER_BLOCK] = + *(struct d_inode *)inode; + bh->b_dirt=1; + inode->i_dirt=0; + brelse(bh); + unlock_inode(inode); +} diff --git a/linux-0.11-lab/1/linux/fs/inode.o b/linux-0.11-lab/1/linux/fs/inode.o new file mode 100644 index 0000000000000000000000000000000000000000..dd67bfa4d43e1073c47e0226043fc43f5f0e9153 GIT binary patch literal 14072 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 I1a}MmH>)TywEzGB literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/fs/ioctl.c b/linux-0.11-lab/1/linux/fs/ioctl.c new file mode 100644 index 0000000..36fc976 --- /dev/null +++ b/linux-0.11-lab/1/linux/fs/ioctl.c @@ -0,0 +1,46 @@ +/* + * linux/fs/ioctl.c + * + * (C) 1991 Linus Torvalds + */ + +#include +#include +#include + +#include + +extern int tty_ioctl(int dev, int cmd, int arg); + +typedef int (*ioctl_ptr)(int dev,int cmd,int arg); + +#define NRDEVS ((sizeof (ioctl_table))/(sizeof (ioctl_ptr))) + +static ioctl_ptr ioctl_table[]={ + NULL, /* nodev */ + NULL, /* /dev/mem */ + NULL, /* /dev/fd */ + NULL, /* /dev/hd */ + tty_ioctl, /* /dev/ttyx */ + tty_ioctl, /* /dev/tty */ + NULL, /* /dev/lp */ + NULL}; /* named pipes */ + + +int sys_ioctl(unsigned int fd, unsigned int cmd, unsigned long arg) +{ + struct file * filp; + int dev,mode; + + if (fd >= NR_OPEN || !(filp = current->filp[fd])) + return -EBADF; + mode=filp->f_inode->i_mode; + if (!S_ISCHR(mode) && !S_ISBLK(mode)) + return -EINVAL; + dev = filp->f_inode->i_zone[0]; + if (MAJOR(dev) >= NRDEVS) + return -ENODEV; + if (!ioctl_table[MAJOR(dev)]) + return -ENOTTY; + return ioctl_table[MAJOR(dev)](dev,cmd,arg); +} diff --git a/linux-0.11-lab/1/linux/fs/ioctl.o b/linux-0.11-lab/1/linux/fs/ioctl.o new file mode 100644 index 0000000000000000000000000000000000000000..1f1f33c5568ad7f154251149e1ecc40766da48c1 GIT binary patch literal 5828 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 +#include +#include + +#include +#include +#include +#include +#include + +#define ACC_MODE(x) ("\004\002\006\377"[(x)&O_ACCMODE]) + +/* + * comment out this line if you want names > NAME_LEN chars to be + * truncated. Else they will be disallowed. + */ +/* #define NO_TRUNCATE */ + +#define MAY_EXEC 1 +#define MAY_WRITE 2 +#define MAY_READ 4 + +/* + * permission() + * + * is used to check for read/write/execute permissions on a file. + * I don't know if we should look at just the euid or both euid and + * uid, but that should be easily changed. + */ +static int permission(struct m_inode * inode,int mask) +{ + int mode = inode->i_mode; + +/* special case: not even root can read/write a deleted file */ + if (inode->i_dev && !inode->i_nlinks) + return 0; + else if (current->euid==inode->i_uid) + mode >>= 6; + else if (current->egid==inode->i_gid) + mode >>= 3; + if (((mode & mask & 0007) == mask) || suser()) + return 1; + return 0; +} + +/* + * ok, we cannot use strncmp, as the name is not in our data space. + * Thus we'll have to use match. No big problem. Match also makes + * some sanity tests. + * + * NOTE! unlike strncmp, match returns 1 for success, 0 for failure. + */ +static int match(int len,const char * name,struct dir_entry * de) +{ + register int same __asm__("ax"); + + if (!de || !de->inode || len > NAME_LEN) + return 0; + if (len < NAME_LEN && de->name[len]) + return 0; + __asm__("cld\n\t" + "fs ; repe ; cmpsb\n\t" + "setz %%al" + :"=a" (same) + :"0" (0),"S" ((long) name),"D" ((long) de->name),"c" (len) + ); + return same; +} + +static int match_kernel(int len,const char * name,struct dir_entry * de) +{ + register int same __asm__("ax"); + + if (!de || !de->inode || len > NAME_LEN) + return 0; + if (len < NAME_LEN && de->name[len]) + return 0; + __asm__("cld\n\t" + "ds ; repe ; cmpsb\n\t" + "setz %%al" + :"=a" (same) + :"0" (0),"S" ((long) name),"D" ((long) de->name),"c" (len) + ); + return same; +} + +/* + * find_entry() + * + * finds an entry in the specified directory with the wanted name. It + * returns the cache buffer in which the entry was found, and the entry + * itself (as a parameter - res_dir). It does NOT read the inode of the + * entry - you'll have to do that yourself if you want to. + * + * This also takes care of the few special cases due to '..'-traversal + * over a pseudo-root and a mount point. + */ +static struct buffer_head * find_entry(struct m_inode ** dir, + const char * name, int namelen, struct dir_entry ** res_dir) +{ + int entries; + int block,i; + struct buffer_head * bh; + struct dir_entry * de; + struct super_block * sb; + +#ifdef NO_TRUNCATE + if (namelen > NAME_LEN) + return NULL; +#else + if (namelen > NAME_LEN) + namelen = NAME_LEN; +#endif + entries = (*dir)->i_size / (sizeof (struct dir_entry)); + *res_dir = NULL; + if (!namelen) + return NULL; +/* check for '..', as we might have to do some "magic" for it */ + if (namelen==2 && get_fs_byte(name)=='.' && get_fs_byte(name+1)=='.') { +/* '..' in a pseudo-root results in a faked '.' (just change namelen) */ + if ((*dir) == current->root) + namelen=1; + else if ((*dir)->i_num == ROOT_INO) { +/* '..' over a mount-point results in 'dir' being exchanged for the mounted + directory-inode. NOTE! We set mounted, so that we can iput the new dir */ + sb=get_super((*dir)->i_dev); + if (sb->s_imount) { + iput(*dir); + (*dir)=sb->s_imount; + (*dir)->i_count++; + } + } + } + if (!(block = (*dir)->i_zone[0])) + return NULL; + if (!(bh = bread((*dir)->i_dev,block))) + return NULL; + i = 0; + de = (struct dir_entry *) bh->b_data; + while (i < entries) { + if ((char *)de >= BLOCK_SIZE+bh->b_data) { + brelse(bh); + bh = NULL; + if (!(block = bmap(*dir,i/DIR_ENTRIES_PER_BLOCK)) || + !(bh = bread((*dir)->i_dev,block))) { + i += DIR_ENTRIES_PER_BLOCK; + continue; + } + de = (struct dir_entry *) bh->b_data; + } + if (match(namelen,name,de)) { + *res_dir = de; + return bh; + } + de++; + i++; + } + brelse(bh); + return NULL; +} + +struct buffer_head * find_entry_kernel(struct m_inode ** dir, + const char * name, int namelen, struct dir_entry ** res_dir) +{ + int entries; + int block,i; + struct buffer_head * bh; + struct dir_entry * de; + struct super_block * sb; + +#ifdef NO_TRUNCATE + if (namelen > NAME_LEN) + return NULL; +#else + if (namelen > NAME_LEN) + namelen = NAME_LEN; +#endif + entries = (*dir)->i_size / (sizeof (struct dir_entry)); + *res_dir = NULL; + if (!namelen) + return NULL; +/* check for '..', as we might have to do some "magic" for it */ + if (namelen==2 && *name=='.' && *(name+1)=='.') { +/* '..' in a pseudo-root results in a faked '.' (just change namelen) */ + if ((*dir) == current->root) + namelen=1; + else if ((*dir)->i_num == ROOT_INO) { +/* '..' over a mount-point results in 'dir' being exchanged for the mounted + directory-inode. NOTE! We set mounted, so that we can iput the new dir */ + sb=get_super((*dir)->i_dev); + if (sb->s_imount) { + iput(*dir); + (*dir)=sb->s_imount; + (*dir)->i_count++; + } + } + } + if (!(block = (*dir)->i_zone[0])) + return NULL; + if (!(bh = bread((*dir)->i_dev,block))) + return NULL; + i = 0; + de = (struct dir_entry *) bh->b_data; + while (i < entries) { + if ((char *)de >= BLOCK_SIZE+bh->b_data) { + brelse(bh); + bh = NULL; + if (!(block = bmap(*dir,i/DIR_ENTRIES_PER_BLOCK)) || + !(bh = bread((*dir)->i_dev,block))) { + i += DIR_ENTRIES_PER_BLOCK; + continue; + } + de = (struct dir_entry *) bh->b_data; + } + if (match_kernel(namelen,name,de)) { + *res_dir = de; + return bh; + } + de++; + i++; + } + brelse(bh); + return NULL; +} + +/* + * add_entry() + * + * adds a file entry to the specified directory, using the same + * semantics as find_entry(). It returns NULL if it failed. + * + * NOTE!! The inode part of 'de' is left at 0 - which means you + * may not sleep between calling this and putting something into + * the entry, as someone else might have used it while you slept. + */ +static struct buffer_head * add_entry(struct m_inode * dir, + const char * name, int namelen, struct dir_entry ** res_dir) +{ + int block,i; + struct buffer_head * bh; + struct dir_entry * de; + + *res_dir = NULL; +#ifdef NO_TRUNCATE + if (namelen > NAME_LEN) + return NULL; +#else + if (namelen > NAME_LEN) + namelen = NAME_LEN; +#endif + if (!namelen) + return NULL; + if (!(block = dir->i_zone[0])) + return NULL; + if (!(bh = bread(dir->i_dev,block))) + return NULL; + i = 0; + de = (struct dir_entry *) bh->b_data; + while (1) { + if ((char *)de >= BLOCK_SIZE+bh->b_data) { + brelse(bh); + bh = NULL; + block = create_block(dir,i/DIR_ENTRIES_PER_BLOCK); + if (!block) + return NULL; + if (!(bh = bread(dir->i_dev,block))) { + i += DIR_ENTRIES_PER_BLOCK; + continue; + } + de = (struct dir_entry *) bh->b_data; + } + if (i*sizeof(struct dir_entry) >= dir->i_size) { + de->inode=0; + dir->i_size = (i+1)*sizeof(struct dir_entry); + dir->i_dirt = 1; + dir->i_ctime = CURRENT_TIME; + } + if (!de->inode) { + dir->i_mtime = CURRENT_TIME; + for (i=0; i < NAME_LEN ; i++) + de->name[i]=(ib_dirt = 1; + *res_dir = de; + return bh; + } + de++; + i++; + } + brelse(bh); + return NULL; +} + +/* + * get_dir() + * + * Getdir traverses the pathname until it hits the topmost directory. + * It returns NULL on failure. + */ +static struct m_inode * get_dir(const char * pathname) +{ + char c; + const char * thisname; + struct m_inode * inode; + struct buffer_head * bh; + int namelen,inr,idev; + struct dir_entry * de; + + if (!current->root || !current->root->i_count) + panic("No root inode"); + if (!current->pwd || !current->pwd->i_count) + panic("No cwd inode"); + if ((c=get_fs_byte(pathname))=='/') { + inode = current->root; + pathname++; + } else if (c) + inode = current->pwd; + else + return NULL; /* empty name is bad */ + inode->i_count++; + while (1) { + thisname = pathname; + if (!S_ISDIR(inode->i_mode) || !permission(inode,MAY_EXEC)) { + iput(inode); + return NULL; + } + for(namelen=0;(c=get_fs_byte(pathname++))&&(c!='/');namelen++) + /* nothing */ ; + if (!c) + return inode; + if (!(bh = find_entry(&inode,thisname,namelen,&de))) { + iput(inode); + return NULL; + } + inr = de->inode; + idev = inode->i_dev; + brelse(bh); + iput(inode); + if (!(inode = iget(idev,inr))) + return NULL; + } +} + +struct m_inode * get_dir_kernel(const char * pathname) +{ + char c; + const char * thisname; + struct m_inode * inode; + struct buffer_head * bh; + int namelen,inr,idev; + struct dir_entry * de; + + if (!current->root || !current->root->i_count) + panic("No root inode"); + if (!current->pwd || !current->pwd->i_count) + panic("No cwd inode"); + if ((c=*pathname)=='/') { + inode = current->root; + pathname++; + } else if (c) + inode = current->pwd; + else + return NULL; /* empty name is bad */ + inode->i_count++; + while (1) { + thisname = pathname; + if (!S_ISDIR(inode->i_mode) || !permission(inode,MAY_EXEC)) { + iput(inode); + return NULL; + } + for(namelen=0;(c=*(pathname++))&&(c!='/');namelen++) + /* nothing */ ; + if (!c) + return inode; + if (!(bh = find_entry_kernel(&inode,thisname,namelen,&de))) { + iput(inode); + return NULL; + } + inr = de->inode; + idev = inode->i_dev; + brelse(bh); + iput(inode); + if (!(inode = iget(idev,inr))) + return NULL; + } +} + +/* + * dir_namei() + * + * dir_namei() returns the inode of the directory of the + * specified name, and the name within that directory. + */ +static struct m_inode * dir_namei(const char * pathname, + int * namelen, const char ** name) +{ + char c; + const char * basename; + struct m_inode * dir; + + if (!(dir = get_dir(pathname))) + return NULL; + basename = pathname; + while (c=get_fs_byte(pathname++)) + if (c=='/') + basename=pathname; + *namelen = pathname-basename-1; + *name = basename; + return dir; +} + +/* + * namei() + * + * is used by most simple commands to get the inode of a specified name. + * Open, link etc use their own routines, but this is enough for things + * like 'chmod' etc. + */ +struct m_inode * namei(const char * pathname) +{ + const char * basename; + int inr,dev,namelen; + struct m_inode * dir; + struct buffer_head * bh; + struct dir_entry * de; + + if (!(dir = dir_namei(pathname,&namelen,&basename))) + return NULL; + if (!namelen) /* special case: '/usr/' etc */ + return dir; + bh = find_entry(&dir,basename,namelen,&de); + if (!bh) { + iput(dir); + return NULL; + } + inr = de->inode; + dev = dir->i_dev; + brelse(bh); + iput(dir); + dir=iget(dev,inr); + if (dir) { + dir->i_atime=CURRENT_TIME; + dir->i_dirt=1; + } + return dir; +} + +/* + * open_namei() + * + * namei for open - this is in fact almost the whole open-routine. + */ +int open_namei(const char * pathname, int flag, int mode, + struct m_inode ** res_inode) +{ + const char * basename; + int inr,dev,namelen; + struct m_inode * dir, *inode; + struct buffer_head * bh; + struct dir_entry * de; + + if ((flag & O_TRUNC) && !(flag & O_ACCMODE)) + flag |= O_WRONLY; + mode &= 0777 & ~current->umask; + mode |= I_REGULAR; + if (!(dir = dir_namei(pathname,&namelen,&basename))) + return -ENOENT; + if (!namelen) { /* special case: '/usr/' etc */ + if (!(flag & (O_ACCMODE|O_CREAT|O_TRUNC))) { + *res_inode=dir; + return 0; + } + iput(dir); + return -EISDIR; + } + bh = find_entry(&dir,basename,namelen,&de); + if (!bh) { + if (!(flag & O_CREAT)) { + iput(dir); + return -ENOENT; + } + if (!permission(dir,MAY_WRITE)) { + iput(dir); + return -EACCES; + } + inode = new_inode(dir->i_dev); + if (!inode) { + iput(dir); + return -ENOSPC; + } + inode->i_uid = current->euid; + inode->i_mode = mode; + inode->i_dirt = 1; + bh = add_entry(dir,basename,namelen,&de); + if (!bh) { + inode->i_nlinks--; + iput(inode); + iput(dir); + return -ENOSPC; + } + de->inode = inode->i_num; + bh->b_dirt = 1; + brelse(bh); + iput(dir); + *res_inode = inode; + return 0; + } + inr = de->inode; + dev = dir->i_dev; + brelse(bh); + iput(dir); + if (flag & O_EXCL) + return -EEXIST; + if (!(inode=iget(dev,inr))) + return -EACCES; + if ((S_ISDIR(inode->i_mode) && (flag & O_ACCMODE)) || + !permission(inode,ACC_MODE(flag))) { + iput(inode); + return -EPERM; + } + inode->i_atime = CURRENT_TIME; + if (flag & O_TRUNC) + truncate(inode); + *res_inode = inode; + return 0; +} + +int sys_mknod(const char * filename, int mode, int dev) +{ + const char * basename; + int namelen; + struct m_inode * dir, * inode; + struct buffer_head * bh; + struct dir_entry * de; + + if (!suser()) + return -EPERM; + if (!(dir = dir_namei(filename,&namelen,&basename))) + return -ENOENT; + if (!namelen) { + iput(dir); + return -ENOENT; + } + if (!permission(dir,MAY_WRITE)) { + iput(dir); + return -EPERM; + } + bh = find_entry(&dir,basename,namelen,&de); + if (bh) { + brelse(bh); + iput(dir); + return -EEXIST; + } + inode = new_inode(dir->i_dev); + if (!inode) { + iput(dir); + return -ENOSPC; + } + inode->i_mode = mode; + if (S_ISBLK(mode) || S_ISCHR(mode)) + inode->i_zone[0] = dev; + inode->i_mtime = inode->i_atime = CURRENT_TIME; + inode->i_dirt = 1; + bh = add_entry(dir,basename,namelen,&de); + if (!bh) { + iput(dir); + inode->i_nlinks=0; + iput(inode); + return -ENOSPC; + } + de->inode = inode->i_num; + bh->b_dirt = 1; + iput(dir); + iput(inode); + brelse(bh); + return 0; +} + +int sys_mkdir(const char * pathname, int mode) +{ + const char * basename; + int namelen; + struct m_inode * dir, * inode; + struct buffer_head * bh, *dir_block; + struct dir_entry * de; + + if (!suser()) + return -EPERM; + if (!(dir = dir_namei(pathname,&namelen,&basename))) + return -ENOENT; + if (!namelen) { + iput(dir); + return -ENOENT; + } + if (!permission(dir,MAY_WRITE)) { + iput(dir); + return -EPERM; + } + bh = find_entry(&dir,basename,namelen,&de); + if (bh) { + brelse(bh); + iput(dir); + return -EEXIST; + } + inode = new_inode(dir->i_dev); + if (!inode) { + iput(dir); + return -ENOSPC; + } + inode->i_size = 32; + inode->i_dirt = 1; + inode->i_mtime = inode->i_atime = CURRENT_TIME; + if (!(inode->i_zone[0]=new_block(inode->i_dev))) { + iput(dir); + inode->i_nlinks--; + iput(inode); + return -ENOSPC; + } + inode->i_dirt = 1; + if (!(dir_block=bread(inode->i_dev,inode->i_zone[0]))) { + iput(dir); + free_block(inode->i_dev,inode->i_zone[0]); + inode->i_nlinks--; + iput(inode); + return -ERROR; + } + de = (struct dir_entry *) dir_block->b_data; + de->inode=inode->i_num; + strcpy(de->name,"."); + de++; + de->inode = dir->i_num; + strcpy(de->name,".."); + inode->i_nlinks = 2; + dir_block->b_dirt = 1; + brelse(dir_block); + inode->i_mode = I_DIRECTORY | (mode & 0777 & ~current->umask); + inode->i_dirt = 1; + bh = add_entry(dir,basename,namelen,&de); + if (!bh) { + iput(dir); + free_block(inode->i_dev,inode->i_zone[0]); + inode->i_nlinks=0; + iput(inode); + return -ENOSPC; + } + de->inode = inode->i_num; + bh->b_dirt = 1; + dir->i_nlinks++; + dir->i_dirt = 1; + iput(dir); + iput(inode); + brelse(bh); + return 0; +} + +/* + * routine to check that the specified directory is empty (for rmdir) + */ +static int empty_dir(struct m_inode * inode) +{ + int nr,block; + int len; + struct buffer_head * bh; + struct dir_entry * de; + + len = inode->i_size / sizeof (struct dir_entry); + if (len<2 || !inode->i_zone[0] || + !(bh=bread(inode->i_dev,inode->i_zone[0]))) { + printk("warning - bad directory on dev %04x\n",inode->i_dev); + return 0; + } + de = (struct dir_entry *) bh->b_data; + if (de[0].inode != inode->i_num || !de[1].inode || + strcmp(".",de[0].name) || strcmp("..",de[1].name)) { + printk("warning - bad directory on dev %04x\n",inode->i_dev); + return 0; + } + nr = 2; + de += 2; + while (nr= (void *) (bh->b_data+BLOCK_SIZE)) { + brelse(bh); + block=bmap(inode,nr/DIR_ENTRIES_PER_BLOCK); + if (!block) { + nr += DIR_ENTRIES_PER_BLOCK; + continue; + } + if (!(bh=bread(inode->i_dev,block))) + return 0; + de = (struct dir_entry *) bh->b_data; + } + if (de->inode) { + brelse(bh); + return 0; + } + de++; + nr++; + } + brelse(bh); + return 1; +} + +int sys_rmdir(const char * name) +{ + const char * basename; + int namelen; + struct m_inode * dir, * inode; + struct buffer_head * bh; + struct dir_entry * de; + + if (!suser()) + return -EPERM; + if (!(dir = dir_namei(name,&namelen,&basename))) + return -ENOENT; + if (!namelen) { + iput(dir); + return -ENOENT; + } + if (!permission(dir,MAY_WRITE)) { + iput(dir); + return -EPERM; + } + bh = find_entry(&dir,basename,namelen,&de); + if (!bh) { + iput(dir); + return -ENOENT; + } + if (!(inode = iget(dir->i_dev, de->inode))) { + iput(dir); + brelse(bh); + return -EPERM; + } + if ((dir->i_mode & S_ISVTX) && current->euid && + inode->i_uid != current->euid) { + iput(dir); + iput(inode); + brelse(bh); + return -EPERM; + } + if (inode->i_dev != dir->i_dev || inode->i_count>1) { + iput(dir); + iput(inode); + brelse(bh); + return -EPERM; + } + if (inode == dir) { /* we may not delete ".", but "../dir" is ok */ + iput(inode); + iput(dir); + brelse(bh); + return -EPERM; + } + if (!S_ISDIR(inode->i_mode)) { + iput(inode); + iput(dir); + brelse(bh); + return -ENOTDIR; + } + if (!empty_dir(inode)) { + iput(inode); + iput(dir); + brelse(bh); + return -ENOTEMPTY; + } + if (inode->i_nlinks != 2) + printk("empty directory has nlink!=2 (%d)",inode->i_nlinks); + de->inode = 0; + bh->b_dirt = 1; + brelse(bh); + inode->i_nlinks=0; + inode->i_dirt=1; + dir->i_nlinks--; + dir->i_ctime = dir->i_mtime = CURRENT_TIME; + dir->i_dirt=1; + iput(dir); + iput(inode); + return 0; +} + +int sys_unlink(const char * name) +{ + const char * basename; + int namelen; + struct m_inode * dir, * inode; + struct buffer_head * bh; + struct dir_entry * de; + + if (!(dir = dir_namei(name,&namelen,&basename))) + return -ENOENT; + if (!namelen) { + iput(dir); + return -ENOENT; + } + if (!permission(dir,MAY_WRITE)) { + iput(dir); + return -EPERM; + } + bh = find_entry(&dir,basename,namelen,&de); + if (!bh) { + iput(dir); + return -ENOENT; + } + if (!(inode = iget(dir->i_dev, de->inode))) { + iput(dir); + brelse(bh); + return -ENOENT; + } + if ((dir->i_mode & S_ISVTX) && !suser() && + current->euid != inode->i_uid && + current->euid != dir->i_uid) { + iput(dir); + iput(inode); + brelse(bh); + return -EPERM; + } + if (S_ISDIR(inode->i_mode)) { + iput(inode); + iput(dir); + brelse(bh); + return -EPERM; + } + if (!inode->i_nlinks) { + printk("Deleting nonexistent file (%04x:%d), %d\n", + inode->i_dev,inode->i_num,inode->i_nlinks); + inode->i_nlinks=1; + } + de->inode = 0; + bh->b_dirt = 1; + brelse(bh); + inode->i_nlinks--; + inode->i_dirt = 1; + inode->i_ctime = CURRENT_TIME; + iput(inode); + iput(dir); + return 0; +} + +int sys_symlink() +{ + return -ENOSYS; +} + +int sys_link(const char * oldname, const char * newname) +{ + struct dir_entry * de; + struct m_inode * oldinode, * dir; + struct buffer_head * bh; + const char * basename; + int namelen; + + oldinode=namei(oldname); + if (!oldinode) + return -ENOENT; + if (S_ISDIR(oldinode->i_mode)) { + iput(oldinode); + return -EPERM; + } + dir = dir_namei(newname,&namelen,&basename); + if (!dir) { + iput(oldinode); + return -EACCES; + } + if (!namelen) { + iput(oldinode); + iput(dir); + return -EPERM; + } + if (dir->i_dev != oldinode->i_dev) { + iput(dir); + iput(oldinode); + return -EXDEV; + } + if (!permission(dir,MAY_WRITE)) { + iput(dir); + iput(oldinode); + return -EACCES; + } + bh = find_entry(&dir,basename,namelen,&de); + if (bh) { + brelse(bh); + iput(dir); + iput(oldinode); + return -EEXIST; + } + bh = add_entry(dir,basename,namelen,&de); + if (!bh) { + iput(dir); + iput(oldinode); + return -ENOSPC; + } + de->inode = oldinode->i_num; + bh->b_dirt = 1; + brelse(bh); + iput(dir); + oldinode->i_nlinks++; + oldinode->i_ctime = CURRENT_TIME; + oldinode->i_dirt = 1; + iput(oldinode); + return 0; +} diff --git a/linux-0.11-lab/1/linux/fs/namei.o b/linux-0.11-lab/1/linux/fs/namei.o new file mode 100644 index 0000000000000000000000000000000000000000..f8c588fb448750a73390e7cd4c30dfb03dd1aacb GIT binary patch literal 23120 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 literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/fs/open.c b/linux-0.11-lab/1/linux/fs/open.c new file mode 100644 index 0000000..3695ff1 --- /dev/null +++ b/linux-0.11-lab/1/linux/fs/open.c @@ -0,0 +1,208 @@ +/* + * linux/fs/open.c + * + * (C) 1991 Linus Torvalds + */ + +#include +#include +#include +#include +#include +#include + +#include +#include +#include +#include + +int sys_ustat(int dev, struct ustat * ubuf) +{ + return -ENOSYS; +} + +int sys_utime(char * filename, struct utimbuf * times) +{ + struct m_inode * inode; + long actime,modtime; + + if (!(inode=namei(filename))) + return -ENOENT; + if (times) { + actime = get_fs_long((unsigned long *) ×->actime); + modtime = get_fs_long((unsigned long *) ×->modtime); + } else + actime = modtime = CURRENT_TIME; + inode->i_atime = actime; + inode->i_mtime = modtime; + inode->i_dirt = 1; + iput(inode); + return 0; +} + +/* + * XXX should we use the real or effective uid? BSD uses the real uid, + * so as to make this call useful to setuid programs. + */ +int sys_access(const char * filename,int mode) +{ + struct m_inode * inode; + int res, i_mode; + + mode &= 0007; + if (!(inode=namei(filename))) + return -EACCES; + i_mode = res = inode->i_mode & 0777; + iput(inode); + if (current->uid == inode->i_uid) + res >>= 6; + else if (current->gid == inode->i_gid) + res >>= 6; + if ((res & 0007 & mode) == mode) + return 0; + /* + * XXX we are doing this test last because we really should be + * swapping the effective with the real user id (temporarily), + * and then calling suser() routine. If we do call the + * suser() routine, it needs to be called last. + */ + if ((!current->uid) && + (!(mode & 1) || (i_mode & 0111))) + return 0; + return -EACCES; +} + +int sys_chdir(const char * filename) +{ + struct m_inode * inode; + + if (!(inode = namei(filename))) + return -ENOENT; + if (!S_ISDIR(inode->i_mode)) { + iput(inode); + return -ENOTDIR; + } + iput(current->pwd); + current->pwd = inode; + return (0); +} + +int sys_chroot(const char * filename) +{ + struct m_inode * inode; + + if (!(inode=namei(filename))) + return -ENOENT; + if (!S_ISDIR(inode->i_mode)) { + iput(inode); + return -ENOTDIR; + } + iput(current->root); + current->root = inode; + return (0); +} + +int sys_chmod(const char * filename,int mode) +{ + struct m_inode * inode; + + if (!(inode=namei(filename))) + return -ENOENT; + if ((current->euid != inode->i_uid) && !suser()) { + iput(inode); + return -EACCES; + } + inode->i_mode = (mode & 07777) | (inode->i_mode & ~07777); + inode->i_dirt = 1; + iput(inode); + return 0; +} + +int sys_chown(const char * filename,int uid,int gid) +{ + struct m_inode * inode; + + if (!(inode=namei(filename))) + return -ENOENT; + if (!suser()) { + iput(inode); + return -EACCES; + } + inode->i_uid=uid; + inode->i_gid=gid; + inode->i_dirt=1; + iput(inode); + return 0; +} + +int sys_open(const char * filename,int flag,int mode) +{ + struct m_inode * inode; + struct file * f; + int i,fd; + + mode &= 0777 & ~current->umask; + for(fd=0 ; fdfilp[fd]) + break; + if (fd>=NR_OPEN) + return -EINVAL; + current->close_on_exec &= ~(1<f_count) break; + if (i>=NR_FILE) + return -EINVAL; + (current->filp[fd]=f)->f_count++; + if ((i=open_namei(filename,flag,mode,&inode))<0) { + current->filp[fd]=NULL; + f->f_count=0; + return i; + } +/* ttys are somewhat special (ttyxx major==4, tty major==5) */ + if (S_ISCHR(inode->i_mode)) + if (MAJOR(inode->i_zone[0])==4) { + if (current->leader && current->tty<0) { + current->tty = MINOR(inode->i_zone[0]); + tty_table[current->tty].pgrp = current->pgrp; + } + } else if (MAJOR(inode->i_zone[0])==5) + if (current->tty<0) { + iput(inode); + current->filp[fd]=NULL; + f->f_count=0; + return -EPERM; + } +/* Likewise with block-devices: check for floppy_change */ + if (S_ISBLK(inode->i_mode)) + check_disk_change(inode->i_zone[0]); + f->f_mode = inode->i_mode; + f->f_flags = flag; + f->f_count = 1; + f->f_inode = inode; + f->f_pos = 0; + return (fd); +} + +int sys_creat(const char * pathname, int mode) +{ + return sys_open(pathname, O_CREAT | O_TRUNC, mode); +} + +int sys_close(unsigned int fd) +{ + struct file * filp; + + if (fd >= NR_OPEN) + return -EINVAL; + current->close_on_exec &= ~(1<filp[fd])) + return -EINVAL; + current->filp[fd] = NULL; + if (filp->f_count == 0) + panic("Close: file count is 0"); + if (--filp->f_count) + return (0); + iput(filp->f_inode); + return (0); +} diff --git a/linux-0.11-lab/1/linux/fs/open.o b/linux-0.11-lab/1/linux/fs/open.o new file mode 100644 index 0000000000000000000000000000000000000000..8e10b183467ce7ababb747e4cc131181f532ce35 GIT binary patch literal 11192 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 literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/fs/pipe.c b/linux-0.11-lab/1/linux/fs/pipe.c new file mode 100644 index 0000000..dfc4480 --- /dev/null +++ b/linux-0.11-lab/1/linux/fs/pipe.c @@ -0,0 +1,111 @@ +/* + * linux/fs/pipe.c + * + * (C) 1991 Linus Torvalds + */ + +#include + +#include +#include /* for get_free_page */ +#include + +int read_pipe(struct m_inode * inode, char * buf, int count) +{ + int chars, size, read = 0; + + while (count>0) { + while (!(size=PIPE_SIZE(*inode))) { + wake_up(&inode->i_wait); + if (inode->i_count != 2) /* are there any writers? */ + return read; + sleep_on(&inode->i_wait); + } + chars = PAGE_SIZE-PIPE_TAIL(*inode); + if (chars > count) + chars = count; + if (chars > size) + chars = size; + count -= chars; + read += chars; + size = PIPE_TAIL(*inode); + PIPE_TAIL(*inode) += chars; + PIPE_TAIL(*inode) &= (PAGE_SIZE-1); + while (chars-->0) + put_fs_byte(((char *)inode->i_size)[size++],buf++); + } + wake_up(&inode->i_wait); + return read; +} + +int write_pipe(struct m_inode * inode, char * buf, int count) +{ + int chars, size, written = 0; + + while (count>0) { + while (!(size=(PAGE_SIZE-1)-PIPE_SIZE(*inode))) { + wake_up(&inode->i_wait); + if (inode->i_count != 2) { /* no readers */ + current->signal |= (1<<(SIGPIPE-1)); + return written?written:-1; + } + sleep_on(&inode->i_wait); + } + chars = PAGE_SIZE-PIPE_HEAD(*inode); + if (chars > count) + chars = count; + if (chars > size) + chars = size; + count -= chars; + written += chars; + size = PIPE_HEAD(*inode); + PIPE_HEAD(*inode) += chars; + PIPE_HEAD(*inode) &= (PAGE_SIZE-1); + while (chars-->0) + ((char *)inode->i_size)[size++]=get_fs_byte(buf++); + } + wake_up(&inode->i_wait); + return written; +} + +int sys_pipe(unsigned long * fildes) +{ + struct m_inode * inode; + struct file * f[2]; + int fd[2]; + int i,j; + + j=0; + for(i=0;j<2 && if_count++; + if (j==1) + f[0]->f_count=0; + if (j<2) + return -1; + j=0; + for(i=0;j<2 && ifilp[i]) { + current->filp[ fd[j]=i ] = f[j]; + j++; + } + if (j==1) + current->filp[fd[0]]=NULL; + if (j<2) { + f[0]->f_count=f[1]->f_count=0; + return -1; + } + if (!(inode=get_pipe_inode())) { + current->filp[fd[0]] = + current->filp[fd[1]] = NULL; + f[0]->f_count = f[1]->f_count = 0; + return -1; + } + f[0]->f_inode = f[1]->f_inode = inode; + f[0]->f_pos = f[1]->f_pos = 0; + f[0]->f_mode = 1; /* read */ + f[1]->f_mode = 2; /* write */ + put_fs_long(fd[0],0+fildes); + put_fs_long(fd[1],1+fildes); + return 0; +} diff --git a/linux-0.11-lab/1/linux/fs/pipe.o b/linux-0.11-lab/1/linux/fs/pipe.o new file mode 100644 index 0000000000000000000000000000000000000000..d5b5db26c38f6881a408d3b6291aeb9d28c67659 GIT binary patch literal 8104 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 Jg} +#include +#include + +#include +#include +#include + +extern int rw_char(int rw,int dev, char * buf, int count, off_t * pos); +extern int read_pipe(struct m_inode * inode, char * buf, int count); +extern int write_pipe(struct m_inode * inode, char * buf, int count); +extern int block_read(int dev, off_t * pos, char * buf, int count); +extern int block_write(int dev, off_t * pos, char * buf, int count); +extern int file_read(struct m_inode * inode, struct file * filp, + char * buf, int count); +extern int file_write(struct m_inode * inode, struct file * filp, + char * buf, int count); + +int sys_lseek(unsigned int fd,off_t offset, int origin) +{ + struct file * file; + int tmp; + + if (fd >= NR_OPEN || !(file=current->filp[fd]) || !(file->f_inode) + || !IS_SEEKABLE(MAJOR(file->f_inode->i_dev))) + return -EBADF; + if (file->f_inode->i_pipe) + return -ESPIPE; + switch (origin) { + case 0: + if (offset<0) return -EINVAL; + file->f_pos=offset; + break; + case 1: + if (file->f_pos+offset<0) return -EINVAL; + file->f_pos += offset; + break; + case 2: + if ((tmp=file->f_inode->i_size+offset) < 0) + return -EINVAL; + file->f_pos = tmp; + break; + default: + return -EINVAL; + } + return file->f_pos; +} + +int sys_read(unsigned int fd,char * buf,int count) +{ + struct file * file; + struct m_inode * inode; + + if (fd>=NR_OPEN || count<0 || !(file=current->filp[fd])) + return -EINVAL; + if (!count) + return 0; + verify_area(buf,count); + inode = file->f_inode; + if (inode->i_pipe) + return (file->f_mode&1)?read_pipe(inode,buf,count):-EIO; + if (S_ISCHR(inode->i_mode)) + return rw_char(READ,inode->i_zone[0],buf,count,&file->f_pos); + if (S_ISBLK(inode->i_mode)) + return block_read(inode->i_zone[0],&file->f_pos,buf,count); + if (S_ISDIR(inode->i_mode) || S_ISREG(inode->i_mode)) { + if (count+file->f_pos > inode->i_size) + count = inode->i_size - file->f_pos; + if (count<=0) + return 0; + return file_read(inode,file,buf,count); + } + printk("(Read)inode->i_mode=%06o\n\r",inode->i_mode); + return -EINVAL; +} + +int sys_write(unsigned int fd,char * buf,int count) +{ + struct file * file; + struct m_inode * inode; + + if (fd>=NR_OPEN || count <0 || !(file=current->filp[fd])) + return -EINVAL; + if (!count) + return 0; + inode=file->f_inode; + if (inode->i_pipe) + return (file->f_mode&2)?write_pipe(inode,buf,count):-EIO; + if (S_ISCHR(inode->i_mode)) + return rw_char(WRITE,inode->i_zone[0],buf,count,&file->f_pos); + if (S_ISBLK(inode->i_mode)) + return block_write(inode->i_zone[0],&file->f_pos,buf,count); + if (S_ISREG(inode->i_mode)) + return file_write(inode,file,buf,count); + printk("(Write)inode->i_mode=%06o\n\r",inode->i_mode); + return -EINVAL; +} diff --git a/linux-0.11-lab/1/linux/fs/read_write.o b/linux-0.11-lab/1/linux/fs/read_write.o new file mode 100644 index 0000000000000000000000000000000000000000..998aad95c9e243e4bfcae9647b34d9235f717844 GIT binary patch literal 7520 zcmbVQYiu0Xb-wf1;mmSLQCvzEBRN?cD{Ezw%cVq1v`kvGMN5?Yh^&V#Id)e2nB}gu zukOx@q+v9+7!{=nR}lg_n!NhJNvN*AKtHNnh1&}46z~!@%^Y@GbSM+Hi&+) z_;%mobMb-b+=o9$?eekszzdgui_HAQ(sVq6%82lGEQ2mj+2<~K+Z0`%8Y+DCs$GC; zV2x_=J>yLH^>=UFxN+@EjO6>iI5qb1OJ4Z(A5i~kU%zGXJdej%Du+ZXEIWMdE6BC9h62MA z*FFygV$Ps-_G5ajP3=Mn;$%Hxqn(z}dF12FaS1v7nUqezq2$`NXa9Tx3EU5_B zL$CjYX`J?3NG#KDtN2$TCPhq$*1Zh&l1x{kusqd^+NERhKFsb6Fan$gvIpkZ%{V(N zJ9h0yU~pX(?-b(gl<{Vm{vh7}iuG{ZTvFY;_QjjTnG(X=ur~Pf2%cx~W!c#o?aC5o zF|j;l-gEiPMoHx)B4Ls3mzS=f%QG^`AM27yzCH~b=81h{o|vy84vfA_LB5zxe^jjM z9J8Fe#WyB?t|@!ilpGHtFFl zG?T&>J^VrFd?BWHXB(%L5ZA*9sf2{yT`%Q@agw2j^l+UuQb_6H?=qSc#`N%HTNp>8+rvEJx4)o5!!}`*qrI4X_Fzhoh5X`%-#!?RyM(FD@9{_~zL|4j2;x%w9$JMc&t58@?@;k{*%Ok&w+_nm(x-f>wBUT}Y`5z|l zvkJAEFp}g0;LwkdZ*m?(d?Us1TSSB^E*H5tq9XJNM)WtvPHuhY01d}zA)MbPznk2& zn$46jc9Gl8%hc~Ck3c^vjB)Zl=ZnmvPvfOOI$1JyrID2V74n6o3`2_SOVcbtX1z+$7$fuzf z#y-*+i|LvseHgtI#)G7Xtvu*{(qmQu^Z@AzYZi2d^eId3xr5}VoD`nMA@aP#H>UB> zLFBV2B0s`pbC1f@en><{!TD3E?lQRpBN@0H2(-Fb|3^riHYk?`YIr1RpZPrM`wMyK zx$5)_BKi)}r44df>KDxDH>E@${enHf<*sdJOZtWR4PK=#v@L#}CpJ#PNZU=3q2H0= zLwI$`@Viy`{%orNt0fg4pnTfl@A1Qz2WHvW9_|(WLQ!n|1Byo(J`5F43+*%cApFr) z;g7BgFMZnKkFN^H=1fZEM%|d~h12YwZX1EEo#gGu) z9YG*QH0@xN!Fz5K2csjf@7D7k2pa5;4Px7%5bKlL-a$Xmw!wo@j$&%lryh`& z{h@Zp^i4uUA*v2g92i?AZh)vp!P<>Ci~Fm7+*?*W_YO{=6F38qIQ)<(`Q#(Gu8<$X z9O~jMn5O-tw+B!8iN~2uCPzxuT)CBZN6MvYYhH9HnhVViQHTaERp~iipOQI-EkaHf z1;R9QMOV>6(^q*5b(a+VYL;fJnKC$*6Q)o0)ELyJaNE%=&(af7$?T+MPhR}?Mf-MD z(RwxISM*ygdopETgyKx=k+xqvda-rUo_zIHY4t-qb^9B58Yiri_Cxx;Q9O34*oQ3p zA^U=TvenY>7_b*lu8Hz9W26}9jwrlz6S>RPTDb8wy-dSP(njZDr>XG>lsQy0i-nt2qZbQK9d-2};arHU(B^0_LwP87g;d-OyxjC=aK!2L9dm2!Y<3!}$)RmrfIcCol zrke6DakVbaq-CWDdWXrC|B6De`0AbV3 zI&vghRW21bucG^jE~U|1-O>dyJwbU2k99UU%bvLh*9F@l#|I|sR9rXghZux<(^B%33bI~Q|P$2|hd zI=WPCRRjhAP>qn_(w-a3FZ#M!xarHmwlsj9X z9E{rcG6Zg*9mQzx!l0frx>Af)nPNQ7^hz-V7E4Dl1SY$q7&4 + +int sys_select() +{ + return -ENOSYS; +} + diff --git a/linux-0.11-lab/1/linux/fs/select.o b/linux-0.11-lab/1/linux/fs/select.o new file mode 100644 index 0000000000000000000000000000000000000000..d61f73a39bf58c107d845f3825c695fe69663502 GIT binary patch literal 1776 zcma)7&ubG=5T2J!Yc*|X8^x9irr?h%?k3TorD`oLDvI>~7iJXeveV zCY}@#J&1bs?8UqPfKX4Kdi3hqL;YsoPO~}bz`U9HX5P%3>16x#`kfm}DH2j-P~Rf@ zl+m7QEas>{P2kmV>r<>uh}!akeCds_eOT8?M2Wg)X97y zXXIz{6KZmJ{3ubzqHEJeej#@`cdNkQ($w4KX(HnU<#LNTV+09~f%U6&dCo2MSm&o^ z=r~TL{^ZAS#{HoyMWNGi>XB9FIHI9A%~auDMj@)y@?EFobsJI14^7W`RO+<7ZqF=R zm5SN1Yo)RVO3jdNuC5hVidAdgsuoSx4(hF|?F;i4q1QW&qPbBto4(tQ%w}M_j=AZh zUncKQJrYawEG&Ru~0ZwnU4Z zUPM;Ij%>1OVMtcsbgYI`>u#*Ky`~RWtlPC(;57dvg*F;I@kis zL)RAOsi&aRIIZ<~a{8_RbIu@$_g4DiB@mtO%TCWGy1^hwHd9;uxYGc5+5Qz*MvUa< z9Gq{Nm4w8{zmS6hLcYY~mLMmkQ0ApQ$Ac%gz;MoiD`Am=g*R7#1j7tNTI!1mRP(~3C{b&IOkWGJ +#include + +#include +#include +#include +#include + +static void cp_stat(struct m_inode * inode, struct stat * statbuf) +{ + struct stat tmp; + int i; + + verify_area(statbuf,sizeof (* statbuf)); + tmp.st_dev = inode->i_dev; + tmp.st_ino = inode->i_num; + tmp.st_mode = inode->i_mode; + tmp.st_nlink = inode->i_nlinks; + tmp.st_uid = inode->i_uid; + tmp.st_gid = inode->i_gid; + tmp.st_rdev = inode->i_zone[0]; + tmp.st_size = inode->i_size; + tmp.st_atime = inode->i_atime; + tmp.st_mtime = inode->i_mtime; + tmp.st_ctime = inode->i_ctime; + for (i=0 ; i= NR_OPEN || !(f=current->filp[fd]) || !(inode=f->f_inode)) + return -EBADF; + cp_stat(inode,statbuf); + return 0; +} + +int sys_readlink() +{ + return -ENOSYS; +} diff --git a/linux-0.11-lab/1/linux/fs/stat.o b/linux-0.11-lab/1/linux/fs/stat.o new file mode 100644 index 0000000000000000000000000000000000000000..fdb41d331a01a0b46c2a069b24d4be4631d5abd0 GIT binary patch literal 7212 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 +#include +#include +#include + +#include +#include + +int sync_dev(int dev); +void wait_for_keypress(void); + +/* set_bit uses setb, as gas doesn't recognize setc */ +#define set_bit(bitnr,addr) ({ \ +register int __res __asm__("ax"); \ +__asm__("bt %2,%3;setb %%al":"=a" (__res):"a" (0),"r" (bitnr),"m" (*(addr))); \ +__res; }) + +struct super_block super_block[NR_SUPER]; +/* this is initialized in init/main.c */ +int ROOT_DEV = 0; + +static void lock_super(struct super_block * sb) +{ + cli(); + while (sb->s_lock) + sleep_on(&(sb->s_wait)); + sb->s_lock = 1; + sti(); +} + +static void free_super(struct super_block * sb) +{ + cli(); + sb->s_lock = 0; + wake_up(&(sb->s_wait)); + sti(); +} + +static void wait_on_super(struct super_block * sb) +{ + cli(); + while (sb->s_lock) + sleep_on(&(sb->s_wait)); + sti(); +} + +struct super_block * get_super(int dev) +{ + struct super_block * s; + + if (!dev) + return NULL; + s = 0+super_block; + while (s < NR_SUPER+super_block) + if (s->s_dev == dev) { + wait_on_super(s); + if (s->s_dev == dev) + return s; + s = 0+super_block; + } else + s++; + return NULL; +} + +void put_super(int dev) +{ + struct super_block * sb; +/* struct m_inode * inode; */ + int i; + + if (dev == ROOT_DEV) { + printk("root diskette changed: prepare for armageddon\n\r"); + return; + } + if (!(sb = get_super(dev))) + return; + if (sb->s_imount) { + printk("Mounted disk changed - tssk, tssk\n\r"); + return; + } + lock_super(sb); + sb->s_dev = 0; + for(i=0;is_imap[i]); + for(i=0;is_zmap[i]); + free_super(sb); + return; +} + +static struct super_block * read_super(int dev) +{ + struct super_block * s; + struct buffer_head * bh; + int i,block; + + if (!dev) + return NULL; + check_disk_change(dev); + if (s = get_super(dev)) + return s; + for (s = 0+super_block ;; s++) { + if (s >= NR_SUPER+super_block) + return NULL; + if (!s->s_dev) + break; + } + s->s_dev = dev; + s->s_isup = NULL; + s->s_imount = NULL; + s->s_time = 0; + s->s_rd_only = 0; + s->s_dirt = 0; + lock_super(s); + if (!(bh = bread(dev,1))) { + s->s_dev=0; + free_super(s); + return NULL; + } + __asm__ volatile ("cld"); /* by wyj */ + *((struct d_super_block *) s) = + *((struct d_super_block *) bh->b_data); + brelse(bh); + if (s->s_magic != SUPER_MAGIC) { + s->s_dev = 0; + free_super(s); + return NULL; + } + for (i=0;is_imap[i] = NULL; + for (i=0;is_zmap[i] = NULL; + block=2; + for (i=0 ; i < s->s_imap_blocks ; i++) + if (s->s_imap[i]=bread(dev,block)) + block++; + else + break; + for (i=0 ; i < s->s_zmap_blocks ; i++) + if (s->s_zmap[i]=bread(dev,block)) + block++; + else + break; + if (block != 2+s->s_imap_blocks+s->s_zmap_blocks) { + for(i=0;is_imap[i]); + for(i=0;is_zmap[i]); + s->s_dev=0; + free_super(s); + return NULL; + } + s->s_imap[0]->b_data[0] |= 1; + s->s_zmap[0]->b_data[0] |= 1; + free_super(s); + return s; +} + +int sys_umount(char * dev_name) +{ + struct m_inode * inode; + struct super_block * sb; + int dev; + + if (!(inode=namei(dev_name))) + return -ENOENT; + dev = inode->i_zone[0]; + if (!S_ISBLK(inode->i_mode)) { + iput(inode); + return -ENOTBLK; + } + iput(inode); + if (dev==ROOT_DEV) + return -EBUSY; + if (!(sb=get_super(dev)) || !(sb->s_imount)) + return -ENOENT; + if (!sb->s_imount->i_mount) + printk("Mounted inode has i_mount=0\n"); + for (inode=inode_table+0 ; inodei_dev==dev && inode->i_count) + return -EBUSY; + sb->s_imount->i_mount=0; + iput(sb->s_imount); + sb->s_imount = NULL; + iput(sb->s_isup); + sb->s_isup = NULL; + put_super(dev); + sync_dev(dev); + return 0; +} + +int sys_mount(char * dev_name, char * dir_name, int rw_flag) +{ + struct m_inode * dev_i, * dir_i; + struct super_block * sb; + int dev; + + if (!(dev_i=namei(dev_name))) + return -ENOENT; + dev = dev_i->i_zone[0]; + if (!S_ISBLK(dev_i->i_mode)) { + iput(dev_i); + return -EPERM; + } + iput(dev_i); + if (!(dir_i=namei(dir_name))) + return -ENOENT; + if (dir_i->i_count != 1 || dir_i->i_num == ROOT_INO) { + iput(dir_i); + return -EBUSY; + } + if (!S_ISDIR(dir_i->i_mode)) { + iput(dir_i); + return -EPERM; + } + if (!(sb=read_super(dev))) { + iput(dir_i); + return -EBUSY; + } + if (sb->s_imount) { + iput(dir_i); + return -EBUSY; + } + if (dir_i->i_mount) { + iput(dir_i); + return -EPERM; + } + sb->s_imount=dir_i; + dir_i->i_mount=1; + dir_i->i_dirt=1; /* NOTE! we don't iput(dir_i) */ + return 0; /* we do that in umount */ +} + +void mount_root(void) +{ + int i,free; + struct super_block * p; + struct m_inode * mi; + + if (32 != sizeof (struct d_inode)) + panic("bad i-node size"); + for(i=0;is_dev = 0; + p->s_lock = 0; + p->s_wait = NULL; + } + if (!(p=read_super(ROOT_DEV))) + panic("Unable to mount root"); + if (!(mi=iget(ROOT_DEV,ROOT_INO))) + panic("Unable to read root i-node"); + mi->i_count += 3 ; /* NOTE! it is logically used 4 times, not 1 */ + p->s_isup = p->s_imount = mi; + current->pwd = mi; + current->root = mi; + free=0; + i=p->s_nzones; + while (-- i >= 0) + if (!set_bit(i&8191,p->s_zmap[i>>13]->b_data)) + free++; + printk("%d/%d free blocks\n\r",free,p->s_nzones); + free=0; + i=p->s_ninodes+1; + while (-- i >= 0) + if (!set_bit(i&8191,p->s_imap[i>>13]->b_data)) + free++; + printk("%d/%d free inodes\n\r",free,p->s_ninodes); +} diff --git a/linux-0.11-lab/1/linux/fs/super.o b/linux-0.11-lab/1/linux/fs/super.o new file mode 100644 index 0000000000000000000000000000000000000000..b551798da16bfa699c2dc2848c061720be0e1b2a GIT binary patch literal 12284 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 + +#include + +static void free_ind(int dev,int block) +{ + struct buffer_head * bh; + unsigned short * p; + int i; + + if (!block) + return; + if (bh=bread(dev,block)) { + p = (unsigned short *) bh->b_data; + for (i=0;i<512;i++,p++) + if (*p) + free_block(dev,*p); + brelse(bh); + } + free_block(dev,block); +} + +static void free_dind(int dev,int block) +{ + struct buffer_head * bh; + unsigned short * p; + int i; + + if (!block) + return; + if (bh=bread(dev,block)) { + p = (unsigned short *) bh->b_data; + for (i=0;i<512;i++,p++) + if (*p) + free_ind(dev,*p); + brelse(bh); + } + free_block(dev,block); +} + +void truncate(struct m_inode * inode) +{ + int i; + + if (!(S_ISREG(inode->i_mode) || S_ISDIR(inode->i_mode))) + return; + for (i=0;i<7;i++) + if (inode->i_zone[i]) { + free_block(inode->i_dev,inode->i_zone[i]); + inode->i_zone[i]=0; + } + free_ind(inode->i_dev,inode->i_zone[7]); + free_dind(inode->i_dev,inode->i_zone[8]); + inode->i_zone[7] = inode->i_zone[8] = 0; + inode->i_size = 0; + inode->i_dirt = 1; + inode->i_mtime = inode->i_ctime = CURRENT_TIME; +} + diff --git a/linux-0.11-lab/1/linux/fs/truncate.o b/linux-0.11-lab/1/linux/fs/truncate.o new file mode 100644 index 0000000000000000000000000000000000000000..8975b924958105c719b40601717933b390dce7b0 GIT binary patch literal 6848 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 T&knY~U11EUL+(?^{YLp;_3Udb literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/include/.DS_Store b/linux-0.11-lab/1/linux/include/.DS_Store new file mode 100755 index 0000000000000000000000000000000000000000..2e0018ed8b4f170f1671abea9a375c9429086a99 GIT binary patch literal 6148 zcmeHK%}T>S5Z>*NCWx4WP>*}@)u`@9H&Cbs3vR}f^E@O;4<6fOHi!o+^A{I<&z7QNoU6O+KAaXg!gP)G> z{4n;HV#)D08NhE>W+4k$#Kvs?`@Q>jVK7Q+wGUn>mdb1EhG`n+rg`lS;?zyNWIS@b z;U)G?y=35P`z(&bneF-KK|k$S+edMfctO-3%H*Kehmfm_AnL`b6OW_bNY3M`0l84e zs$|(gvnm>m#-u8;R;yMOd(HjH#55|q^~00y?c-DSJb8Il#B%rprEF=O!W$TKJG^&? zQ5Z)z;GJenBMFHCVt^P}6$bSAXKbv>hH0O~05R}m2Jn0kpoq4{T%kNVpuy`Sj+YQo zz{a-(qR?n-%oV~22v@0qDwXRe23P6e7dpHm_$8dfEf5!4DeFhZ9A|fU0atnhqYFKc0o}vE>}290YjEz fh{aO811bgl0u4Z0W3CW9AaoIsG*Ckf{3-*VQRPuB literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/include/._.DS_Store b/linux-0.11-lab/1/linux/include/._.DS_Store new file mode 100755 index 0000000000000000000000000000000000000000..f6670c35b1929d923cf1bc18462f59d08e62bf56 GIT binary patch literal 4096 zcmZQz6=P>$Vqox1Ojhs@R)|o50+1L3ClDJkFz{^v(m+1nBL)UWIhYCu0iY;W;207T z#31B;1fqkX0;{4?!O;*H4S~@R7!85Z5Eu=C(GVC7fzc2c4S~@R7!85Z5TJ4hFapg3 zVK9&j$;d2LC`v8PFD*(=RY=P(%2vqCD@n~O$;{77%*m-#$Vp8rQAo;3%*zILb)mY3 QG==JaxL0Ht$Vqox1Ojhs@R)|o50+1L3ClDJkFz{^v(m+1nBL)UWIUt(=a103vVi0oQ z1JS_%q!}X6w17+pi3>0=NG0dz>LnHw#H7N@49B$lKq2Lwa)oB`4v3=I4T zb-9VjIY2?)zmF4u6vJodx$GdCnW1ZD$Vqox1Ojhs@R)|o50+1L3ClDJkFz{^v(m+1nBL)UWIUt(=a103vVi0oQ z3(>(a1E^dSO$#HC4;2?p&d=3LEGWoH)hjGbEK1BP$;?Y-Ffgz%vNkhFHA+mfw6qRR zOiL`vv_>;zlsg&%qaiRF0;3@?8UmvsFd71*Aut*OqaiRF0;3@?8Un~60P1XlFc`>% zWMmdA6r~pDmlh?bDx~EXWh-Rnm81f@o%wl*IXRUIIjLzS3Q0MMdD+0eFjUu&rcnJ4 L_lgXI-2eXoiYP05 literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/include/a.out.h b/linux-0.11-lab/1/linux/include/a.out.h new file mode 100755 index 0000000..3e67974 --- /dev/null +++ b/linux-0.11-lab/1/linux/include/a.out.h @@ -0,0 +1,220 @@ +#ifndef _A_OUT_H +#define _A_OUT_H + +#define __GNU_EXEC_MACROS__ + +struct exec { + unsigned long a_magic; /* Use macros N_MAGIC, etc for access */ + unsigned a_text; /* length of text, in bytes */ + unsigned a_data; /* length of data, in bytes */ + unsigned a_bss; /* length of uninitialized data area for file, in bytes */ + unsigned a_syms; /* length of symbol table data in file, in bytes */ + unsigned a_entry; /* start address */ + unsigned a_trsize; /* length of relocation info for text, in bytes */ + unsigned a_drsize; /* length of relocation info for data, in bytes */ +}; + +#ifndef N_MAGIC +#define N_MAGIC(exec) ((exec).a_magic) +#endif + +#ifndef OMAGIC +/* Code indicating object file or impure executable. */ +#define OMAGIC 0407 +/* Code indicating pure executable. */ +#define NMAGIC 0410 +/* Code indicating demand-paged executable. */ +#define ZMAGIC 0413 +#endif /* not OMAGIC */ + +#ifndef N_BADMAG +#define N_BADMAG(x) \ + (N_MAGIC(x) != OMAGIC && N_MAGIC(x) != NMAGIC \ + && N_MAGIC(x) != ZMAGIC) +#endif + +#define _N_BADMAG(x) \ + (N_MAGIC(x) != OMAGIC && N_MAGIC(x) != NMAGIC \ + && N_MAGIC(x) != ZMAGIC) + +#define _N_HDROFF(x) (SEGMENT_SIZE - sizeof (struct exec)) + +#ifndef N_TXTOFF +#define N_TXTOFF(x) \ + (N_MAGIC(x) == ZMAGIC ? _N_HDROFF((x)) + sizeof (struct exec) : sizeof (struct exec)) +#endif + +#ifndef N_DATOFF +#define N_DATOFF(x) (N_TXTOFF(x) + (x).a_text) +#endif + +#ifndef N_TRELOFF +#define N_TRELOFF(x) (N_DATOFF(x) + (x).a_data) +#endif + +#ifndef N_DRELOFF +#define N_DRELOFF(x) (N_TRELOFF(x) + (x).a_trsize) +#endif + +#ifndef N_SYMOFF +#define N_SYMOFF(x) (N_DRELOFF(x) + (x).a_drsize) +#endif + +#ifndef N_STROFF +#define N_STROFF(x) (N_SYMOFF(x) + (x).a_syms) +#endif + +/* Address of text segment in memory after it is loaded. */ +#ifndef N_TXTADDR +#define N_TXTADDR(x) 0 +#endif + +/* Address of data segment in memory after it is loaded. + Note that it is up to you to define SEGMENT_SIZE + on machines not listed here. */ +#if defined(vax) || defined(hp300) || defined(pyr) +#define SEGMENT_SIZE PAGE_SIZE +#endif +#ifdef hp300 +#define PAGE_SIZE 4096 +#endif +#ifdef sony +#define SEGMENT_SIZE 0x2000 +#endif /* Sony. */ +#ifdef is68k +#define SEGMENT_SIZE 0x20000 +#endif +#if defined(m68k) && defined(PORTAR) +#define PAGE_SIZE 0x400 +#define SEGMENT_SIZE PAGE_SIZE +#endif + +#define PAGE_SIZE 4096 +#define SEGMENT_SIZE 1024 + +#define _N_SEGMENT_ROUND(x) (((x) + SEGMENT_SIZE - 1) & ~(SEGMENT_SIZE - 1)) + +#define _N_TXTENDADDR(x) (N_TXTADDR(x)+(x).a_text) + +#ifndef N_DATADDR +#define N_DATADDR(x) \ + (N_MAGIC(x)==OMAGIC? (_N_TXTENDADDR(x)) \ + : (_N_SEGMENT_ROUND (_N_TXTENDADDR(x)))) +#endif + +/* Address of bss segment in memory after it is loaded. */ +#ifndef N_BSSADDR +#define N_BSSADDR(x) (N_DATADDR(x) + (x).a_data) +#endif + +#ifndef N_NLIST_DECLARED +struct nlist { + union { + char *n_name; + struct nlist *n_next; + long n_strx; + } n_un; + unsigned char n_type; + char n_other; + short n_desc; + unsigned long n_value; +}; +#endif + +#ifndef N_UNDF +#define N_UNDF 0 +#endif +#ifndef N_ABS +#define N_ABS 2 +#endif +#ifndef N_TEXT +#define N_TEXT 4 +#endif +#ifndef N_DATA +#define N_DATA 6 +#endif +#ifndef N_BSS +#define N_BSS 8 +#endif +#ifndef N_COMM +#define N_COMM 18 +#endif +#ifndef N_FN +#define N_FN 15 +#endif + +#ifndef N_EXT +#define N_EXT 1 +#endif +#ifndef N_TYPE +#define N_TYPE 036 +#endif +#ifndef N_STAB +#define N_STAB 0340 +#endif + +/* The following type indicates the definition of a symbol as being + an indirect reference to another symbol. The other symbol + appears as an undefined reference, immediately following this symbol. + + Indirection is asymmetrical. The other symbol's value will be used + to satisfy requests for the indirect symbol, but not vice versa. + If the other symbol does not have a definition, libraries will + be searched to find a definition. */ +#define N_INDR 0xa + +/* The following symbols refer to set elements. + All the N_SET[ATDB] symbols with the same name form one set. + Space is allocated for the set in the text section, and each set + element's value is stored into one word of the space. + The first word of the space is the length of the set (number of elements). + + The address of the set is made into an N_SETV symbol + whose name is the same as the name of the set. + This symbol acts like a N_DATA global symbol + in that it can satisfy undefined external references. */ + +/* These appear as input to LD, in a .o file. */ +#define N_SETA 0x14 /* Absolute set element symbol */ +#define N_SETT 0x16 /* Text set element symbol */ +#define N_SETD 0x18 /* Data set element symbol */ +#define N_SETB 0x1A /* Bss set element symbol */ + +/* This is output from LD. */ +#define N_SETV 0x1C /* Pointer to set vector in data area. */ + +#ifndef N_RELOCATION_INFO_DECLARED + +/* This structure describes a single relocation to be performed. + The text-relocation section of the file is a vector of these structures, + all of which apply to the text section. + Likewise, the data-relocation section applies to the data section. */ + +struct relocation_info +{ + /* Address (within segment) to be relocated. */ + int r_address; + /* The meaning of r_symbolnum depends on r_extern. */ + unsigned int r_symbolnum:24; + /* Nonzero means value is a pc-relative offset + and it should be relocated for changes in its own address + as well as for changes in the symbol or section specified. */ + unsigned int r_pcrel:1; + /* Length (as exponent of 2) of the field to be relocated. + Thus, a value of 2 indicates 1<<2 bytes. */ + unsigned int r_length:2; + /* 1 => relocate with value of symbol. + r_symbolnum is the index of the symbol + in file's the symbol table. + 0 => relocate with the address of a segment. + r_symbolnum is N_TEXT, N_DATA, N_BSS or N_ABS + (the N_EXT bit may be set also, but signifies nothing). */ + unsigned int r_extern:1; + /* Four bits that aren't used, but when writing an object file + it is desirable to clear them. */ + unsigned int r_pad:4; +}; +#endif /* no N_RELOCATION_INFO_DECLARED. */ + + +#endif /* __A_OUT_GNU_H__ */ diff --git a/linux-0.11-lab/1/linux/include/asm/io.h b/linux-0.11-lab/1/linux/include/asm/io.h new file mode 100755 index 0000000..d5cc42a --- /dev/null +++ b/linux-0.11-lab/1/linux/include/asm/io.h @@ -0,0 +1,24 @@ +#define outb(value,port) \ +__asm__ ("outb %%al,%%dx"::"a" (value),"d" (port)) + + +#define inb(port) ({ \ +unsigned char _v; \ +__asm__ volatile ("inb %%dx,%%al":"=a" (_v):"d" (port)); \ +_v; \ +}) + +#define outb_p(value,port) \ +__asm__ ("outb %%al,%%dx\n" \ + "\tjmp 1f\n" \ + "1:\tjmp 1f\n" \ + "1:"::"a" (value),"d" (port)) + +#define inb_p(port) ({ \ +unsigned char _v; \ +__asm__ volatile ("inb %%dx,%%al\n" \ + "\tjmp 1f\n" \ + "1:\tjmp 1f\n" \ + "1:":"=a" (_v):"d" (port)); \ +_v; \ +}) diff --git a/linux-0.11-lab/1/linux/include/asm/memory.h b/linux-0.11-lab/1/linux/include/asm/memory.h new file mode 100755 index 0000000..51b69e7 --- /dev/null +++ b/linux-0.11-lab/1/linux/include/asm/memory.h @@ -0,0 +1,15 @@ +/* + * NOTE!!! memcpy(dest,src,n) assumes ds=es=normal data segment. This + * goes for all kernel functions (ds=es=kernel space, fs=local data, + * gs=null), as well as for all well-behaving user programs (ds=es= + * user data space). This is NOT a bug, as any user program that changes + * es deserves to die if it isn't careful. + */ +#define memcpy(dest,src,n) ({ \ +void * _res = dest; \ +__asm__ ("cld;rep;movsb" \ + ::"D" ((long)(_res)),"S" ((long)(src)),"c" ((long) (n)) \ + ); \ +_res; \ +}) + diff --git a/linux-0.11-lab/1/linux/include/asm/segment.h b/linux-0.11-lab/1/linux/include/asm/segment.h new file mode 100755 index 0000000..94dd102 --- /dev/null +++ b/linux-0.11-lab/1/linux/include/asm/segment.h @@ -0,0 +1,65 @@ +static inline unsigned char get_fs_byte(const char * addr) +{ + unsigned register char _v; + + __asm__ ("movb %%fs:%1,%0":"=r" (_v):"m" (*addr)); + return _v; +} + +static inline unsigned short get_fs_word(const unsigned short *addr) +{ + unsigned short _v; + + __asm__ ("movw %%fs:%1,%0":"=r" (_v):"m" (*addr)); + return _v; +} + +static inline unsigned long get_fs_long(const unsigned long *addr) +{ + unsigned long _v; + + __asm__ ("movl %%fs:%1,%0":"=r" (_v):"m" (*addr)); \ + return _v; +} + +static inline void put_fs_byte(char val,char *addr) +{ +__asm__ ("movb %0,%%fs:%1"::"r" (val),"m" (*addr)); +} + +static inline void put_fs_word(short val,short * addr) +{ +__asm__ ("movw %0,%%fs:%1"::"r" (val),"m" (*addr)); +} + +static inline void put_fs_long(unsigned long val,unsigned long * addr) +{ +__asm__ ("movl %0,%%fs:%1"::"r" (val),"m" (*addr)); +} + +/* + * Someone who knows GNU asm better than I should double check the followig. + * It seems to work, but I don't know if I'm doing something subtly wrong. + * --- TYT, 11/24/91 + * [ nothing wrong here, Linus ] + */ + +static inline unsigned long get_fs() +{ + unsigned short _v; + __asm__("mov %%fs,%%ax":"=a" (_v):); + return _v; +} + +static inline unsigned long get_ds() +{ + unsigned short _v; + __asm__("mov %%ds,%%ax":"=a" (_v):); + return _v; +} + +static inline void set_fs(unsigned long val) +{ + __asm__("mov %0,%%fs"::"a" ((unsigned short) val)); +} + diff --git a/linux-0.11-lab/1/linux/include/asm/system.h b/linux-0.11-lab/1/linux/include/asm/system.h new file mode 100755 index 0000000..0b5a21d --- /dev/null +++ b/linux-0.11-lab/1/linux/include/asm/system.h @@ -0,0 +1,66 @@ +#define move_to_user_mode() \ +__asm__ ("movl %%esp,%%eax\n\t" \ + "pushl $0x17\n\t" \ + "pushl %%eax\n\t" \ + "pushfl\n\t" \ + "pushl $0x0f\n\t" \ + "pushl $1f\n\t" \ + "iret\n" \ + "1:\tmovl $0x17,%%eax\n\t" \ + "movw %%ax,%%ds\n\t" \ + "movw %%ax,%%es\n\t" \ + "movw %%ax,%%fs\n\t" \ + "movw %%ax,%%gs" \ + :::"ax") + +#define sti() __asm__ ("sti"::) +#define cli() __asm__ ("cli"::) +#define nop() __asm__ ("nop"::) + +#define iret() __asm__ ("iret"::) + +#define _set_gate(gate_addr,type,dpl,addr) \ +__asm__ ("movw %%dx,%%ax\n\t" \ + "movw %0,%%dx\n\t" \ + "movl %%eax,%1\n\t" \ + "movl %%edx,%2" \ + : \ + : "i" ((short) (0x8000+(dpl<<13)+(type<<8))), \ + "o" (*((char *) (gate_addr))), \ + "o" (*(4+(char *) (gate_addr))), \ + "d" ((char *) (addr)),"a" (0x00080000)) + +#define set_intr_gate(n,addr) \ + _set_gate(&idt[n],14,0,addr) + +#define set_trap_gate(n,addr) \ + _set_gate(&idt[n],15,0,addr) + +#define set_system_gate(n,addr) \ + _set_gate(&idt[n],15,3,addr) + +#define _set_seg_desc(gate_addr,type,dpl,base,limit) {\ + *(gate_addr) = ((base) & 0xff000000) | \ + (((base) & 0x00ff0000)>>16) | \ + ((limit) & 0xf0000) | \ + ((dpl)<<13) | \ + (0x00408000) | \ + ((type)<<8); \ + *((gate_addr)+1) = (((base) & 0x0000ffff)<<16) | \ + ((limit) & 0x0ffff); } + +#define _set_tssldt_desc(n,addr,type) \ +__asm__ ("movw $104,%1\n\t" \ + "movw %%ax,%2\n\t" \ + "rorl $16,%%eax\n\t" \ + "movb %%al,%3\n\t" \ + "movb $" type ",%4\n\t" \ + "movb $0x00,%5\n\t" \ + "movb %%ah,%6\n\t" \ + "rorl $16,%%eax" \ + ::"a" (addr), "m" (*(n)), "m" (*(n+2)), "m" (*(n+4)), \ + "m" (*(n+5)), "m" (*(n+6)), "m" (*(n+7)) \ + ) + +#define set_tss_desc(n,addr) _set_tssldt_desc(((char *) (n)),addr,"0x89") +#define set_ldt_desc(n,addr) _set_tssldt_desc(((char *) (n)),addr,"0x82") diff --git a/linux-0.11-lab/1/linux/include/const.h b/linux-0.11-lab/1/linux/include/const.h new file mode 100755 index 0000000..7828e61 --- /dev/null +++ b/linux-0.11-lab/1/linux/include/const.h @@ -0,0 +1,15 @@ +#ifndef _CONST_H +#define _CONST_H + +#define BUFFER_END 0x200000 + +#define I_TYPE 0170000 +#define I_DIRECTORY 0040000 +#define I_REGULAR 0100000 +#define I_BLOCK_SPECIAL 0060000 +#define I_CHAR_SPECIAL 0020000 +#define I_NAMED_PIPE 0010000 +#define I_SET_UID_BIT 0004000 +#define I_SET_GID_BIT 0002000 + +#endif diff --git a/linux-0.11-lab/1/linux/include/ctype.h b/linux-0.11-lab/1/linux/include/ctype.h new file mode 100755 index 0000000..7acf55d --- /dev/null +++ b/linux-0.11-lab/1/linux/include/ctype.h @@ -0,0 +1,34 @@ +#ifndef _CTYPE_H +#define _CTYPE_H + +#define _U 0x01 /* upper */ +#define _L 0x02 /* lower */ +#define _D 0x04 /* digit */ +#define _C 0x08 /* cntrl */ +#define _P 0x10 /* punct */ +#define _S 0x20 /* white space (space/lf/tab) */ +#define _X 0x40 /* hex digit */ +#define _SP 0x80 /* hard space (0x20) */ + +extern unsigned char _ctype[]; +extern char _ctmp; + +#define isalnum(c) ((_ctype+1)[c]&(_U|_L|_D)) +#define isalpha(c) ((_ctype+1)[c]&(_U|_L)) +#define iscntrl(c) ((_ctype+1)[c]&(_C)) +#define isdigit(c) ((_ctype+1)[c]&(_D)) +#define isgraph(c) ((_ctype+1)[c]&(_P|_U|_L|_D)) +#define islower(c) ((_ctype+1)[c]&(_L)) +#define isprint(c) ((_ctype+1)[c]&(_P|_U|_L|_D|_SP)) +#define ispunct(c) ((_ctype+1)[c]&(_P)) +#define isspace(c) ((_ctype+1)[c]&(_S)) +#define isupper(c) ((_ctype+1)[c]&(_U)) +#define isxdigit(c) ((_ctype+1)[c]&(_D|_X)) + +#define isascii(c) (((unsigned) c)<=0x7f) +#define toascii(c) (((unsigned) c)&0x7f) + +#define tolower(c) (_ctmp=c,isupper(_ctmp)?_ctmp-('A'-'a'):_ctmp) +#define toupper(c) (_ctmp=c,islower(_ctmp)?_ctmp-('a'-'A'):_ctmp) + +#endif diff --git a/linux-0.11-lab/1/linux/include/errno.h b/linux-0.11-lab/1/linux/include/errno.h new file mode 100755 index 0000000..c282f69 --- /dev/null +++ b/linux-0.11-lab/1/linux/include/errno.h @@ -0,0 +1,60 @@ +#ifndef _ERRNO_H +#define _ERRNO_H + +/* + * ok, as I hadn't got any other source of information about + * possible error numbers, I was forced to use the same numbers + * as minix. + * Hopefully these are posix or something. I wouldn't know (and posix + * isn't telling me - they want $$$ for their f***ing standard). + * + * We don't use the _SIGN cludge of minix, so kernel returns must + * see to the sign by themselves. + * + * NOTE! Remember to change strerror() if you change this file! + */ + +extern int errno; + +#define ERROR 99 +#define EPERM 1 +#define ENOENT 2 +#define ESRCH 3 +#define EINTR 4 +#define EIO 5 +#define ENXIO 6 +#define E2BIG 7 +#define ENOEXEC 8 +#define EBADF 9 +#define ECHILD 10 +#define EAGAIN 11 +#define ENOMEM 12 +#define EACCES 13 +#define EFAULT 14 +#define ENOTBLK 15 +#define EBUSY 16 +#define EEXIST 17 +#define EXDEV 18 +#define ENODEV 19 +#define ENOTDIR 20 +#define EISDIR 21 +#define EINVAL 22 +#define ENFILE 23 +#define EMFILE 24 +#define ENOTTY 25 +#define ETXTBSY 26 +#define EFBIG 27 +#define ENOSPC 28 +#define ESPIPE 29 +#define EROFS 30 +#define EMLINK 31 +#define EPIPE 32 +#define EDOM 33 +#define ERANGE 34 +#define EDEADLK 35 +#define ENAMETOOLONG 36 +#define ENOLCK 37 +#define ENOSYS 38 +#define ENOTEMPTY 39 + +#endif diff --git a/linux-0.11-lab/1/linux/include/fcntl.h b/linux-0.11-lab/1/linux/include/fcntl.h new file mode 100755 index 0000000..a5bf9af --- /dev/null +++ b/linux-0.11-lab/1/linux/include/fcntl.h @@ -0,0 +1,55 @@ +#ifndef _FCNTL_H +#define _FCNTL_H + +#include + +/* open/fcntl - NOCTTY, NDELAY isn't implemented yet */ +#define O_ACCMODE 00003 +#define O_RDONLY 00 +#define O_WRONLY 01 +#define O_RDWR 02 +#define O_CREAT 00100 /* not fcntl */ +#define O_EXCL 00200 /* not fcntl */ +#define O_NOCTTY 00400 /* not fcntl */ +#define O_TRUNC 01000 /* not fcntl */ +#define O_APPEND 02000 +#define O_NONBLOCK 04000 /* not fcntl */ +#define O_NDELAY O_NONBLOCK + +/* Defines for fcntl-commands. Note that currently + * locking isn't supported, and other things aren't really + * tested. + */ +#define F_DUPFD 0 /* dup */ +#define F_GETFD 1 /* get f_flags */ +#define F_SETFD 2 /* set f_flags */ +#define F_GETFL 3 /* more flags (cloexec) */ +#define F_SETFL 4 +#define F_GETLK 5 /* not implemented */ +#define F_SETLK 6 +#define F_SETLKW 7 + +/* for F_[GET|SET]FL */ +#define FD_CLOEXEC 1 /* actually anything with low bit set goes */ + +/* Ok, these are locking features, and aren't implemented at any + * level. POSIX wants them. + */ +#define F_RDLCK 0 +#define F_WRLCK 1 +#define F_UNLCK 2 + +/* Once again - not implemented, but ... */ +struct flock { + short l_type; + short l_whence; + off_t l_start; + off_t l_len; + pid_t l_pid; +}; + +extern int creat(const char * filename,mode_t mode); +extern int fcntl(int fildes,int cmd, ...); +extern int open(const char * filename, int flags, ...); + +#endif diff --git a/linux-0.11-lab/1/linux/include/linux/._sys.h b/linux-0.11-lab/1/linux/include/linux/._sys.h new file mode 100755 index 0000000000000000000000000000000000000000..75e4511c8e0684af955381ca596fcf676d5f3e51 GIT binary patch literal 4096 zcmZQz6=P>$Vqox1Ojhs@R)|o50+1L3ClDJkFz{^v(m+1nBL)UWIUt(=a103vVi0ma z0nx$m1gJa{O$*3$khlN?gH&>Uu3ln6K~Ab(PGWIMX>n>wN@7W>azHRt&leya$-rQa zP?wupk_c3jXqD~j;**$^niFqkR#;?QnwOnfP;6#iW?EKmUXoU1VrE_fviJbolLU}i zmWKqaLG&lRn&yQ^EqU(q*2qPFzN(+KPhx`Xt<3a=0k3D>^h%LU6x>`fV@E>cfepb8CEVI2c(+?Au>;=l8psm0@|4b!eAg5l95@gP?TDnUs{x$ zs*sjnl&z4NSCX1nl9`{En3GefkdvBLqL7r6n3oOg3qy4cX$sZBh0P$3A A5dZ)H literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/include/linux/config.h b/linux-0.11-lab/1/linux/include/linux/config.h new file mode 100755 index 0000000..c979fb3 --- /dev/null +++ b/linux-0.11-lab/1/linux/include/linux/config.h @@ -0,0 +1,48 @@ +#ifndef _CONFIG_H +#define _CONFIG_H + +/* + * The root-device is no longer hard-coded. You can change the default + * root-device by changing the line ROOT_DEV = XXX in boot/bootsect.s + */ + +/* + * define your keyboard here - + * KBD_FINNISH for Finnish keyboards + * KBD_US for US-type + * KBD_GR for German keyboards + * KBD_FR for Frech keyboard + */ +#define KBD_US +/*#define KBD_GR */ +/*#define KBD_FR */ +/*#define KBD_FINNISH */ + +/* + * Normally, Linux can get the drive parameters from the BIOS at + * startup, but if this for some unfathomable reason fails, you'd + * be left stranded. For this case, you can define HD_TYPE, which + * contains all necessary info on your harddisk. + * + * The HD_TYPE macro should look like this: + * + * #define HD_TYPE { head, sect, cyl, wpcom, lzone, ctl} + * + * In case of two harddisks, the info should be sepatated by + * commas: + * + * #define HD_TYPE { h,s,c,wpcom,lz,ctl },{ h,s,c,wpcom,lz,ctl } + */ +/* + This is an example, two drives, first is type 2, second is type 3: + +#define HD_TYPE { 4,17,615,300,615,8 }, { 6,17,615,300,615,0 } + + NOTE: ctl is 0 for all drives with heads<=8, and ctl=8 for drives + with more than 8 heads. + + If you want the BIOS to tell what kind of drive you have, just + leave HD_TYPE undefined. This is the normal thing to do. +*/ + +#endif diff --git a/linux-0.11-lab/1/linux/include/linux/fdreg.h b/linux-0.11-lab/1/linux/include/linux/fdreg.h new file mode 100755 index 0000000..01355af --- /dev/null +++ b/linux-0.11-lab/1/linux/include/linux/fdreg.h @@ -0,0 +1,71 @@ +/* + * This file contains some defines for the floppy disk controller. + * Various sources. Mostly "IBM Microcomputers: A Programmers + * Handbook", Sanches and Canton. + */ +#ifndef _FDREG_H +#define _FDREG_H + +extern int ticks_to_floppy_on(unsigned int nr); +extern void floppy_on(unsigned int nr); +extern void floppy_off(unsigned int nr); +extern void floppy_select(unsigned int nr); +extern void floppy_deselect(unsigned int nr); + +/* Fd controller regs. S&C, about page 340 */ +#define FD_STATUS 0x3f4 +#define FD_DATA 0x3f5 +#define FD_DOR 0x3f2 /* Digital Output Register */ +#define FD_DIR 0x3f7 /* Digital Input Register (read) */ +#define FD_DCR 0x3f7 /* Diskette Control Register (write)*/ + +/* Bits of main status register */ +#define STATUS_BUSYMASK 0x0F /* drive busy mask */ +#define STATUS_BUSY 0x10 /* FDC busy */ +#define STATUS_DMA 0x20 /* 0- DMA mode */ +#define STATUS_DIR 0x40 /* 0- cpu->fdc */ +#define STATUS_READY 0x80 /* Data reg ready */ + +/* Bits of FD_ST0 */ +#define ST0_DS 0x03 /* drive select mask */ +#define ST0_HA 0x04 /* Head (Address) */ +#define ST0_NR 0x08 /* Not Ready */ +#define ST0_ECE 0x10 /* Equipment chech error */ +#define ST0_SE 0x20 /* Seek end */ +#define ST0_INTR 0xC0 /* Interrupt code mask */ + +/* Bits of FD_ST1 */ +#define ST1_MAM 0x01 /* Missing Address Mark */ +#define ST1_WP 0x02 /* Write Protect */ +#define ST1_ND 0x04 /* No Data - unreadable */ +#define ST1_OR 0x10 /* OverRun */ +#define ST1_CRC 0x20 /* CRC error in data or addr */ +#define ST1_EOC 0x80 /* End Of Cylinder */ + +/* Bits of FD_ST2 */ +#define ST2_MAM 0x01 /* Missing Addess Mark (again) */ +#define ST2_BC 0x02 /* Bad Cylinder */ +#define ST2_SNS 0x04 /* Scan Not Satisfied */ +#define ST2_SEH 0x08 /* Scan Equal Hit */ +#define ST2_WC 0x10 /* Wrong Cylinder */ +#define ST2_CRC 0x20 /* CRC error in data field */ +#define ST2_CM 0x40 /* Control Mark = deleted */ + +/* Bits of FD_ST3 */ +#define ST3_HA 0x04 /* Head (Address) */ +#define ST3_TZ 0x10 /* Track Zero signal (1=track 0) */ +#define ST3_WP 0x40 /* Write Protect */ + +/* Values for FD_COMMAND */ +#define FD_RECALIBRATE 0x07 /* move to track 0 */ +#define FD_SEEK 0x0F /* seek track */ +#define FD_READ 0xE6 /* read with MT, MFM, SKip deleted */ +#define FD_WRITE 0xC5 /* write with MT, MFM */ +#define FD_SENSEI 0x08 /* Sense Interrupt Status */ +#define FD_SPECIFY 0x03 /* specify HUT etc */ + +/* DMA commands */ +#define DMA_READ 0x46 +#define DMA_WRITE 0x4A + +#endif diff --git a/linux-0.11-lab/1/linux/include/linux/fs.h b/linux-0.11-lab/1/linux/include/linux/fs.h new file mode 100755 index 0000000..7a90b10 --- /dev/null +++ b/linux-0.11-lab/1/linux/include/linux/fs.h @@ -0,0 +1,202 @@ +/* + * This file has definitions for some important file table + * structures etc. + */ + +#ifndef _FS_H +#define _FS_H + +#include + +/* devices are as follows: (same as minix, so we can use the minix + * file system. These are major numbers.) + * + * 0 - unused (nodev) + * 1 - /dev/mem + * 2 - /dev/fd + * 3 - /dev/hd + * 4 - /dev/ttyx + * 5 - /dev/tty + * 6 - /dev/lp + * 7 - unnamed pipes + */ + +#define IS_SEEKABLE(x) ((x)>=1 && (x)<=3) + +#define READ 0 +#define WRITE 1 +#define READA 2 /* read-ahead - don't pause */ +#define WRITEA 3 /* "write-ahead" - silly, but somewhat useful */ + +void buffer_init(long buffer_end); + +#define MAJOR(a) (((unsigned)(a))>>8) +#define MINOR(a) ((a)&0xff) + +#define NAME_LEN 14 +#define ROOT_INO 1 + +#define I_MAP_SLOTS 8 +#define Z_MAP_SLOTS 8 +#define SUPER_MAGIC 0x137F + +#define NR_OPEN 20 +#define NR_INODE 32 +#define NR_FILE 64 +#define NR_SUPER 8 +#define NR_HASH 307 +#define NR_BUFFERS nr_buffers +#define BLOCK_SIZE 1024 +#define BLOCK_SIZE_BITS 10 +#ifndef NULL +#define NULL ((void *) 0) +#endif + +#define INODES_PER_BLOCK ((BLOCK_SIZE)/(sizeof (struct d_inode))) +#define DIR_ENTRIES_PER_BLOCK ((BLOCK_SIZE)/(sizeof (struct dir_entry))) + +#define PIPE_HEAD(inode) ((inode).i_zone[0]) +#define PIPE_TAIL(inode) ((inode).i_zone[1]) +#define PIPE_SIZE(inode) ((PIPE_HEAD(inode)-PIPE_TAIL(inode))&(PAGE_SIZE-1)) +#define PIPE_EMPTY(inode) (PIPE_HEAD(inode)==PIPE_TAIL(inode)) +#define PIPE_FULL(inode) (PIPE_SIZE(inode)==(PAGE_SIZE-1)) +#define INC_PIPE(head) \ +__asm__("incl %0\n\tandl $4095,%0"::"m" (head)) + +typedef char buffer_block[BLOCK_SIZE]; + +struct buffer_head { + char * b_data; /* pointer to data block (1024 bytes) */ + unsigned long b_blocknr; /* block number */ + unsigned short b_dev; /* device (0 = free) */ + unsigned char b_uptodate; + unsigned char b_dirt; /* 0-clean,1-dirty */ + unsigned char b_count; /* users using this block */ + unsigned char b_lock; /* 0 - ok, 1 -locked */ + struct task_struct * b_wait; + struct buffer_head * b_prev; + struct buffer_head * b_next; + struct buffer_head * b_prev_free; + struct buffer_head * b_next_free; +}; + +struct d_inode { + unsigned short i_mode; + unsigned short i_uid; + unsigned long i_size; + unsigned long i_time; + unsigned char i_gid; + unsigned char i_nlinks; + unsigned short i_zone[9]; +}; + +struct m_inode { + unsigned short i_mode; + unsigned short i_uid; + unsigned long i_size; + unsigned long i_mtime; + unsigned char i_gid; + unsigned char i_nlinks; + unsigned short i_zone[9]; +/* these are in memory also */ + struct task_struct * i_wait; + unsigned long i_atime; + unsigned long i_ctime; + unsigned short i_dev; + unsigned short i_num; + unsigned short i_count; + unsigned char i_lock; + unsigned char i_dirt; + unsigned char i_pipe; + unsigned char i_mount; + unsigned char i_seek; + unsigned char i_update; +}; + +struct file { + unsigned short f_mode; + unsigned short f_flags; + unsigned short f_count; + struct m_inode * f_inode; + off_t f_pos; +}; + +struct super_block { + unsigned short s_ninodes; + unsigned short s_nzones; + unsigned short s_imap_blocks; + unsigned short s_zmap_blocks; + unsigned short s_firstdatazone; + unsigned short s_log_zone_size; + unsigned long s_max_size; + unsigned short s_magic; +/* These are only in memory */ + struct buffer_head * s_imap[8]; + struct buffer_head * s_zmap[8]; + unsigned short s_dev; + struct m_inode * s_isup; + struct m_inode * s_imount; + unsigned long s_time; + struct task_struct * s_wait; + unsigned char s_lock; + unsigned char s_rd_only; + unsigned char s_dirt; +}; + +struct d_super_block { + unsigned short s_ninodes; + unsigned short s_nzones; + unsigned short s_imap_blocks; + unsigned short s_zmap_blocks; + unsigned short s_firstdatazone; + unsigned short s_log_zone_size; + unsigned long s_max_size; + unsigned short s_magic; +}; + +struct dir_entry { + unsigned short inode; + char name[NAME_LEN]; +}; + +extern struct m_inode inode_table[NR_INODE]; +extern struct file file_table[NR_FILE]; +extern struct super_block super_block[NR_SUPER]; +extern struct buffer_head * start_buffer; +extern int nr_buffers; + +extern void check_disk_change(int dev); +extern int floppy_change(unsigned int nr); +extern int ticks_to_floppy_on(unsigned int dev); +extern void floppy_on(unsigned int dev); +extern void floppy_off(unsigned int dev); +extern void truncate(struct m_inode * inode); +extern void sync_inodes(void); +extern void wait_on(struct m_inode * inode); +extern int bmap(struct m_inode * inode,int block); +extern int create_block(struct m_inode * inode,int block); +extern struct m_inode * namei(const char * pathname); +extern int open_namei(const char * pathname, int flag, int mode, + struct m_inode ** res_inode); +extern void iput(struct m_inode * inode); +extern struct m_inode * iget(int dev,int nr); +extern struct m_inode * get_empty_inode(void); +extern struct m_inode * get_pipe_inode(void); +extern struct buffer_head * get_hash_table(int dev, int block); +extern struct buffer_head * getblk(int dev, int block); +extern void ll_rw_block(int rw, struct buffer_head * bh); +extern void brelse(struct buffer_head * buf); +extern struct buffer_head * bread(int dev,int block); +extern void bread_page(unsigned long addr,int dev,int b[4]); +extern struct buffer_head * breada(int dev,int block,...); +extern int new_block(int dev); +extern void free_block(int dev, int block); +extern struct m_inode * new_inode(int dev); +extern void free_inode(struct m_inode * inode); +extern int sync_dev(int dev); +extern struct super_block * get_super(int dev); +extern int ROOT_DEV; + +extern void mount_root(void); + +#endif diff --git a/linux-0.11-lab/1/linux/include/linux/hdreg.h b/linux-0.11-lab/1/linux/include/linux/hdreg.h new file mode 100755 index 0000000..e6c593f --- /dev/null +++ b/linux-0.11-lab/1/linux/include/linux/hdreg.h @@ -0,0 +1,65 @@ +/* + * This file contains some defines for the AT-hd-controller. + * Various sources. Check out some definitions (see comments with + * a ques). + */ +#ifndef _HDREG_H +#define _HDREG_H + +/* Hd controller regs. Ref: IBM AT Bios-listing */ +#define HD_DATA 0x1f0 /* _CTL when writing */ +#define HD_ERROR 0x1f1 /* see err-bits */ +#define HD_NSECTOR 0x1f2 /* nr of sectors to read/write */ +#define HD_SECTOR 0x1f3 /* starting sector */ +#define HD_LCYL 0x1f4 /* starting cylinder */ +#define HD_HCYL 0x1f5 /* high byte of starting cyl */ +#define HD_CURRENT 0x1f6 /* 101dhhhh , d=drive, hhhh=head */ +#define HD_STATUS 0x1f7 /* see status-bits */ +#define HD_PRECOMP HD_ERROR /* same io address, read=error, write=precomp */ +#define HD_COMMAND HD_STATUS /* same io address, read=status, write=cmd */ + +#define HD_CMD 0x3f6 + +/* Bits of HD_STATUS */ +#define ERR_STAT 0x01 +#define INDEX_STAT 0x02 +#define ECC_STAT 0x04 /* Corrected error */ +#define DRQ_STAT 0x08 +#define SEEK_STAT 0x10 +#define WRERR_STAT 0x20 +#define READY_STAT 0x40 +#define BUSY_STAT 0x80 + +/* Values for HD_COMMAND */ +#define WIN_RESTORE 0x10 +#define WIN_READ 0x20 +#define WIN_WRITE 0x30 +#define WIN_VERIFY 0x40 +#define WIN_FORMAT 0x50 +#define WIN_INIT 0x60 +#define WIN_SEEK 0x70 +#define WIN_DIAGNOSE 0x90 +#define WIN_SPECIFY 0x91 + +/* Bits for HD_ERROR */ +#define MARK_ERR 0x01 /* Bad address mark ? */ +#define TRK0_ERR 0x02 /* couldn't find track 0 */ +#define ABRT_ERR 0x04 /* ? */ +#define ID_ERR 0x10 /* ? */ +#define ECC_ERR 0x40 /* ? */ +#define BBD_ERR 0x80 /* ? */ + +struct partition { + unsigned char boot_ind; /* 0x80 - active (unused) */ + unsigned char head; /* ? */ + unsigned char sector; /* ? */ + unsigned char cyl; /* ? */ + unsigned char sys_ind; /* ? */ + unsigned char end_head; /* ? */ + unsigned char end_sector; /* ? */ + unsigned char end_cyl; /* ? */ + unsigned int start_sect; /* starting sector counting from 0 */ + unsigned int nr_sects; /* nr of sectors in partition */ +}; + +#endif diff --git a/linux-0.11-lab/1/linux/include/linux/head.h b/linux-0.11-lab/1/linux/include/linux/head.h new file mode 100755 index 0000000..db3dda2 --- /dev/null +++ b/linux-0.11-lab/1/linux/include/linux/head.h @@ -0,0 +1,20 @@ +#ifndef _HEAD_H +#define _HEAD_H + +typedef struct desc_struct { + unsigned long a,b; +} desc_table[256]; + +extern unsigned long pg_dir[1024]; +extern desc_table idt,gdt; + +#define GDT_NUL 0 +#define GDT_CODE 1 +#define GDT_DATA 2 +#define GDT_TMP 3 + +#define LDT_NUL 0 +#define LDT_CODE 1 +#define LDT_DATA 2 + +#endif diff --git a/linux-0.11-lab/1/linux/include/linux/kernel.h b/linux-0.11-lab/1/linux/include/linux/kernel.h new file mode 100755 index 0000000..cb40dd5 --- /dev/null +++ b/linux-0.11-lab/1/linux/include/linux/kernel.h @@ -0,0 +1,22 @@ +/* + * 'kernel.h' contains some often-used function prototypes etc + */ +void verify_area(void * addr,int count); +volatile void panic(const char * str); +int printf(const char * fmt, ...); +int printk(const char * fmt, ...); +int tty_write(unsigned ch,char * buf,int count); +void * malloc(unsigned int size); +void free_s(void * obj, int size); + +#define free(x) free_s((x), 0) + +/* + * This is defined as a macro, but at some point this might become a + * real subroutine that sets a flag if it returns true (to do + * BSD-style accounting where the process is flagged if it uses root + * privs). The implication of this is that you should do normal + * permissions checks first, and check suser() last. + */ +#define suser() (current->euid == 0) + diff --git a/linux-0.11-lab/1/linux/include/linux/mm.h b/linux-0.11-lab/1/linux/include/linux/mm.h new file mode 100755 index 0000000..5a160f3 --- /dev/null +++ b/linux-0.11-lab/1/linux/include/linux/mm.h @@ -0,0 +1,10 @@ +#ifndef _MM_H +#define _MM_H + +#define PAGE_SIZE 4096 + +extern unsigned long get_free_page(void); +extern unsigned long put_page(unsigned long page,unsigned long address); +extern void free_page(unsigned long addr); + +#endif diff --git a/linux-0.11-lab/1/linux/include/linux/sched.h b/linux-0.11-lab/1/linux/include/linux/sched.h new file mode 100755 index 0000000..772646a --- /dev/null +++ b/linux-0.11-lab/1/linux/include/linux/sched.h @@ -0,0 +1,239 @@ +#ifndef _SCHED_H +#define _SCHED_H + +#define NR_TASKS 64 +#define HZ 100 + +#define FIRST_TASK task[0] +#define LAST_TASK task[NR_TASKS-1] + +#include +#include +#include +#include + +#if (NR_OPEN > 32) +#error "Currently the close-on-exec-flags are in one word, max 32 files/proc" +#endif + +#define TASK_RUNNING 0 +#define TASK_INTERRUPTIBLE 1 +#define TASK_UNINTERRUPTIBLE 2 +#define TASK_ZOMBIE 3 +#define TASK_STOPPED 4 + +#ifndef NULL +#define NULL ((void *) 0) +#endif + +extern int copy_page_tables(unsigned long from, unsigned long to, long size); +extern int free_page_tables(unsigned long from, unsigned long size); + +extern void sched_init(void); +extern void schedule(void); +extern void trap_init(void); +extern void panic(const char * str); +extern int tty_write(unsigned minor,char * buf,int count); + +typedef int (*fn_ptr)(); + +struct i387_struct { + long cwd; + long swd; + long twd; + long fip; + long fcs; + long foo; + long fos; + long st_space[20]; /* 8*10 bytes for each FP-reg = 80 bytes */ +}; + +struct tss_struct { + long back_link; /* 16 high bits zero */ + long esp0; + long ss0; /* 16 high bits zero */ + long esp1; + long ss1; /* 16 high bits zero */ + long esp2; + long ss2; /* 16 high bits zero */ + long cr3; + long eip; + long eflags; + long eax,ecx,edx,ebx; + long esp; + long ebp; + long esi; + long edi; + long es; /* 16 high bits zero */ + long cs; /* 16 high bits zero */ + long ss; /* 16 high bits zero */ + long ds; /* 16 high bits zero */ + long fs; /* 16 high bits zero */ + long gs; /* 16 high bits zero */ + long ldt; /* 16 high bits zero */ + long trace_bitmap; /* bits: trace 0, bitmap 16-31 */ + struct i387_struct i387; +}; + +struct task_struct { +/* these are hardcoded - don't touch */ + long state; /* -1 unrunnable, 0 runnable, >0 stopped */ + long counter; + long priority; + long signal; + struct sigaction sigaction[32]; + long blocked; /* bitmap of masked signals */ +/* various fields */ + int exit_code; + unsigned long start_code,end_code,end_data,brk,start_stack; + long pid,father,pgrp,session,leader; + unsigned short uid,euid,suid; + unsigned short gid,egid,sgid; + long alarm; + long utime,stime,cutime,cstime,start_time; + unsigned short used_math; +/* file system info */ + int tty; /* -1 if no tty, so it must be signed */ + unsigned short umask; + struct m_inode * pwd; + struct m_inode * root; + struct m_inode * executable; + unsigned long close_on_exec; + struct file * filp[NR_OPEN]; +/* ldt for this task 0 - zero 1 - cs 2 - ds&ss */ + struct desc_struct ldt[3]; +/* tss for this task */ + struct tss_struct tss; +}; + +/* + * INIT_TASK is used to set up the first task table, touch at + * your own risk!. Base=0, limit=0x9ffff (=640kB) + */ +#define INIT_TASK \ +/* state etc */ { 0,15,15, \ +/* signals */ 0,{{},},0, \ +/* ec,brk... */ 0,0,0,0,0,0, \ +/* pid etc.. */ 0,-1,0,0,0, \ +/* uid etc */ 0,0,0,0,0,0, \ +/* alarm */ 0,0,0,0,0,0, \ +/* math */ 0, \ +/* fs info */ -1,0022,NULL,NULL,NULL,0, \ +/* filp */ {NULL,}, \ + { \ + {0,0}, \ +/* ldt */ {0x9f,0xc0fa00}, \ + {0x9f,0xc0f200}, \ + }, \ +/*tss*/ {0,PAGE_SIZE+(long)&init_task,0x10,0,0,0,0,(long)&pg_dir,\ + 0,0,0,0,0,0,0,0, \ + 0,0,0x17,0x17,0x17,0x17,0x17,0x17, \ + _LDT(0),0x80000000, \ + {} \ + }, \ +} + +extern struct task_struct *task[NR_TASKS]; +extern struct task_struct *last_task_used_math; +extern struct task_struct *current; +extern long volatile jiffies; +extern long startup_time; + +#define CURRENT_TIME (startup_time+jiffies/HZ) + +extern void add_timer(long jiffies, void (*fn)(void)); +extern void sleep_on(struct task_struct ** p); +extern void interruptible_sleep_on(struct task_struct ** p); +extern void wake_up(struct task_struct ** p); + +/* + * Entry into gdt where to find first TSS. 0-nul, 1-cs, 2-ds, 3-syscall + * 4-TSS0, 5-LDT0, 6-TSS1 etc ... + */ +#define FIRST_TSS_ENTRY 4 +#define FIRST_LDT_ENTRY (FIRST_TSS_ENTRY+1) +#define _TSS(n) ((((unsigned long) n)<<4)+(FIRST_TSS_ENTRY<<3)) +#define _LDT(n) ((((unsigned long) n)<<4)+(FIRST_LDT_ENTRY<<3)) +#define ltr(n) __asm__("ltr %%ax"::"a" (_TSS(n))) +#define lldt(n) __asm__("lldt %%ax"::"a" (_LDT(n))) +#define str(n) \ +__asm__("str %%ax\n\t" \ + "subl %2,%%eax\n\t" \ + "shrl $4,%%eax" \ + :"=a" (n) \ + :"a" (0),"i" (FIRST_TSS_ENTRY<<3)) +/* + * switch_to(n) should switch tasks to task nr n, first + * checking that n isn't the current task, in which case it does nothing. + * This also clears the TS-flag if the task we switched to has used + * tha math co-processor latest. + */ +#define switch_to(n) {\ +struct {long a,b;} __tmp; \ +__asm__("cmpl %%ecx,current\n\t" \ + "je 1f\n\t" \ + "movw %%dx,%1\n\t" \ + "xchgl %%ecx,current\n\t" \ + "ljmp *%0\n\t" \ + "cmpl %%ecx,last_task_used_math\n\t" \ + "jne 1f\n\t" \ + "clts\n" \ + "1:" \ + ::"m" (*&__tmp.a),"m" (*&__tmp.b), \ + "d" (_TSS(n)),"c" ((long) task[n])); \ +} + +#define PAGE_ALIGN(n) (((n)+0xfff)&0xfffff000) + +#define _set_base(addr,base) \ +__asm__ ("push %%edx\n\t" \ + "movw %%dx,%0\n\t" \ + "rorl $16,%%edx\n\t" \ + "movb %%dl,%1\n\t" \ + "movb %%dh,%2\n\t" \ + "pop %%edx" \ + ::"m" (*((addr)+2)), \ + "m" (*((addr)+4)), \ + "m" (*((addr)+7)), \ + "d" (base) \ + ) + +#define _set_limit(addr,limit) \ +__asm__ ("push %%edx\n\t" \ + "movw %%dx,%0\n\t" \ + "rorl $16,%%edx\n\t" \ + "movb %1,%%dh\n\t" \ + "andb $0xf0,%%dh\n\t" \ + "orb %%dh,%%dl\n\t" \ + "movb %%dl,%1\n\t" \ + "pop %%edx" \ + ::"m" (*(addr)), \ + "m" (*((addr)+6)), \ + "d" (limit) \ + ) + +#define set_base(ldt,base) _set_base( ((char *)&(ldt)) , (base) ) +#define set_limit(ldt,limit) _set_limit( ((char *)&(ldt)) , (limit-1)>>12 ) + +static inline unsigned long _get_base(char * addr) +{ + unsigned long __base; + __asm__("movb %3,%%dh\n\t" + "movb %2,%%dl\n\t" + "shll $16,%%edx\n\t" + "movw %1,%%dx" + :"=&d" (__base) + :"m" (*((addr)+2)), + "m" (*((addr)+4)), + "m" (*((addr)+7))); + return __base; +} + +#define get_base(ldt) _get_base( ((char *)&(ldt)) ) + +#define get_limit(segment) ({ \ +unsigned long __limit; \ +__asm__("lsll %1,%0\n\tincl %0":"=r" (__limit):"r" (segment)); \ +__limit;}) + +#endif diff --git a/linux-0.11-lab/1/linux/include/linux/sys.h b/linux-0.11-lab/1/linux/include/linux/sys.h new file mode 100755 index 0000000..6e1ba2e --- /dev/null +++ b/linux-0.11-lab/1/linux/include/linux/sys.h @@ -0,0 +1,117 @@ +/* + * Why isn't this a .c file? Enquiring minds.... + */ + +extern int sys_setup(); +extern int sys_exit(); +extern int sys_fork(); +extern int sys_read(); +extern int sys_write(); +extern int sys_open(); +extern int sys_close(); +extern int sys_waitpid(); +extern int sys_creat(); +extern int sys_link(); +extern int sys_unlink(); +extern int sys_execve(); +extern int sys_chdir(); +extern int sys_time(); +extern int sys_mknod(); +extern int sys_chmod(); +extern int sys_chown(); +extern int sys_break(); +extern int sys_stat(); +extern int sys_lseek(); +extern int sys_getpid(); +extern int sys_mount(); +extern int sys_umount(); +extern int sys_setuid(); +extern int sys_getuid(); +extern int sys_stime(); +extern int sys_ptrace(); +extern int sys_alarm(); +extern int sys_fstat(); +extern int sys_pause(); +extern int sys_utime(); +extern int sys_stty(); +extern int sys_gtty(); +extern int sys_access(); +extern int sys_nice(); +extern int sys_ftime(); +extern int sys_sync(); +extern int sys_kill(); +extern int sys_rename(); +extern int sys_mkdir(); +extern int sys_rmdir(); +extern int sys_dup(); +extern int sys_pipe(); +extern int sys_times(); +extern int sys_prof(); +extern int sys_brk(); +extern int sys_setgid(); +extern int sys_getgid(); +extern int sys_signal(); +extern int sys_geteuid(); +extern int sys_getegid(); +extern int sys_acct(); +extern int sys_phys(); +extern int sys_lock(); +extern int sys_ioctl(); +extern int sys_fcntl(); +extern int sys_mpx(); +extern int sys_setpgid(); +extern int sys_ulimit(); +extern int sys_uname(); +extern int sys_umask(); +extern int sys_chroot(); +extern int sys_ustat(); +extern int sys_dup2(); +extern int sys_getppid(); +extern int sys_getpgrp(); +extern int sys_setsid(); +extern int sys_sigaction(); +extern int sys_sgetmask(); +extern int sys_ssetmask(); +extern int sys_setreuid(); +extern int sys_setregid(); +extern int sys_sigpending(); +extern int sys_sigsuspend(); +extern int sys_sethostname(); +extern int sys_setrlimit(); +extern int sys_getrlimit(); +extern int sys_getrusage(); +extern int sys_gettimeofday(); +extern int sys_settimeofday(); +extern int sys_getgroups(); +extern int sys_setgroups(); +extern int sys_select(); +extern int sys_symlink(); +extern int sys_lstat(); +extern int sys_readlink(); +extern int sys_uselib(); +extern int sys_execve2(); +extern int sys_getdents(); +extern int sys_pipe2(); +extern int sys_sleep(); +extern int sys_getcwd(); + +fn_ptr sys_call_table[] = { sys_setup, sys_exit, sys_fork, sys_read, +sys_write, sys_open, sys_close, sys_waitpid, sys_creat, sys_link, +sys_unlink, sys_execve, sys_chdir, sys_time, sys_mknod, sys_chmod, +sys_chown, sys_break, sys_stat, sys_lseek, sys_getpid, sys_mount, +sys_umount, sys_setuid, sys_getuid, sys_stime, sys_ptrace, sys_alarm, +sys_fstat, sys_pause, sys_utime, sys_stty, sys_gtty, sys_access, +sys_nice, sys_ftime, sys_sync, sys_kill, sys_rename, sys_mkdir, +sys_rmdir, sys_dup, sys_pipe, sys_times, sys_prof, sys_brk, sys_setgid, +sys_getgid, sys_signal, sys_geteuid, sys_getegid, sys_acct, sys_phys, +sys_lock, sys_ioctl, sys_fcntl, sys_mpx, sys_setpgid, sys_ulimit, +sys_uname, sys_umask, sys_chroot, sys_ustat, sys_dup2, sys_getppid, +sys_getpgrp, sys_setsid, sys_sigaction, sys_sgetmask, sys_ssetmask, +sys_setreuid,sys_setregid, sys_sigsuspend, sys_sigpending, sys_sethostname, +sys_setrlimit, sys_getrlimit, sys_getrusage, sys_gettimeofday, +sys_settimeofday, sys_getgroups, sys_setgroups, sys_select, sys_symlink, +sys_lstat, sys_readlink, sys_uselib, sys_execve2, sys_getdents, sys_pipe2, +sys_sleep, sys_getcwd }; + +/* So we don't have to do any more manual updating.... */ +int NR_syscalls = sizeof(sys_call_table)/sizeof(fn_ptr); diff --git a/linux-0.11-lab/1/linux/include/linux/tty.h b/linux-0.11-lab/1/linux/include/linux/tty.h new file mode 100755 index 0000000..ad846b3 --- /dev/null +++ b/linux-0.11-lab/1/linux/include/linux/tty.h @@ -0,0 +1,77 @@ +/* + * 'tty.h' defines some structures used by tty_io.c and some defines. + * + * NOTE! Don't touch this without checking that nothing in rs_io.s or + * con_io.s breaks. Some constants are hardwired into the system (mainly + * offsets into 'tty_queue' + */ + +#ifndef _TTY_H +#define _TTY_H + +#include + +#define TTY_BUF_SIZE 1024 + +struct tty_queue { + unsigned long data; + unsigned long head; + unsigned long tail; + struct task_struct * proc_list; + char buf[TTY_BUF_SIZE]; +}; + +#define INC(a) ((a) = ((a)+1) & (TTY_BUF_SIZE-1)) +#define DEC(a) ((a) = ((a)-1) & (TTY_BUF_SIZE-1)) +#define EMPTY(a) ((a).head == (a).tail) +#define LEFT(a) (((a).tail-(a).head-1)&(TTY_BUF_SIZE-1)) +#define LAST(a) ((a).buf[(TTY_BUF_SIZE-1)&((a).head-1)]) +#define FULL(a) (!LEFT(a)) +#define CHARS(a) (((a).head-(a).tail)&(TTY_BUF_SIZE-1)) +#define GETCH(queue,c) \ +(void)({c=(queue).buf[(queue).tail];INC((queue).tail);}) +#define PUTCH(c,queue) \ +(void)({(queue).buf[(queue).head]=(c);INC((queue).head);}) + +#define INTR_CHAR(tty) ((tty)->termios.c_cc[VINTR]) +#define QUIT_CHAR(tty) ((tty)->termios.c_cc[VQUIT]) +#define ERASE_CHAR(tty) ((tty)->termios.c_cc[VERASE]) +#define KILL_CHAR(tty) ((tty)->termios.c_cc[VKILL]) +#define EOF_CHAR(tty) ((tty)->termios.c_cc[VEOF]) +#define START_CHAR(tty) ((tty)->termios.c_cc[VSTART]) +#define STOP_CHAR(tty) ((tty)->termios.c_cc[VSTOP]) +#define SUSPEND_CHAR(tty) ((tty)->termios.c_cc[VSUSP]) + +struct tty_struct { + struct termios termios; + int pgrp; + int stopped; + void (*write)(struct tty_struct * tty); + struct tty_queue read_q; + struct tty_queue write_q; + struct tty_queue secondary; + }; + +extern struct tty_struct tty_table[]; + +/* intr=^C quit=^| erase=del kill=^U + eof=^D vtime=\0 vmin=\1 sxtc=\0 + start=^Q stop=^S susp=^Z eol=\0 + reprint=^R discard=^U werase=^W lnext=^V + eol2=\0 +*/ +#define INIT_C_CC "\003\034\177\025\004\0\1\0\021\023\032\0\022\017\027\026\0" + +void rs_init(void); +void con_init(void); +void tty_init(void); + +int tty_read(unsigned c, char * buf, int n); +int tty_write(unsigned c, char * buf, int n); + +void rs_write(struct tty_struct * tty); +void con_write(struct tty_struct * tty); + +void copy_to_cooked(struct tty_struct * tty); + +#endif diff --git a/linux-0.11-lab/1/linux/include/new.h b/linux-0.11-lab/1/linux/include/new.h new file mode 100755 index 0000000..c508915 --- /dev/null +++ b/linux-0.11-lab/1/linux/include/new.h @@ -0,0 +1,30 @@ +#ifndef _NEW_H +#define _NEW_H + +#include + +struct linux_dirent { + long d_ino; + off_t d_off; + unsigned short d_reclen; + char d_name[14]; +}; + +/* Return value of `mmap' in case of an error. */ +#define MAP_FAILED ((void *) -1) + +#define PROT_READ 0x1 /* page can be read */ +#define PROT_WRITE 0x2 /* page can be written */ +#define PROT_EXEC 0x4 /* page can be executed */ +#define PROT_SEM 0x8 /* page may be used for atomic ops */ +#define PROT_NONE 0x0 /* page can not be accessed */ + +/* compatibility flags */ +#define MAP_FILE 0 + +#define MAP_SHARED 0x01 /* Share changes */ +#define MAP_PRIVATE 0x02 /* Changes are private */ + +#define CLONE_VM 0x00000100 /* set if VM shared between processes */ + +#endif diff --git a/linux-0.11-lab/1/linux/include/signal.h b/linux-0.11-lab/1/linux/include/signal.h new file mode 100755 index 0000000..0eea9a3 --- /dev/null +++ b/linux-0.11-lab/1/linux/include/signal.h @@ -0,0 +1,68 @@ +#ifndef _SIGNAL_H +#define _SIGNAL_H + +#include + +typedef int sig_atomic_t; +typedef unsigned int sigset_t; /* 32 bits */ + +#define _NSIG 32 +#define NSIG _NSIG + +#define SIGHUP 1 +#define SIGINT 2 +#define SIGQUIT 3 +#define SIGILL 4 +#define SIGTRAP 5 +#define SIGABRT 6 +#define SIGIOT 6 +#define SIGUNUSED 7 +#define SIGFPE 8 +#define SIGKILL 9 +#define SIGUSR1 10 +#define SIGSEGV 11 +#define SIGUSR2 12 +#define SIGPIPE 13 +#define SIGALRM 14 +#define SIGTERM 15 +#define SIGSTKFLT 16 +#define SIGCHLD 17 +#define SIGCONT 18 +#define SIGSTOP 19 +#define SIGTSTP 20 +#define SIGTTIN 21 +#define SIGTTOU 22 + +/* Ok, I haven't implemented sigactions, but trying to keep headers POSIX */ +#define SA_NOCLDSTOP 1 +#define SA_NOMASK 0x40000000 +#define SA_ONESHOT 0x80000000 + +#define SIG_BLOCK 0 /* for blocking signals */ +#define SIG_UNBLOCK 1 /* for unblocking signals */ +#define SIG_SETMASK 2 /* for setting the signal mask */ + +#define SIG_DFL ((void (*)(int))0) /* default signal handling */ +#define SIG_IGN ((void (*)(int))1) /* ignore signal */ + +struct sigaction { + void (*sa_handler)(int); + sigset_t sa_mask; + int sa_flags; + void (*sa_restorer)(void); +}; + +void (*signal(int _sig, void (*_func)(int)))(int); +int raise(int sig); +int kill(pid_t pid, int sig); +int sigaddset(sigset_t *mask, int signo); +int sigdelset(sigset_t *mask, int signo); +int sigemptyset(sigset_t *mask); +int sigfillset(sigset_t *mask); +int sigismember(sigset_t *mask, int signo); /* 1 - is, 0 - not, -1 error */ +int sigpending(sigset_t *set); +int sigprocmask(int how, sigset_t *set, sigset_t *oldset); +int sigsuspend(sigset_t *sigmask); +int sigaction(int sig, struct sigaction *act, struct sigaction *oldact); + +#endif /* _SIGNAL_H */ diff --git a/linux-0.11-lab/1/linux/include/stdarg.h b/linux-0.11-lab/1/linux/include/stdarg.h new file mode 100755 index 0000000..fd79ec0 --- /dev/null +++ b/linux-0.11-lab/1/linux/include/stdarg.h @@ -0,0 +1,28 @@ +#ifndef _STDARG_H +#define _STDARG_H + +typedef char *va_list; + +/* Amount of space required in an argument list for an arg of type TYPE. + TYPE may alternatively be an expression whose type is used. */ + +#define __va_rounded_size(TYPE) \ + (((sizeof (TYPE) + sizeof (int) - 1) / sizeof (int)) * sizeof (int)) + +#ifndef __sparc__ +#define va_start(AP, LASTARG) \ + (AP = ((char *) &(LASTARG) + __va_rounded_size (LASTARG))) +#else +#define va_start(AP, LASTARG) \ + (__builtin_saveregs (), \ + AP = ((char *) &(LASTARG) + __va_rounded_size (LASTARG))) +#endif + +void va_end (va_list); /* Defined in gnulib */ +#define va_end(AP) + +#define va_arg(AP, TYPE) \ + (AP += __va_rounded_size (TYPE), \ + *((TYPE *) (AP - __va_rounded_size (TYPE)))) + +#endif /* _STDARG_H */ diff --git a/linux-0.11-lab/1/linux/include/stddef.h b/linux-0.11-lab/1/linux/include/stddef.h new file mode 100755 index 0000000..97f72ff --- /dev/null +++ b/linux-0.11-lab/1/linux/include/stddef.h @@ -0,0 +1,19 @@ +#ifndef _STDDEF_H +#define _STDDEF_H + +#ifndef _PTRDIFF_T +#define _PTRDIFF_T +typedef long ptrdiff_t; +#endif + +#ifndef _SIZE_T +#define _SIZE_T +typedef unsigned long size_t; +#endif + +#undef NULL +#define NULL ((void *)0) + +#define offsetof(TYPE, MEMBER) ((size_t) &((TYPE *)0)->MEMBER) + +#endif diff --git a/linux-0.11-lab/1/linux/include/string.h b/linux-0.11-lab/1/linux/include/string.h new file mode 100755 index 0000000..48b91e5 --- /dev/null +++ b/linux-0.11-lab/1/linux/include/string.h @@ -0,0 +1,405 @@ +#ifndef _STRING_H_ +#define _STRING_H_ + +#ifndef NULL +#define NULL ((void *) 0) +#endif + +#ifndef _SIZE_T +#define _SIZE_T +typedef unsigned int size_t; +#endif + +extern char * strerror(int errno); + +/* + * This string-include defines all string functions as inline + * functions. Use gcc. It also assumes ds=es=data space, this should be + * normal. Most of the string-functions are rather heavily hand-optimized, + * see especially strtok,strstr,str[c]spn. They should work, but are not + * very easy to understand. Everything is done entirely within the register + * set, making the functions fast and clean. String instructions have been + * used through-out, making for "slightly" unclear code :-) + * + * (C) 1991 Linus Torvalds + */ + +extern inline char * strcpy(char * dest,const char *src) +{ +__asm__("cld\n" + "1:\tlodsb\n\t" + "stosb\n\t" + "testb %%al,%%al\n\t" + "jne 1b" + ::"S" (src),"D" (dest)); +return dest; +} + +extern inline char * strncpy(char * dest,const char *src,int count) +{ +__asm__("cld\n" + "1:\tdecl %2\n\t" + "js 2f\n\t" + "lodsb\n\t" + "stosb\n\t" + "testb %%al,%%al\n\t" + "jne 1b\n\t" + "rep\n\t" + "stosb\n" + "2:" + ::"S" (src),"D" (dest),"c" (count)); +return dest; +} + +extern inline char * strcat(char * dest,const char * src) +{ +__asm__("cld\n\t" + "repne\n\t" + "scasb\n\t" + "decl %1\n" + "1:\tlodsb\n\t" + "stosb\n\t" + "testb %%al,%%al\n\t" + "jne 1b" + ::"S" (src),"D" (dest),"a" (0),"c" (0xffffffff)); +return dest; +} + +extern inline char * strncat(char * dest,const char * src,int count) +{ +__asm__("cld\n\t" + "repne\n\t" + "scasb\n\t" + "decl %1\n\t" + "movl %4,%3\n" + "1:\tdecl %3\n\t" + "js 2f\n\t" + "lodsb\n\t" + "stosb\n\t" + "testb %%al,%%al\n\t" + "jne 1b\n" + "2:\txorl %2,%2\n\t" + "stosb" + ::"S" (src),"D" (dest),"a" (0),"c" (0xffffffff),"g" (count) + ); +return dest; +} + +extern inline int strcmp(const char * cs,const char * ct) +{ +register int __res __asm__("ax"); +__asm__("cld\n" + "1:\tlodsb\n\t" + "scasb\n\t" + "jne 2f\n\t" + "testb %%al,%%al\n\t" + "jne 1b\n\t" + "xorl %%eax,%%eax\n\t" + "jmp 3f\n" + "2:\tmovl $1,%%eax\n\t" + "jl 3f\n\t" + "negl %%eax\n" + "3:" + :"=a" (__res):"D" (cs),"S" (ct)); +return __res; +} + +extern inline int strncmp(const char * cs,const char * ct,int count) +{ +register int __res __asm__("ax"); +__asm__("cld\n" + "1:\tdecl %3\n\t" + "js 2f\n\t" + "lodsb\n\t" + "scasb\n\t" + "jne 3f\n\t" + "testb %%al,%%al\n\t" + "jne 1b\n" + "2:\txorl %%eax,%%eax\n\t" + "jmp 4f\n" + "3:\tmovl $1,%%eax\n\t" + "jl 4f\n\t" + "negl %%eax\n" + "4:" + :"=a" (__res):"D" (cs),"S" (ct),"c" (count)); +return __res; +} + +extern inline char * strchr(const char * s,char c) +{ +register char * __res __asm__("ax"); +__asm__("cld\n\t" + "movb %%al,%%ah\n" + "1:\tlodsb\n\t" + "cmpb %%ah,%%al\n\t" + "je 2f\n\t" + "testb %%al,%%al\n\t" + "jne 1b\n\t" + "movl $1,%1\n" + "2:\tmovl %1,%0\n\t" + "decl %0" + :"=a" (__res):"S" (s),"0" (c)); +return __res; +} + +extern inline char * strrchr(const char * s,char c) +{ +register char * __res __asm__("dx"); +__asm__("cld\n\t" + "movb %%al,%%ah\n" + "1:\tlodsb\n\t" + "cmpb %%ah,%%al\n\t" + "jne 2f\n\t" + "movl %%esi,%0\n\t" + "decl %0\n" + "2:\ttestb %%al,%%al\n\t" + "jne 1b" + :"=d" (__res):"0" (0),"S" (s),"a" (c)); +return __res; +} + +extern inline int strspn(const char * cs, const char * ct) +{ +register char * __res __asm__("si"); +__asm__("cld\n\t" + "movl %4,%%edi\n\t" + "repne\n\t" + "scasb\n\t" + "notl %%ecx\n\t" + "decl %%ecx\n\t" + "movl %%ecx,%%edx\n" + "1:\tlodsb\n\t" + "testb %%al,%%al\n\t" + "je 2f\n\t" + "movl %4,%%edi\n\t" + "movl %%edx,%%ecx\n\t" + "repne\n\t" + "scasb\n\t" + "je 1b\n" + "2:\tdecl %0" + :"=S" (__res):"a" (0),"c" (0xffffffff),"0" (cs),"g" (ct) + ); +return __res-cs; +} + +extern inline int strcspn(const char * cs, const char * ct) +{ +register char * __res __asm__("si"); +__asm__("cld\n\t" + "movl %4,%%edi\n\t" + "repne\n\t" + "scasb\n\t" + "notl %%ecx\n\t" + "decl %%ecx\n\t" + "movl %%ecx,%%edx\n" + "1:\tlodsb\n\t" + "testb %%al,%%al\n\t" + "je 2f\n\t" + "movl %4,%%edi\n\t" + "movl %%edx,%%ecx\n\t" + "repne\n\t" + "scasb\n\t" + "jne 1b\n" + "2:\tdecl %0" + :"=S" (__res):"a" (0),"c" (0xffffffff),"0" (cs),"g" (ct) + ); +return __res-cs; +} + +extern inline char * strpbrk(const char * cs,const char * ct) +{ +register char * __res __asm__("si"); +__asm__("cld\n\t" + "movl %4,%%edi\n\t" + "repne\n\t" + "scasb\n\t" + "notl %%ecx\n\t" + "decl %%ecx\n\t" + "movl %%ecx,%%edx\n" + "1:\tlodsb\n\t" + "testb %%al,%%al\n\t" + "je 2f\n\t" + "movl %4,%%edi\n\t" + "movl %%edx,%%ecx\n\t" + "repne\n\t" + "scasb\n\t" + "jne 1b\n\t" + "decl %0\n\t" + "jmp 3f\n" + "2:\txorl %0,%0\n" + "3:" + :"=S" (__res):"a" (0),"c" (0xffffffff),"0" (cs),"g" (ct) + ); +return __res; +} + +extern inline char * strstr(const char * cs,const char * ct) +{ +register char * __res __asm__("ax"); +__asm__("cld\n\t" \ + "movl %4,%%edi\n\t" + "repne\n\t" + "scasb\n\t" + "notl %%ecx\n\t" + "decl %%ecx\n\t" /* NOTE! This also sets Z if searchstring='' */ + "movl %%ecx,%%edx\n" + "1:\tmovl %4,%%edi\n\t" + "movl %%esi,%%eax\n\t" + "movl %%edx,%%ecx\n\t" + "repe\n\t" + "cmpsb\n\t" + "je 2f\n\t" /* also works for empty string, see above */ + "xchgl %%eax,%%esi\n\t" + "incl %%esi\n\t" + "cmpb $0,-1(%%eax)\n\t" + "jne 1b\n\t" + "xorl %%eax,%%eax\n\t" + "2:" + :"=a" (__res):"0" (0),"c" (0xffffffff),"S" (cs),"g" (ct) + ); +return __res; +} + +extern inline int strlen(const char * s) +{ +register int __res ; +__asm__("cld\n\t" + "repne\n\t" + "scasb\n\t" + "notl %0\n\t" + "decl %0" + :"=c" (__res):"D" (s),"a" (0),"0" (0xffffffff)); +return __res; +} + +extern char * ___strtok; + +extern inline char * strtok(char * s,const char * ct) +{ +register char * __res __asm__("si"); +__asm__("testl %1,%1\n\t" + "jne 1f\n\t" + "testl %0,%0\n\t" + "je 8f\n\t" + "movl %0,%1\n" + "1:\txorl %0,%0\n\t" + "movl $-1,%%ecx\n\t" + "xorl %%eax,%%eax\n\t" + "cld\n\t" + "movl %4,%%edi\n\t" + "repne\n\t" + "scasb\n\t" + "notl %%ecx\n\t" + "decl %%ecx\n\t" + "je 7f\n\t" /* empty delimeter-string */ + "movl %%ecx,%%edx\n" + "2:\tlodsb\n\t" + "testb %%al,%%al\n\t" + "je 7f\n\t" + "movl %4,%%edi\n\t" + "movl %%edx,%%ecx\n\t" + "repne\n\t" + "scasb\n\t" + "je 2b\n\t" + "decl %1\n\t" + "cmpb $0,(%1)\n\t" + "je 7f\n\t" + "movl %1,%0\n" + "3:\tlodsb\n\t" + "testb %%al,%%al\n\t" + "je 5f\n\t" + "movl %4,%%edi\n\t" + "movl %%edx,%%ecx\n\t" + "repne\n\t" + "scasb\n\t" + "jne 3b\n\t" + "decl %1\n\t" + "cmpb $0,(%1)\n\t" + "je 5f\n\t" + "movb $0,(%1)\n\t" + "incl %1\n\t" + "jmp 6f\n" + "5:\txorl %1,%1\n" + "6:\tcmpb $0,(%0)\n\t" + "jne 7f\n\t" + "xorl %0,%0\n" + "7:\ttestl %0,%0\n\t" + "jne 8f\n\t" + "movl %0,%1\n" + "8:" + :"=b" (__res),"=S" (___strtok) + :"0" (___strtok),"1" (s),"g" (ct) + ); +return __res; +} + +extern inline void * memcpy(void * dest,const void * src, int n) +{ +__asm__("cld\n\t" + "rep\n\t" + "movsb" + ::"c" (n),"S" (src),"D" (dest) + ); +return dest; +} + +extern inline void * memmove(void * dest,const void * src, int n) +{ +if (dest + +struct stat { + dev_t st_dev; + ino_t st_ino; + umode_t st_mode; + nlink_t st_nlink; + uid_t st_uid; + gid_t st_gid; + dev_t st_rdev; + off_t st_size; + time_t st_atime; + time_t st_mtime; + time_t st_ctime; +}; + +#define S_IFMT 00170000 +#define S_IFLNK 0120000 +#define S_IFREG 0100000 +#define S_IFBLK 0060000 +#define S_IFDIR 0040000 +#define S_IFCHR 0020000 +#define S_IFIFO 0010000 +#define S_ISUID 0004000 +#define S_ISGID 0002000 +#define S_ISVTX 0001000 + +#define S_ISLNK(m) (((m) & S_IFMT) == S_IFLNK) +#define S_ISREG(m) (((m) & S_IFMT) == S_IFREG) +#define S_ISDIR(m) (((m) & S_IFMT) == S_IFDIR) +#define S_ISCHR(m) (((m) & S_IFMT) == S_IFCHR) +#define S_ISBLK(m) (((m) & S_IFMT) == S_IFBLK) +#define S_ISFIFO(m) (((m) & S_IFMT) == S_IFIFO) + +#define S_IRWXU 00700 +#define S_IRUSR 00400 +#define S_IWUSR 00200 +#define S_IXUSR 00100 + +#define S_IRWXG 00070 +#define S_IRGRP 00040 +#define S_IWGRP 00020 +#define S_IXGRP 00010 + +#define S_IRWXO 00007 +#define S_IROTH 00004 +#define S_IWOTH 00002 +#define S_IXOTH 00001 + +extern int chmod(const char *_path, mode_t mode); +extern int fstat(int fildes, struct stat *stat_buf); +extern int mkdir(const char *_path, mode_t mode); +extern int mkfifo(const char *_path, mode_t mode); +extern int stat(const char *filename, struct stat *stat_buf); +extern mode_t umask(mode_t mask); + +#endif diff --git a/linux-0.11-lab/1/linux/include/sys/times.h b/linux-0.11-lab/1/linux/include/sys/times.h new file mode 100755 index 0000000..68d5bfb --- /dev/null +++ b/linux-0.11-lab/1/linux/include/sys/times.h @@ -0,0 +1,15 @@ +#ifndef _TIMES_H +#define _TIMES_H + +#include + +struct tms { + time_t tms_utime; + time_t tms_stime; + time_t tms_cutime; + time_t tms_cstime; +}; + +extern time_t times(struct tms * tp); + +#endif diff --git a/linux-0.11-lab/1/linux/include/sys/types.h b/linux-0.11-lab/1/linux/include/sys/types.h new file mode 100755 index 0000000..557aa31 --- /dev/null +++ b/linux-0.11-lab/1/linux/include/sys/types.h @@ -0,0 +1,46 @@ +#ifndef _SYS_TYPES_H +#define _SYS_TYPES_H + +#ifndef _SIZE_T +#define _SIZE_T +typedef unsigned int size_t; +#endif + +#ifndef _TIME_T +#define _TIME_T +typedef long time_t; +#endif + +#ifndef _PTRDIFF_T +#define _PTRDIFF_T +typedef long ptrdiff_t; +#endif + +#ifndef NULL +#define NULL ((void *) 0) +#endif + +typedef int pid_t; +typedef unsigned short uid_t; +typedef unsigned char gid_t; +typedef unsigned short dev_t; +typedef unsigned short ino_t; +typedef unsigned short mode_t; +typedef unsigned short umode_t; +typedef unsigned char nlink_t; +typedef int daddr_t; +typedef long off_t; +typedef unsigned char u_char; +typedef unsigned short ushort; + +typedef struct { int quot,rem; } div_t; +typedef struct { long quot,rem; } ldiv_t; + +struct ustat { + daddr_t f_tfree; + ino_t f_tinode; + char f_fname[6]; + char f_fpack[6]; +}; + +#endif diff --git a/linux-0.11-lab/1/linux/include/sys/utsname.h b/linux-0.11-lab/1/linux/include/sys/utsname.h new file mode 100755 index 0000000..0a1c5a0 --- /dev/null +++ b/linux-0.11-lab/1/linux/include/sys/utsname.h @@ -0,0 +1,16 @@ +#ifndef _SYS_UTSNAME_H +#define _SYS_UTSNAME_H + +#include + +struct utsname { + char sysname[9]; + char nodename[9]; + char release[9]; + char version[9]; + char machine[9]; +}; + +extern int uname(struct utsname * utsbuf); + +#endif diff --git a/linux-0.11-lab/1/linux/include/sys/wait.h b/linux-0.11-lab/1/linux/include/sys/wait.h new file mode 100755 index 0000000..53190c2 --- /dev/null +++ b/linux-0.11-lab/1/linux/include/sys/wait.h @@ -0,0 +1,23 @@ +#ifndef _SYS_WAIT_H +#define _SYS_WAIT_H + +#include + +#define _LOW(v) ( (v) & 0377) +#define _HIGH(v) ( ((v) >> 8) & 0377) + +/* options for waitpid, WUNTRACED not supported */ +#define WNOHANG 1 +#define WUNTRACED 2 + +#define WIFEXITED(s) (!((s)&0xFF) +#define WIFSTOPPED(s) (((s)&0xFF)==0x7F) +#define WEXITSTATUS(s) (((s)>>8)&0xFF) +#define WTERMSIG(s) ((s)&0x7F) +#define WSTOPSIG(s) (((s)>>8)&0xFF) +#define WIFSIGNALED(s) (((unsigned int)(s)-1 & 0xFFFF) < 0xFF) + +pid_t wait(int *stat_loc); +pid_t waitpid(pid_t pid, int *stat_loc, int options); + +#endif diff --git a/linux-0.11-lab/1/linux/include/termios.h b/linux-0.11-lab/1/linux/include/termios.h new file mode 100755 index 0000000..2b7b913 --- /dev/null +++ b/linux-0.11-lab/1/linux/include/termios.h @@ -0,0 +1,228 @@ +#ifndef _TERMIOS_H +#define _TERMIOS_H + +#define TTY_BUF_SIZE 1024 + +/* 0x54 is just a magic number to make these relatively uniqe ('T') */ + +#define TCGETS 0x5401 +#define TCSETS 0x5402 +#define TCSETSW 0x5403 +#define TCSETSF 0x5404 +#define TCGETA 0x5405 +#define TCSETA 0x5406 +#define TCSETAW 0x5407 +#define TCSETAF 0x5408 +#define TCSBRK 0x5409 +#define TCXONC 0x540A +#define TCFLSH 0x540B +#define TIOCEXCL 0x540C +#define TIOCNXCL 0x540D +#define TIOCSCTTY 0x540E +#define TIOCGPGRP 0x540F +#define TIOCSPGRP 0x5410 +#define TIOCOUTQ 0x5411 +#define TIOCSTI 0x5412 +#define TIOCGWINSZ 0x5413 +#define TIOCSWINSZ 0x5414 +#define TIOCMGET 0x5415 +#define TIOCMBIS 0x5416 +#define TIOCMBIC 0x5417 +#define TIOCMSET 0x5418 +#define TIOCGSOFTCAR 0x5419 +#define TIOCSSOFTCAR 0x541A +#define TIOCINQ 0x541B + +struct winsize { + unsigned short ws_row; + unsigned short ws_col; + unsigned short ws_xpixel; + unsigned short ws_ypixel; +}; + +#define NCC 8 +struct termio { + unsigned short c_iflag; /* input mode flags */ + unsigned short c_oflag; /* output mode flags */ + unsigned short c_cflag; /* control mode flags */ + unsigned short c_lflag; /* local mode flags */ + unsigned char c_line; /* line discipline */ + unsigned char c_cc[NCC]; /* control characters */ +}; + +#define NCCS 17 +struct termios { + unsigned long c_iflag; /* input mode flags */ + unsigned long c_oflag; /* output mode flags */ + unsigned long c_cflag; /* control mode flags */ + unsigned long c_lflag; /* local mode flags */ + unsigned char c_line; /* line discipline */ + unsigned char c_cc[NCCS]; /* control characters */ +}; + +/* c_cc characters */ +#define VINTR 0 +#define VQUIT 1 +#define VERASE 2 +#define VKILL 3 +#define VEOF 4 +#define VTIME 5 +#define VMIN 6 +#define VSWTC 7 +#define VSTART 8 +#define VSTOP 9 +#define VSUSP 10 +#define VEOL 11 +#define VREPRINT 12 +#define VDISCARD 13 +#define VWERASE 14 +#define VLNEXT 15 +#define VEOL2 16 + +/* c_iflag bits */ +#define IGNBRK 0000001 +#define BRKINT 0000002 +#define IGNPAR 0000004 +#define PARMRK 0000010 +#define INPCK 0000020 +#define ISTRIP 0000040 +#define INLCR 0000100 +#define IGNCR 0000200 +#define ICRNL 0000400 +#define IUCLC 0001000 +#define IXON 0002000 +#define IXANY 0004000 +#define IXOFF 0010000 +#define IMAXBEL 0020000 + +/* c_oflag bits */ +#define OPOST 0000001 +#define OLCUC 0000002 +#define ONLCR 0000004 +#define OCRNL 0000010 +#define ONOCR 0000020 +#define ONLRET 0000040 +#define OFILL 0000100 +#define OFDEL 0000200 +#define NLDLY 0000400 +#define NL0 0000000 +#define NL1 0000400 +#define CRDLY 0003000 +#define CR0 0000000 +#define CR1 0001000 +#define CR2 0002000 +#define CR3 0003000 +#define TABDLY 0014000 +#define TAB0 0000000 +#define TAB1 0004000 +#define TAB2 0010000 +#define TAB3 0014000 +#define XTABS 0014000 +#define BSDLY 0020000 +#define BS0 0000000 +#define BS1 0020000 +#define VTDLY 0040000 +#define VT0 0000000 +#define VT1 0040000 +#define FFDLY 0040000 +#define FF0 0000000 +#define FF1 0040000 + +/* c_cflag bit meaning */ +#define CBAUD 0000017 +#define B0 0000000 /* hang up */ +#define B50 0000001 +#define B75 0000002 +#define B110 0000003 +#define B134 0000004 +#define B150 0000005 +#define B200 0000006 +#define B300 0000007 +#define B600 0000010 +#define B1200 0000011 +#define B1800 0000012 +#define B2400 0000013 +#define B4800 0000014 +#define B9600 0000015 +#define B19200 0000016 +#define B38400 0000017 +#define EXTA B19200 +#define EXTB B38400 +#define CSIZE 0000060 +#define CS5 0000000 +#define CS6 0000020 +#define CS7 0000040 +#define CS8 0000060 +#define CSTOPB 0000100 +#define CREAD 0000200 +#define CPARENB 0000400 +#define CPARODD 0001000 +#define HUPCL 0002000 +#define CLOCAL 0004000 +#define CIBAUD 03600000 /* input baud rate (not used) */ +#define CRTSCTS 020000000000 /* flow control */ + +#define PARENB CPARENB +#define PARODD CPARODD + +/* c_lflag bits */ +#define ISIG 0000001 +#define ICANON 0000002 +#define XCASE 0000004 +#define ECHO 0000010 +#define ECHOE 0000020 +#define ECHOK 0000040 +#define ECHONL 0000100 +#define NOFLSH 0000200 +#define TOSTOP 0000400 +#define ECHOCTL 0001000 +#define ECHOPRT 0002000 +#define ECHOKE 0004000 +#define FLUSHO 0010000 +#define PENDIN 0040000 +#define IEXTEN 0100000 + +/* modem lines */ +#define TIOCM_LE 0x001 +#define TIOCM_DTR 0x002 +#define TIOCM_RTS 0x004 +#define TIOCM_ST 0x008 +#define TIOCM_SR 0x010 +#define TIOCM_CTS 0x020 +#define TIOCM_CAR 0x040 +#define TIOCM_RNG 0x080 +#define TIOCM_DSR 0x100 +#define TIOCM_CD TIOCM_CAR +#define TIOCM_RI TIOCM_RNG + +/* tcflow() and TCXONC use these */ +#define TCOOFF 0 +#define TCOON 1 +#define TCIOFF 2 +#define TCION 3 + +/* tcflush() and TCFLSH use these */ +#define TCIFLUSH 0 +#define TCOFLUSH 1 +#define TCIOFLUSH 2 + +/* tcsetattr uses these */ +#define TCSANOW 0 +#define TCSADRAIN 1 +#define TCSAFLUSH 2 + +typedef int speed_t; + +extern speed_t cfgetispeed(struct termios *termios_p); +extern speed_t cfgetospeed(struct termios *termios_p); +extern int cfsetispeed(struct termios *termios_p, speed_t speed); +extern int cfsetospeed(struct termios *termios_p, speed_t speed); +extern int tcdrain(int fildes); +extern int tcflow(int fildes, int action); +extern int tcflush(int fildes, int queue_selector); +extern int tcgetattr(int fildes, struct termios *termios_p); +extern int tcsendbreak(int fildes, int duration); +extern int tcsetattr(int fildes, int optional_actions, + struct termios *termios_p); + +#endif diff --git a/linux-0.11-lab/1/linux/include/time.h b/linux-0.11-lab/1/linux/include/time.h new file mode 100755 index 0000000..d0a765d --- /dev/null +++ b/linux-0.11-lab/1/linux/include/time.h @@ -0,0 +1,42 @@ +#ifndef _TIME_H +#define _TIME_H + +#ifndef _TIME_T +#define _TIME_T +typedef long time_t; +#endif + +#ifndef _SIZE_T +#define _SIZE_T +typedef unsigned int size_t; +#endif + +#define CLOCKS_PER_SEC 100 + +typedef long clock_t; + +struct tm { + int tm_sec; + int tm_min; + int tm_hour; + int tm_mday; + int tm_mon; + int tm_year; + int tm_wday; + int tm_yday; + int tm_isdst; +}; + +clock_t clock(void); +time_t time(time_t * tp); +double difftime(time_t time2, time_t time1); +time_t mktime(struct tm * tp); + +char * asctime(const struct tm * tp); +char * ctime(const time_t * tp); +struct tm * gmtime(const time_t *tp); +struct tm *localtime(const time_t * tp); +size_t strftime(char * s, size_t smax, const char * fmt, const struct tm * tp); +void tzset(void); + +#endif diff --git a/linux-0.11-lab/1/linux/include/unistd.h b/linux-0.11-lab/1/linux/include/unistd.h new file mode 100755 index 0000000..61dd3fe --- /dev/null +++ b/linux-0.11-lab/1/linux/include/unistd.h @@ -0,0 +1,278 @@ +#ifndef _UNISTD_H +#define _UNISTD_H + +/* ok, this may be a joke, but I'm working on it */ +#define _POSIX_VERSION 198808L + +#define _POSIX_CHOWN_RESTRICTED /* only root can do a chown (I think..) */ +#define _POSIX_NO_TRUNC /* no pathname truncation (but see in kernel) */ +#define _POSIX_VDISABLE '\0' /* character to disable things like ^C */ +/*#define _POSIX_SAVED_IDS */ /* we'll get to this yet */ +/*#define _POSIX_JOB_CONTROL */ /* we aren't there quite yet. Soon hopefully */ + +#define STDIN_FILENO 0 +#define STDOUT_FILENO 1 +#define STDERR_FILENO 2 + +#ifndef NULL +#define NULL ((void *)0) +#endif + +/* access */ +#define F_OK 0 +#define X_OK 1 +#define W_OK 2 +#define R_OK 4 + +/* lseek */ +#define SEEK_SET 0 +#define SEEK_CUR 1 +#define SEEK_END 2 + +/* _SC stands for System Configuration. We don't use them much */ +#define _SC_ARG_MAX 1 +#define _SC_CHILD_MAX 2 +#define _SC_CLOCKS_PER_SEC 3 +#define _SC_NGROUPS_MAX 4 +#define _SC_OPEN_MAX 5 +#define _SC_JOB_CONTROL 6 +#define _SC_SAVED_IDS 7 +#define _SC_VERSION 8 + +/* more (possibly) configurable things - now pathnames */ +#define _PC_LINK_MAX 1 +#define _PC_MAX_CANON 2 +#define _PC_MAX_INPUT 3 +#define _PC_NAME_MAX 4 +#define _PC_PATH_MAX 5 +#define _PC_PIPE_BUF 6 +#define _PC_NO_TRUNC 7 +#define _PC_VDISABLE 8 +#define _PC_CHOWN_RESTRICTED 9 + +#include +#include +#include +#include + +#ifdef __LIBRARY__ + +#define __NR_setup 0 /* used only by init, to get system going */ +#define __NR_exit 1 +#define __NR_fork 2 +#define __NR_read 3 +#define __NR_write 4 +#define __NR_open 5 +#define __NR_close 6 +#define __NR_waitpid 7 +#define __NR_creat 8 +#define __NR_link 9 +#define __NR_unlink 10 +#define __NR_execve 11 +#define __NR_chdir 12 +#define __NR_time 13 +#define __NR_mknod 14 +#define __NR_chmod 15 +#define __NR_chown 16 +#define __NR_break 17 +#define __NR_stat 18 +#define __NR_lseek 19 +#define __NR_getpid 20 +#define __NR_mount 21 +#define __NR_umount 22 +#define __NR_setuid 23 +#define __NR_getuid 24 +#define __NR_stime 25 +#define __NR_ptrace 26 +#define __NR_alarm 27 +#define __NR_fstat 28 +#define __NR_pause 29 +#define __NR_utime 30 +#define __NR_stty 31 +#define __NR_gtty 32 +#define __NR_access 33 +#define __NR_nice 34 +#define __NR_ftime 35 +#define __NR_sync 36 +#define __NR_kill 37 +#define __NR_rename 38 +#define __NR_mkdir 39 +#define __NR_rmdir 40 +#define __NR_dup 41 +#define __NR_pipe 42 +#define __NR_times 43 +#define __NR_prof 44 +#define __NR_brk 45 +#define __NR_setgid 46 +#define __NR_getgid 47 +#define __NR_signal 48 +#define __NR_geteuid 49 +#define __NR_getegid 50 +#define __NR_acct 51 +#define __NR_phys 52 +#define __NR_lock 53 +#define __NR_ioctl 54 +#define __NR_fcntl 55 +#define __NR_mpx 56 +#define __NR_setpgid 57 +#define __NR_ulimit 58 +#define __NR_uname 59 +#define __NR_umask 60 +#define __NR_chroot 61 +#define __NR_ustat 62 +#define __NR_dup2 63 +#define __NR_getppid 64 +#define __NR_getpgrp 65 +#define __NR_setsid 66 +#define __NR_sigaction 67 +#define __NR_sgetmask 68 +#define __NR_ssetmask 69 +#define __NR_setreuid 70 +#define __NR_setregid 71 +#define __NR_sigsuspend 72 +#define __NR_sigpending 73 +#define __NR_sethostname 74 +#define __NR_setrlimit 75 +#define __NR_getrlimit 76 +#define __NR_getrusage 77 +#define __NR_gettimeofday 78 +#define __NR_settimeofday 79 +#define __NR_getgroups 80 +#define __NR_setgroups 81 +#define __NR_select 82 +#define __NR_symlink 83 +#define __NR_lstat 84 +#define __NR_readlink 85 +#define __NR_uselib 86 +#define __NR_execve2 87 +#define __NR_getdents 88 +#define __NR_pipe2 89 +#define __NR_sleep 90 +#define __NR_getcwd 91 +#define __NR_mmap 92 +#define __NR_munmap 93 +#define __NR_clone 94 + +#define _syscall0(type,name) \ +type name(void) \ +{ \ +long __res; \ +__asm__ volatile ("int $0x80" \ + : "=a" (__res) \ + : "0" (__NR_##name)); \ +if (__res >= 0) \ + return (type) __res; \ +errno = -__res; \ +return -1; \ +} + +#define _syscall1(type,name,atype,a) \ +type name(atype a) \ +{ \ +long __res; \ +__asm__ volatile ("int $0x80" \ + : "=a" (__res) \ + : "0" (__NR_##name),"b" ((long)(a))); \ +if (__res >= 0) \ + return (type) __res; \ +errno = -__res; \ +return -1; \ +} + +#define _syscall2(type,name,atype,a,btype,b) \ +type name(atype a,btype b) \ +{ \ +long __res; \ +__asm__ volatile ("int $0x80" \ + : "=a" (__res) \ + : "0" (__NR_##name),"b" ((long)(a)),"c" ((long)(b))); \ +if (__res >= 0) \ + return (type) __res; \ +errno = -__res; \ +return -1; \ +} + +#define _syscall3(type,name,atype,a,btype,b,ctype,c) \ +type name(atype a,btype b,ctype c) \ +{ \ +long __res; \ +__asm__ volatile ("int $0x80" \ + : "=a" (__res) \ + : "0" (__NR_##name),"b" ((long)(a)),"c" ((long)(b)),"d" ((long)(c))); \ +if (__res>=0) \ + return (type) __res; \ +errno=-__res; \ +return -1; \ +} + +#endif /* __LIBRARY__ */ + +extern int errno; + +int access(const char * filename, mode_t mode); +int acct(const char * filename); +int alarm(int sec); +int brk(void * end_data_segment); +void * sbrk(ptrdiff_t increment); +int chdir(const char * filename); +int chmod(const char * filename, mode_t mode); +int chown(const char * filename, uid_t owner, gid_t group); +int chroot(const char * filename); +int close(int fildes); +int creat(const char * filename, mode_t mode); +int dup(int fildes); +int execve(const char * filename, char ** argv, char ** envp); +int execv(const char * pathname, char ** argv); +int execvp(const char * file, char ** argv); +int execl(const char * pathname, char * arg0, ...); +int execlp(const char * file, char * arg0, ...); +int execle(const char * pathname, char * arg0, ...); +volatile void exit(int status); +volatile void _exit(int status); +int fcntl(int fildes, int cmd, ...); +int fork(void); +int getpid(void); +int getuid(void); +int geteuid(void); +int getgid(void); +int getegid(void); +int ioctl(int fildes, int cmd, ...); +int kill(pid_t pid, int signal); +int link(const char * filename1, const char * filename2); +int lseek(int fildes, off_t offset, int origin); +int mknod(const char * filename, mode_t mode, dev_t dev); +int mount(const char * specialfile, const char * dir, int rwflag); +int nice(int val); +int open(const char * filename, int flag, ...); +int pause(void); +int pipe(int * fildes); +int read(int fildes, char * buf, off_t count); +int setpgrp(void); +int setpgid(pid_t pid,pid_t pgid); +int setuid(uid_t uid); +int setgid(gid_t gid); +void (*signal(int sig, void (*fn)(int)))(int); +int stat(const char * filename, struct stat * stat_buf); +int fstat(int fildes, struct stat * stat_buf); +int stime(time_t * tptr); +int sync(void); +time_t time(time_t * tloc); +time_t times(struct tms * tbuf); +int ulimit(int cmd, long limit); +mode_t umask(mode_t mask); +int umount(const char * specialfile); +int uname(struct utsname * name); +int unlink(const char * filename); +int ustat(dev_t dev, struct ustat * ubuf); +int utime(const char * filename, struct utimbuf * times); +pid_t waitpid(pid_t pid,int * wait_stat,int options); +pid_t wait(int * wait_stat); +int write(int fildes, const char * buf, off_t count); +int dup2(int oldfd, int newfd); +int getppid(void); +pid_t getpgrp(void); +pid_t setsid(void); + +#define __always_inline inline __attribute__((always_inline)) + +#endif diff --git a/linux-0.11-lab/1/linux/include/utime.h b/linux-0.11-lab/1/linux/include/utime.h new file mode 100755 index 0000000..83f07c7 --- /dev/null +++ b/linux-0.11-lab/1/linux/include/utime.h @@ -0,0 +1,13 @@ +#ifndef _UTIME_H +#define _UTIME_H + +#include /* I know - shouldn't do this, but .. */ + +struct utimbuf { + time_t actime; + time_t modtime; +}; + +extern int utime(const char *filename, struct utimbuf *times); + +#endif diff --git a/linux-0.11-lab/1/linux/init/main.c b/linux-0.11-lab/1/linux/init/main.c new file mode 100644 index 0000000..bd86a68 --- /dev/null +++ b/linux-0.11-lab/1/linux/init/main.c @@ -0,0 +1,216 @@ +/* + * linux/init/main.c + * + * (C) 1991 Linus Torvalds + */ + +#define __LIBRARY__ +#include +#include + +/* + * we need this inline - forking from kernel space will result + * in NO COPY ON WRITE (!!!), until an execve is executed. This + * is no problem, but for the stack. This is handled by not letting + * main() use the stack at all after fork(). Thus, no function + * calls - which means inline code for fork too, as otherwise we + * would use the stack upon exit from 'fork()'. + * + * Actually only pause and fork are needed inline, so that there + * won't be any messing with the stack from main(), but we define + * some others too. + */ + +__always_inline _syscall0(int,fork) +__always_inline _syscall0(int,pause) +__always_inline _syscall1(int,setup,void *,BIOS) +__always_inline _syscall0(int,sync) + +#include +#include +#include +#include +#include + +#include +#include +#include +#include + +#include + +static char printbuf[1024]; + +extern int vsprintf(); +extern void init(void); +extern void blk_dev_init(void); +extern void chr_dev_init(void); +extern void hd_init(void); +extern void floppy_init(void); +extern void mem_init(long start, long end); +extern long rd_init(long mem_start, int length); +extern long kernel_mktime(struct tm * tm); +extern long startup_time; + +/* + * This is set up by the setup-routine at boot-time + */ +#define EXT_MEM_K (*(unsigned short *)0x90002) +#define DRIVE_INFO (*(struct drive_info *)0x90080) +#define ORIG_ROOT_DEV (*(unsigned short *)0x901FC) + +/* + * Yeah, yeah, it's ugly, but I cannot find how to do this correctly + * and this seems to work. I anybody has more info on the real-time + * clock I'd be interested. Most of this was trial and error, and some + * bios-listing reading. Urghh. + */ + +#define CMOS_READ(addr) ({ \ +outb_p(0x80|addr,0x70); \ +inb_p(0x71); \ +}) + +#define BCD_TO_BIN(val) ((val)=((val)&15) + ((val)>>4)*10) + +static void time_init(void) +{ + struct tm time; + + do { + time.tm_sec = CMOS_READ(0); + time.tm_min = CMOS_READ(2); + time.tm_hour = CMOS_READ(4); + time.tm_mday = CMOS_READ(7); + time.tm_mon = CMOS_READ(8); + time.tm_year = CMOS_READ(9); + } while (time.tm_sec != CMOS_READ(0)); + BCD_TO_BIN(time.tm_sec); + BCD_TO_BIN(time.tm_min); + BCD_TO_BIN(time.tm_hour); + BCD_TO_BIN(time.tm_mday); + BCD_TO_BIN(time.tm_mon); + BCD_TO_BIN(time.tm_year); + time.tm_mon--; + startup_time = kernel_mktime(&time); +} + +static long memory_end = 0; +static long buffer_memory_end = 0; +static long main_memory_start = 0; + +struct drive_info { char dummy[32]; } drive_info; + +void main(void) /* This really IS void, no error here. */ +{ /* The startup routine assumes (well, ...) this */ +/* + * Interrupts are still disabled. Do necessary setups, then + * enable them + */ + ROOT_DEV = ORIG_ROOT_DEV; + __asm__ volatile ("cld"); /* by wyj */ + drive_info = DRIVE_INFO; + memory_end = (1<<20) + (EXT_MEM_K<<10); + memory_end &= 0xfffff000; + if (memory_end > 16*1024*1024) + memory_end = 16*1024*1024; + if (memory_end > 12*1024*1024) + buffer_memory_end = 4*1024*1024; + else if (memory_end > 6*1024*1024) + buffer_memory_end = 2*1024*1024; + else + buffer_memory_end = 1*1024*1024; + main_memory_start = buffer_memory_end; +#ifdef RAMDISK + main_memory_start += rd_init(main_memory_start, RAMDISK*1024); +#endif + mem_init(main_memory_start,memory_end); + trap_init(); + blk_dev_init(); + chr_dev_init(); + tty_init(); + time_init(); + sched_init(); + buffer_init(buffer_memory_end); + hd_init(); + floppy_init(); + sti(); + move_to_user_mode(); + if (!fork()) { /* we count on this going ok */ + init(); + } +/* + * NOTE!! For any other task 'pause()' would mean we have to get a + * signal to awaken, but task0 is the sole exception (see 'schedule()') + * as task 0 gets activated at every idle moment (when no other tasks + * can run). For task0 'pause()' just means we go check if some other + * task can run, and if not we return here. + */ + for(;;) pause(); +} + +static int printf(const char *fmt, ...) +{ + va_list args; + int i; + + va_start(args, fmt); + write(1,printbuf,i=vsprintf(printbuf, fmt, args)); + va_end(args); + return i; +} + +static char * argv_rc[] = { "/bin/sh", NULL }; +static char * envp_rc[] = { "HOME=/", NULL, NULL }; + +static char * argv[] = { "-/bin/sh",NULL }; +static char * envp[] = { "HOME=/usr/root", NULL, NULL }; + +void init(void) +{ + int pid,i; + + setup((void *) &drive_info); + (void) open("/dev/tty0",O_RDWR,0); + (void) dup(0); + (void) dup(0); + printf("%d buffers = %d bytes buffer space\n\r",NR_BUFFERS, + NR_BUFFERS*BLOCK_SIZE); + printf("Free mem: %d bytes\n\r",memory_end-main_memory_start); + if (!(pid=fork())) { + close(0); + if (open("/etc/rc",O_RDONLY,0)) + _exit(1); + execve("/bin/sh",argv_rc,envp_rc); + _exit(2); + } + if (pid>0) + while (pid != wait(&i)) + /* nothing */; + while (1) { + if ((pid=fork())<0) { + printf("Fork failed in init\r\n"); + continue; + } + if (!pid) { + close(0);close(1);close(2); + setsid(); + (void) open("/dev/tty0",O_RDWR,0); + (void) dup(0); + (void) dup(0); + _exit(execve("/bin/sh",argv,envp)); + } + while (1) + if (pid == wait(&i)) + break; + printf("\n\rchild %d died with code %04x\n\r",pid,i); + sync(); + } + _exit(0); /* NOTE! _exit, not exit() */ +} + +void print_nr(int sid) +{ + if (sid > 86) + printk(" --syscall: sid=%d, pid=%d\n", sid, current->pid); +} diff --git a/linux-0.11-lab/1/linux/init/main.c.rej b/linux-0.11-lab/1/linux/init/main.c.rej new file mode 100644 index 0000000..375d6cd --- /dev/null +++ b/linux-0.11-lab/1/linux/init/main.c.rej @@ -0,0 +1,12 @@ +--- init/main.c 2016-08-08 09:40:13.000000000 +0800 ++++ init/main.c 2021-07-06 14:16:56.000000000 +0800 +@@ -208,3 +208,9 @@ + } + _exit(0); /* NOTE! _exit, not exit() */ + } ++ ++void print_nr(int sid) ++{ ++ if (sid > 86) ++ printk(" --syscall: sid=%d, pid=%d\n", sid, current->pid); ++} diff --git a/linux-0.11-lab/1/linux/init/main.o b/linux-0.11-lab/1/linux/init/main.o new file mode 100644 index 0000000000000000000000000000000000000000..76004d9171df07e86db5b0a0639f46502a8b6448 GIT binary patch literal 12220 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 tmp_make + (for i in *.c;do echo -n `echo $$i | sed 's,\.c,\.s,'`" "; \ + $(CPP) -M $$i;done) >> tmp_make + cp tmp_make Makefile + (cd chr_drv; make dep) + (cd blk_drv; make dep) + +### Dependencies: +exit.s exit.o : exit.c ../include/errno.h ../include/signal.h \ + ../include/sys/types.h ../include/sys/wait.h ../include/linux/sched.h \ + ../include/linux/head.h ../include/linux/fs.h ../include/linux/mm.h \ + ../include/linux/kernel.h ../include/linux/tty.h ../include/termios.h \ + ../include/asm/segment.h +fork.s fork.o : fork.c ../include/errno.h ../include/linux/sched.h \ + ../include/linux/head.h ../include/linux/fs.h ../include/sys/types.h \ + ../include/linux/mm.h ../include/signal.h ../include/linux/kernel.h \ + ../include/asm/segment.h ../include/asm/system.h +mktime.s mktime.o : mktime.c ../include/time.h +panic.s panic.o : panic.c ../include/linux/kernel.h ../include/linux/sched.h \ + ../include/linux/head.h ../include/linux/fs.h ../include/sys/types.h \ + ../include/linux/mm.h ../include/signal.h +printk.s printk.o : printk.c ../include/stdarg.h ../include/stddef.h \ + ../include/linux/kernel.h +sched.s sched.o : sched.c ../include/linux/sched.h ../include/linux/head.h \ + ../include/linux/fs.h ../include/sys/types.h ../include/linux/mm.h \ + ../include/signal.h ../include/linux/kernel.h ../include/linux/sys.h \ + ../include/linux/fdreg.h ../include/asm/system.h ../include/asm/io.h \ + ../include/asm/segment.h +signal.s signal.o : signal.c ../include/linux/sched.h ../include/linux/head.h \ + ../include/linux/fs.h ../include/sys/types.h ../include/linux/mm.h \ + ../include/signal.h ../include/linux/kernel.h ../include/asm/segment.h +sys.s sys.o : sys.c ../include/errno.h ../include/linux/sched.h \ + ../include/linux/head.h ../include/linux/fs.h ../include/sys/types.h \ + ../include/linux/mm.h ../include/signal.h ../include/linux/tty.h \ + ../include/termios.h ../include/linux/kernel.h ../include/asm/segment.h \ + ../include/sys/times.h ../include/sys/utsname.h +traps.s traps.o : traps.c ../include/string.h ../include/linux/head.h \ + ../include/linux/sched.h ../include/linux/fs.h ../include/sys/types.h \ + ../include/linux/mm.h ../include/signal.h ../include/linux/kernel.h \ + ../include/asm/system.h ../include/asm/segment.h ../include/asm/io.h +vsprintf.s vsprintf.o : vsprintf.c ../include/stdarg.h ../include/string.h diff --git a/linux-0.11-lab/1/linux/kernel/asm.o b/linux-0.11-lab/1/linux/kernel/asm.o new file mode 100644 index 0000000000000000000000000000000000000000..a89ec75e6e7dea54ae5b8d9b94ba28158b48a77f GIT binary patch literal 1740 zcma)+O=uHQ5XWcRv}sSZ2!7VKN<_gLTB@F^9;`i75B*Zxid{F^*K{@67k4+Yil|sH zrv|)<7wbhmD2RBl?IjkWde90*5b+=$0#XkiyeY()eY^2xiRgpv|Nnb$W-{}d&9$S) z`xHe1e<@H4e+Zz*gMDtmZfJlym?EDGMTQ55PMti_THiEx4rWIp9YYK2@F4#&zm)${ zdN=d3q3K?@?aYKaK6ZL^#Z6j!Eo4c^qL61o9t*iIN>a0?YOGAXEIm;+mxxDna!+$#}~zPg>(|qFzDh#3ziNdZhm7_Gt$HGtt5$ zJb2(2L6$5XS6!9gLaHZMBo4WC>dM&)G@;K)yrt}^F9miX@AvkI_oDBSxC{Lei4UOf zm-sOHL5cg&k4j8uHzb}wuS$Fw{k+6C(HA7XgML}!hv?r*yy$rny5~3eqzG`)Jgcaa zE(!kRc@m2M7T_NN{u$t~^pB$a<^Z<^_)viR13VsJBf!@Kd@I0Ua+O&Yx70Y-8Aw() zvWCvYA?PfYNr0I$z%ZR|;8|u(Ciz8(@r %eax + xchgl %ebx,(%esp) # &function <-> %ebx + pushl %ecx + pushl %edx + pushl %edi + pushl %esi + pushl %ebp + push %ds + push %es + push %fs + pushl %eax # error code + lea 44(%esp),%eax # offset + pushl %eax + movl $0x10,%eax + mov %ax,%ds + mov %ax,%es + mov %ax,%fs + call *%ebx + addl $8,%esp + pop %fs + pop %es + pop %ds + popl %ebp + popl %esi + popl %edi + popl %edx + popl %ecx + popl %ebx + popl %eax + iret + +invalid_TSS: + pushl $do_invalid_TSS + jmp error_code + +segment_not_present: + pushl $do_segment_not_present + jmp error_code + +stack_segment: + pushl $do_stack_segment + jmp error_code + +general_protection: + pushl $do_general_protection + jmp error_code + diff --git a/linux-0.11-lab/1/linux/kernel/blk_drv/Makefile b/linux-0.11-lab/1/linux/kernel/blk_drv/Makefile new file mode 100644 index 0000000..1fb57f9 --- /dev/null +++ b/linux-0.11-lab/1/linux/kernel/blk_drv/Makefile @@ -0,0 +1,58 @@ +# +# Makefile for the FREAX-kernel block device drivers. +# +# Note! Dependencies are done automagically by 'make dep', which also +# removes any old dependencies. DON'T put your own dependencies here +# unless it's something special (ie not a .c file). +# + +AR =ar +AS =as +LD =ld +LDFLAGS =-s -x +CC =gcc -march=i386 +CFLAGS =-w -g -fstrength-reduce -fomit-frame-pointer -mcld \ + -finline-functions -nostdinc -fno-stack-protector -I../../include +CPP =gcc -E -nostdinc -I../../include + +.c.s: + $(CC) $(CFLAGS) \ + -S -o $*.s $< +.s.o: + $(AS) -o $*.o $< +.c.o: + $(CC) $(CFLAGS) \ + -c -o $*.o $< + +OBJS = ll_rw_blk.o floppy.o hd.o ramdisk.o + +blk_drv.a: $(OBJS) + $(AR) rcs blk_drv.a $(OBJS) + sync + +clean: + rm -f core *.o *.a tmp_make + for i in *.c;do rm -f `basename $$i .c`.s;done + +dep: + sed '/\#\#\# Dependencies/q' < Makefile > tmp_make + (for i in *.c;do echo -n `echo $$i | sed 's,\.c,\.s,'`" "; \ + $(CPP) -M $$i;done) >> tmp_make + cp tmp_make Makefile + +### Dependencies: +floppy.s floppy.o : floppy.c ../../include/linux/sched.h ../../include/linux/head.h \ + ../../include/linux/fs.h ../../include/sys/types.h ../../include/linux/mm.h \ + ../../include/signal.h ../../include/linux/kernel.h \ + ../../include/linux/fdreg.h ../../include/asm/system.h \ + ../../include/asm/io.h ../../include/asm/segment.h blk.h +hd.s hd.o : hd.c ../../include/linux/config.h ../../include/linux/sched.h \ + ../../include/linux/head.h ../../include/linux/fs.h \ + ../../include/sys/types.h ../../include/linux/mm.h ../../include/signal.h \ + ../../include/linux/kernel.h ../../include/linux/hdreg.h \ + ../../include/asm/system.h ../../include/asm/io.h \ + ../../include/asm/segment.h blk.h +ll_rw_blk.s ll_rw_blk.o : ll_rw_blk.c ../../include/errno.h ../../include/linux/sched.h \ + ../../include/linux/head.h ../../include/linux/fs.h \ + ../../include/sys/types.h ../../include/linux/mm.h ../../include/signal.h \ + ../../include/linux/kernel.h ../../include/asm/system.h blk.h diff --git a/linux-0.11-lab/1/linux/kernel/blk_drv/blk.h b/linux-0.11-lab/1/linux/kernel/blk_drv/blk.h new file mode 100644 index 0000000..7a69b71 --- /dev/null +++ b/linux-0.11-lab/1/linux/kernel/blk_drv/blk.h @@ -0,0 +1,140 @@ +#ifndef _BLK_H +#define _BLK_H + +#define NR_BLK_DEV 7 +/* + * NR_REQUEST is the number of entries in the request-queue. + * NOTE that writes may use only the low 2/3 of these: reads + * take precedence. + * + * 32 seems to be a reasonable number: enough to get some benefit + * from the elevator-mechanism, but not so much as to lock a lot of + * buffers when they are in the queue. 64 seems to be too many (easily + * long pauses in reading when heavy writing/syncing is going on) + */ +#define NR_REQUEST 32 + +/* + * Ok, this is an expanded form so that we can use the same + * request for paging requests when that is implemented. In + * paging, 'bh' is NULL, and 'waiting' is used to wait for + * read/write completion. + */ +struct request { + int dev; /* -1 if no request */ + int cmd; /* READ or WRITE */ + int errors; + unsigned long sector; + unsigned long nr_sectors; + char * buffer; + struct task_struct * waiting; + struct buffer_head * bh; + struct request * next; +}; + +/* + * This is used in the elevator algorithm: Note that + * reads always go before writes. This is natural: reads + * are much more time-critical than writes. + */ +#define IN_ORDER(s1,s2) \ +((s1)->cmd<(s2)->cmd || (s1)->cmd==(s2)->cmd && \ +((s1)->dev < (s2)->dev || ((s1)->dev == (s2)->dev && \ +(s1)->sector < (s2)->sector))) + +struct blk_dev_struct { + void (*request_fn)(void); + struct request * current_request; +}; + +extern struct blk_dev_struct blk_dev[NR_BLK_DEV]; +extern struct request request[NR_REQUEST]; +extern struct task_struct * wait_for_request; + +#ifdef MAJOR_NR + +/* + * Add entries as needed. Currently the only block devices + * supported are hard-disks and floppies. + */ + +#if (MAJOR_NR == 1) +/* ram disk */ +#define DEVICE_NAME "ramdisk" +#define DEVICE_REQUEST do_rd_request +#define DEVICE_NR(device) ((device) & 7) +#define DEVICE_ON(device) +#define DEVICE_OFF(device) + +#elif (MAJOR_NR == 2) +/* floppy */ +#define DEVICE_NAME "floppy" +#define DEVICE_INTR do_floppy +#define DEVICE_REQUEST do_fd_request +#define DEVICE_NR(device) ((device) & 3) +#define DEVICE_ON(device) floppy_on(DEVICE_NR(device)) +#define DEVICE_OFF(device) floppy_off(DEVICE_NR(device)) + +#elif (MAJOR_NR == 3) +/* harddisk */ +#define DEVICE_NAME "harddisk" +#define DEVICE_INTR do_hd +#define DEVICE_REQUEST do_hd_request +#define DEVICE_NR(device) (MINOR(device)/5) +#define DEVICE_ON(device) +#define DEVICE_OFF(device) + +#elif (MAJOR_NR > 3) +/* unknown blk device */ +#error "unknown blk device" + +#endif + +#define CURRENT (blk_dev[MAJOR_NR].current_request) +#define CURRENT_DEV DEVICE_NR(CURRENT->dev) + +#ifdef DEVICE_INTR +void (*DEVICE_INTR)(void) = NULL; +#endif +static void (DEVICE_REQUEST)(void); + +static inline void unlock_buffer(struct buffer_head * bh) +{ + if (!bh->b_lock) + printk(DEVICE_NAME ": free buffer being unlocked\n"); + bh->b_lock=0; + wake_up(&bh->b_wait); +} + +static inline void end_request(int uptodate) +{ + DEVICE_OFF(CURRENT->dev); + if (CURRENT->bh) { + CURRENT->bh->b_uptodate = uptodate; + unlock_buffer(CURRENT->bh); + } + if (!uptodate) { + printk(DEVICE_NAME " I/O error\n\r"); + printk("dev %04x, block %d\n\r",CURRENT->dev, + CURRENT->bh->b_blocknr); + } + wake_up(&CURRENT->waiting); + wake_up(&wait_for_request); + CURRENT->dev = -1; + CURRENT = CURRENT->next; +} + +#define INIT_REQUEST \ +repeat: \ + if (!CURRENT) \ + return; \ + if (MAJOR(CURRENT->dev) != MAJOR_NR) \ + panic(DEVICE_NAME ": request list destroyed"); \ + if (CURRENT->bh) { \ + if (!CURRENT->bh->b_lock) \ + panic(DEVICE_NAME ": block not locked"); \ + } + +#endif + +#endif diff --git a/linux-0.11-lab/1/linux/kernel/blk_drv/blk_drv.a b/linux-0.11-lab/1/linux/kernel/blk_drv/blk_drv.a new file mode 100644 index 0000000000000000000000000000000000000000..02751f123aa0c72fe90e820ca24599de825468be GIT binary patch literal 52212 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 +#include +#include +#include +#include +#include +#include + +#define MAJOR_NR 2 +#include "blk.h" + +static int recalibrate = 0; +static int reset = 0; +static int seek = 0; + +extern unsigned char current_DOR; + +#define immoutb_p(val,port) \ +__asm__("outb %0,%1\n\tjmp 1f\n1:\tjmp 1f\n1:"::"a" ((char) (val)),"i" (port)) + +#define TYPE(x) ((x)>>2) +#define DRIVE(x) ((x)&0x03) +/* + * Note that MAX_ERRORS=8 doesn't imply that we retry every bad read + * max 8 times - some types of errors increase the errorcount by 2, + * so we might actually retry only 5-6 times before giving up. + */ +#define MAX_ERRORS 8 + +/* + * globals used by 'result()' + */ +#define MAX_REPLIES 7 +static unsigned char reply_buffer[MAX_REPLIES]; +#define ST0 (reply_buffer[0]) +#define ST1 (reply_buffer[1]) +#define ST2 (reply_buffer[2]) +#define ST3 (reply_buffer[3]) + +/* + * This struct defines the different floppy types. Unlike minix + * linux doesn't have a "search for right type"-type, as the code + * for that is convoluted and weird. I've got enough problems with + * this driver as it is. + * + * The 'stretch' tells if the tracks need to be boubled for some + * types (ie 360kB diskette in 1.2MB drive etc). Others should + * be self-explanatory. + */ +static struct floppy_struct { + unsigned int size, sect, head, track, stretch; + unsigned char gap,rate,spec1; +} floppy_type[] = { + { 0, 0,0, 0,0,0x00,0x00,0x00 }, /* no testing */ + { 720, 9,2,40,0,0x2A,0x02,0xDF }, /* 360kB PC diskettes */ + { 2400,15,2,80,0,0x1B,0x00,0xDF }, /* 1.2 MB AT-diskettes */ + { 720, 9,2,40,1,0x2A,0x02,0xDF }, /* 360kB in 720kB drive */ + { 1440, 9,2,80,0,0x2A,0x02,0xDF }, /* 3.5" 720kB diskette */ + { 720, 9,2,40,1,0x23,0x01,0xDF }, /* 360kB in 1.2MB drive */ + { 1440, 9,2,80,0,0x23,0x01,0xDF }, /* 720kB in 1.2MB drive */ + { 2880,18,2,80,0,0x1B,0x00,0xCF }, /* 1.44MB diskette */ +}; +/* + * Rate is 0 for 500kb/s, 2 for 300kbps, 1 for 250kbps + * Spec1 is 0xSH, where S is stepping rate (F=1ms, E=2ms, D=3ms etc), + * H is head unload time (1=16ms, 2=32ms, etc) + * + * Spec2 is (HLD<<1 | ND), where HLD is head load time (1=2ms, 2=4 ms etc) + * and ND is set means no DMA. Hardcoded to 6 (HLD=6ms, use DMA). + */ + +extern void floppy_interrupt(void); +extern char tmp_floppy_area[1024]; + +/* + * These are global variables, as that's the easiest way to give + * information to interrupts. They are the data used for the current + * request. + */ +static int cur_spec1 = -1; +static int cur_rate = -1; +static struct floppy_struct * floppy = floppy_type; +static unsigned char current_drive = 0; +static unsigned char sector = 0; +static unsigned char head = 0; +static unsigned char track = 0; +static unsigned char seek_track = 0; +static unsigned char current_track = 255; +static unsigned char command = 0; +unsigned char selected = 0; +struct task_struct * wait_on_floppy_select = NULL; + +void floppy_deselect(unsigned int nr) +{ + if (nr != (current_DOR & 3)) + printk("floppy_deselect: drive not selected\n\r"); + selected = 0; + wake_up(&wait_on_floppy_select); +} + +/* + * floppy-change is never called from an interrupt, so we can relax a bit + * here, sleep etc. Note that floppy-on tries to set current_DOR to point + * to the desired drive, but it will probably not survive the sleep if + * several floppies are used at the same time: thus the loop. + */ +int floppy_change(unsigned int nr) +{ +repeat: + floppy_on(nr); + while ((current_DOR & 3) != nr && selected) + interruptible_sleep_on(&wait_on_floppy_select); + if ((current_DOR & 3) != nr) + goto repeat; + if (inb(FD_DIR) & 0x80) { + floppy_off(nr); + return 1; + } + floppy_off(nr); + return 0; +} + +#define copy_buffer(from,to) \ +__asm__("cld ; rep ; movsl" \ + ::"c" (BLOCK_SIZE/4),"S" ((long)(from)),"D" ((long)(to)) \ + ) + +static void setup_DMA(void) +{ + long addr = (long) CURRENT->buffer; + + cli(); + if (addr >= 0x100000) { + addr = (long) tmp_floppy_area; + if (command == FD_WRITE) + copy_buffer(CURRENT->buffer,tmp_floppy_area); + } +/* mask DMA 2 */ + immoutb_p(4|2,10); +/* output command byte. I don't know why, but everyone (minix, */ +/* sanches & canton) output this twice, first to 12 then to 11 */ + __asm__("outb %%al,$12\n\tjmp 1f\n1:\tjmp 1f\n1:\t" + "outb %%al,$11\n\tjmp 1f\n1:\tjmp 1f\n1:":: + "a" ((char) ((command == FD_READ)?DMA_READ:DMA_WRITE))); +/* 8 low bits of addr */ + immoutb_p(addr,4); + addr >>= 8; +/* bits 8-15 of addr */ + immoutb_p(addr,4); + addr >>= 8; +/* bits 16-19 of addr */ + immoutb_p(addr,0x81); +/* low 8 bits of count-1 (1024-1=0x3ff) */ + immoutb_p(0xff,5); +/* high 8 bits of count-1 */ + immoutb_p(3,5); +/* activate DMA 2 */ + immoutb_p(0|2,10); + sti(); +} + +static void output_byte(char byte) +{ + int counter; + unsigned char status; + + if (reset) + return; + for(counter = 0 ; counter < 10000 ; counter++) { + status = inb_p(FD_STATUS) & (STATUS_READY | STATUS_DIR); + if (status == STATUS_READY) { + outb(byte,FD_DATA); + return; + } + } + reset = 1; + printk("Unable to send byte to FDC\n\r"); +} + +static int result(void) +{ + int i = 0, counter, status; + + if (reset) + return -1; + for (counter = 0 ; counter < 10000 ; counter++) { + status = inb_p(FD_STATUS)&(STATUS_DIR|STATUS_READY|STATUS_BUSY); + if (status == STATUS_READY) + return i; + if (status == (STATUS_DIR|STATUS_READY|STATUS_BUSY)) { + if (i >= MAX_REPLIES) + break; + reply_buffer[i++] = inb_p(FD_DATA); + } + } + reset = 1; + printk("Getstatus times out\n\r"); + return -1; +} + +static void bad_flp_intr(void) +{ + CURRENT->errors++; + if (CURRENT->errors > MAX_ERRORS) { + floppy_deselect(current_drive); + end_request(0); + } + if (CURRENT->errors > MAX_ERRORS/2) + reset = 1; + else + recalibrate = 1; +} + +/* + * Ok, this interrupt is called after a DMA read/write has succeeded, + * so we check the results, and copy any buffers. + */ +static void rw_interrupt(void) +{ + if (result() != 7 || (ST0 & 0xf8) || (ST1 & 0xbf) || (ST2 & 0x73)) { + if (ST1 & 0x02) { + printk("Drive %d is write protected\n\r",current_drive); + floppy_deselect(current_drive); + end_request(0); + } else + bad_flp_intr(); + do_fd_request(); + return; + } + if (command == FD_READ && (unsigned long)(CURRENT->buffer) >= 0x100000) + copy_buffer(tmp_floppy_area,CURRENT->buffer); + floppy_deselect(current_drive); + end_request(1); + do_fd_request(); +} + +inline void setup_rw_floppy(void) +{ + setup_DMA(); + do_floppy = rw_interrupt; + output_byte(command); + output_byte(head<<2 | current_drive); + output_byte(track); + output_byte(head); + output_byte(sector); + output_byte(2); /* sector size = 512 */ + output_byte(floppy->sect); + output_byte(floppy->gap); + output_byte(0xFF); /* sector size (0xff when n!=0 ?) */ + if (reset) + do_fd_request(); +} + +/* + * This is the routine called after every seek (or recalibrate) interrupt + * from the floppy controller. Note that the "unexpected interrupt" routine + * also does a recalibrate, but doesn't come here. + */ +static void seek_interrupt(void) +{ +/* sense drive status */ + output_byte(FD_SENSEI); + if (result() != 2 || (ST0 & 0xF8) != 0x20 || ST1 != seek_track) { + bad_flp_intr(); + do_fd_request(); + return; + } + current_track = ST1; + setup_rw_floppy(); +} + +/* + * This routine is called when everything should be correctly set up + * for the transfer (ie floppy motor is on and the correct floppy is + * selected). + */ +static void transfer(void) +{ + if (cur_spec1 != floppy->spec1) { + cur_spec1 = floppy->spec1; + output_byte(FD_SPECIFY); + output_byte(cur_spec1); /* hut etc */ + output_byte(6); /* Head load time =6ms, DMA */ + } + if (cur_rate != floppy->rate) + outb_p(cur_rate = floppy->rate,FD_DCR); + if (reset) { + do_fd_request(); + return; + } + if (!seek) { + setup_rw_floppy(); + return; + } + do_floppy = seek_interrupt; + if (seek_track) { + output_byte(FD_SEEK); + output_byte(head<<2 | current_drive); + output_byte(seek_track); + } else { + output_byte(FD_RECALIBRATE); + output_byte(head<<2 | current_drive); + } + if (reset) + do_fd_request(); +} + +/* + * Special case - used after a unexpected interrupt (or reset) + */ +static void recal_interrupt(void) +{ + output_byte(FD_SENSEI); + if (result()!=2 || (ST0 & 0xE0) == 0x60) + reset = 1; + else + recalibrate = 0; + do_fd_request(); +} + +void unexpected_floppy_interrupt(void) +{ + output_byte(FD_SENSEI); + if (result()!=2 || (ST0 & 0xE0) == 0x60) + reset = 1; + else + recalibrate = 1; +} + +static void recalibrate_floppy(void) +{ + recalibrate = 0; + current_track = 0; + current_drive = 1; /* by wyj, ?? */ + do_floppy = recal_interrupt; + output_byte(FD_RECALIBRATE); + output_byte(head<<2 | current_drive); + if (reset) + do_fd_request(); +} + +static void reset_interrupt(void) +{ + output_byte(FD_SENSEI); + (void) result(); + output_byte(FD_SPECIFY); + output_byte(cur_spec1); /* hut etc */ + output_byte(6); /* Head load time =6ms, DMA */ + do_fd_request(); +} + +/* + * reset is done by pulling bit 2 of DOR low for a while. + */ +static void reset_floppy(void) +{ + int i; + + reset = 0; + cur_spec1 = -1; + cur_rate = -1; + recalibrate = 1; + printk("Reset-floppy called\n\r"); + cli(); + do_floppy = reset_interrupt; + outb_p(current_DOR & ~0x04,FD_DOR); + for (i=0 ; i<100 ; i++) + __asm__("nop"); + outb(current_DOR,FD_DOR); + sti(); +} + +static void floppy_on_interrupt(void) +{ +/* We cannot do a floppy-select, as that might sleep. We just force it */ + selected = 1; + if (current_drive != (current_DOR & 3)) { + current_DOR &= 0xFC; + current_DOR |= current_drive; + outb(current_DOR,FD_DOR); + add_timer(2,&transfer); + } else + transfer(); +} + +void do_fd_request(void) +{ + unsigned int block; + + seek = 0; + if (reset) { + reset_floppy(); + return; + } + if (recalibrate) { + recalibrate_floppy(); + return; + } + INIT_REQUEST; + floppy = (MINOR(CURRENT->dev)>>2) + floppy_type; + if (current_drive != CURRENT_DEV) + seek = 1; + current_drive = CURRENT_DEV; + block = CURRENT->sector; + if (block+2 > floppy->size) { + end_request(0); + goto repeat; + } + sector = block % floppy->sect; + block /= floppy->sect; + head = block % floppy->head; + track = block / floppy->head; + seek_track = track << floppy->stretch; + if (seek_track != current_track) + seek = 1; + sector++; + if (CURRENT->cmd == READ) + command = FD_READ; + else if (CURRENT->cmd == WRITE) + command = FD_WRITE; + else + panic("do_fd_request: unknown command"); + add_timer(ticks_to_floppy_on(current_drive),&floppy_on_interrupt); +} + +void floppy_init(void) +{ + blk_dev[MAJOR_NR].request_fn = DEVICE_REQUEST; + set_trap_gate(0x26,&floppy_interrupt); + outb(inb_p(0x21)&~0x40,0x21); +} diff --git a/linux-0.11-lab/1/linux/kernel/blk_drv/floppy.o b/linux-0.11-lab/1/linux/kernel/blk_drv/floppy.o new file mode 100644 index 0000000000000000000000000000000000000000..33235bcdcc660371f0cfe6077089e24f2a1c3a96 GIT binary patch literal 16612 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 literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/kernel/blk_drv/hd.c b/linux-0.11-lab/1/linux/kernel/blk_drv/hd.c new file mode 100644 index 0000000..c0e908f --- /dev/null +++ b/linux-0.11-lab/1/linux/kernel/blk_drv/hd.c @@ -0,0 +1,351 @@ +/* + * linux/kernel/hd.c + * + * (C) 1991 Linus Torvalds + */ + +/* + * This is the low-level hd interrupt support. It traverses the + * request-list, using interrupts to jump between functions. As + * all the functions are called within interrupts, we may not + * sleep. Special care is recommended. + * + * modified by Drew Eckhardt to check nr of hd's from the CMOS. + */ + +#include +#include +#include +#include +#include +#include +#include +#include + +#define MAJOR_NR 3 +#include "blk.h" + +#define CMOS_READ(addr) ({ \ +outb_p(0x80|addr,0x70); \ +inb_p(0x71); \ +}) + +/* Max read/write errors/sector */ +#define MAX_ERRORS 7 +#define MAX_HD 2 + +static void recal_intr(void); + +static int recalibrate = 0; /* 1, wen */ +static int reset = 0; + +/* + * This struct defines the HD's and their types. + */ +struct hd_i_struct { + int head,sect,cyl,wpcom,lzone,ctl; + }; +#ifdef HD_TYPE +struct hd_i_struct hd_info[] = { HD_TYPE }; +#define NR_HD ((sizeof (hd_info))/(sizeof (struct hd_i_struct))) +#else +struct hd_i_struct hd_info[] = { {0,0,0,0,0,0},{0,0,0,0,0,0} }; +static int NR_HD = 0; +#endif + +static struct hd_struct { + long start_sect; + long nr_sects; +} hd[5*MAX_HD]={{0,0},}; + +#define port_read(port,buf,nr) \ +__asm__("cld;rep;insw"::"d" (port),"D" (buf),"c" (nr)) + +#define port_write(port,buf,nr) \ +__asm__("cld;rep;outsw"::"d" (port),"S" (buf),"c" (nr)) + +extern void hd_interrupt(void); +extern void rd_load(void); + +/* This may be used only once, enforced by 'static int callable' */ +int sys_setup(void * BIOS) +{ + static int callable = 1; + int i,drive; + unsigned char cmos_disks; + struct partition *p; + struct buffer_head * bh; + + if (!callable) + return -1; + callable = 0; +#ifndef HD_TYPE + for (drive=0 ; drive<2 ; drive++) { + hd_info[drive].cyl = *(unsigned short *) BIOS; + hd_info[drive].head = *(unsigned char *) (2+BIOS); + hd_info[drive].wpcom = *(unsigned short *) (5+BIOS); + hd_info[drive].ctl = *(unsigned char *) (8+BIOS); + hd_info[drive].lzone = *(unsigned short *) (12+BIOS); + hd_info[drive].sect = *(unsigned char *) (14+BIOS); + BIOS += 16; + } + if (hd_info[1].cyl) + NR_HD=2; + else + NR_HD=1; +#endif + for (i=0 ; i are the primary drives in the system, and + the ones reflected as drive 1 or 2. + + The first drive is stored in the high nibble of CMOS + byte 0x12, the second in the low nibble. This will be + either a 4 bit drive type or 0xf indicating use byte 0x19 + for an 8 bit type, drive 1, 0x1a for drive 2 in CMOS. + + Needless to say, a non-zero value means we have + an AT controller hard disk for that drive. + + + */ + + if ((cmos_disks = CMOS_READ(0x12)) & 0xf0) + if (cmos_disks & 0x0f) + NR_HD = 2; + else + NR_HD = 1; + else + NR_HD = 0; + for (i = NR_HD ; i < 2 ; i++) { + hd[i*5].start_sect = 0; + hd[i*5].nr_sects = 0; + } + for (drive=0 ; driveb_data[510] != 0x55 || (unsigned char) + bh->b_data[511] != 0xAA) { + printk("Bad partition table on drive %d\n\r",drive); + panic(""); + } + p = 0x1BE + (void *)bh->b_data; + for (i=1;i<5;i++,p++) { + hd[i+5*drive].start_sect = p->start_sect; + hd[i+5*drive].nr_sects = p->nr_sects; + } + brelse(bh); + } + if (NR_HD) + printk("Partition table%s ok.\n\r",(NR_HD>1)?"s":""); + rd_load(); + mount_root(); + return (0); +} + +static int controller_ready(void) +{ + /* int retries=10000; */ + int retries=100000; + + /* while (--retries && (inb_p(HD_STATUS)&0xc0)!=0x40); */ + while (--retries && (inb_p(HD_STATUS)&0x80)); + return (retries); +} + +static int win_result(void) +{ + int i=inb_p(HD_STATUS); + + if ((i & (BUSY_STAT | READY_STAT | WRERR_STAT | SEEK_STAT | ERR_STAT)) + == (READY_STAT | SEEK_STAT)) + return(0); /* ok */ + if (i&1) i=inb(HD_ERROR); + return (1); +} + +static void hd_out(unsigned int drive,unsigned int nsect,unsigned int sect, + unsigned int head,unsigned int cyl,unsigned int cmd, + void (*intr_addr)(void)) +{ + register int port asm("dx"); + + if (drive>1 || head>15) + panic("Trying to write bad sector"); + if (!controller_ready()) + panic("HD controller not ready"); + do_hd = intr_addr; + outb_p(hd_info[drive].ctl,HD_CMD); + port=HD_DATA; + outb_p(hd_info[drive].wpcom>>2,++port); + outb_p(nsect,++port); + outb_p(sect,++port); + outb_p(cyl,++port); + outb_p(cyl>>8,++port); + outb_p(0xA0|(drive<<4)|head,++port); + outb(cmd,++port); +} + +static int drive_busy(void) +{ + unsigned int i; + + for (i = 0; i < 10000; i++) + if (READY_STAT == (inb_p(HD_STATUS) & (BUSY_STAT|READY_STAT))) + break; + i = inb(HD_STATUS); + i &= BUSY_STAT | READY_STAT | SEEK_STAT; + if (i == READY_STAT | SEEK_STAT) + return(0); + printk("HD controller times out\n\r"); + return(1); +} + +static void reset_controller(void) +{ + int i; + + outb(4,HD_CMD); + for(i = 0; i < 100; i++) nop(); + outb(hd_info[0].ctl & 0x0f ,HD_CMD); + if (drive_busy()) + printk("HD-controller still busy\n\r"); + if ((i = inb(HD_ERROR)) != 1) + printk("HD-controller reset failed: %02x\n\r",i); +} + +static void reset_hd(int nr) +{ + reset_controller(); + hd_out(nr,hd_info[nr].sect,hd_info[nr].sect,hd_info[nr].head-1, + hd_info[nr].cyl,WIN_SPECIFY,&recal_intr); +} + +void unexpected_hd_interrupt(void) +{ + printk("Unexpected HD interrupt\n\r"); +} + +static void bad_rw_intr(void) +{ + if (++CURRENT->errors >= MAX_ERRORS) + end_request(0); + if (CURRENT->errors > MAX_ERRORS/2) + reset = 1; +} + +static void read_intr(void) +{ + if (win_result()) { + bad_rw_intr(); + do_hd_request(); + return; + } + port_read(HD_DATA,CURRENT->buffer,256); + CURRENT->errors = 0; + CURRENT->buffer += 512; + CURRENT->sector++; + if (--CURRENT->nr_sectors) { + do_hd = &read_intr; + return; + } + end_request(1); + do_hd_request(); +} + +static void write_intr(void) +{ + if (win_result()) { + bad_rw_intr(); + do_hd_request(); + return; + } + if (--CURRENT->nr_sectors) { + CURRENT->sector++; + CURRENT->buffer += 512; + do_hd = &write_intr; + port_write(HD_DATA,CURRENT->buffer,256); + return; + } + end_request(1); + do_hd_request(); +} + +static void recal_intr(void) +{ + if (win_result()) + bad_rw_intr(); + do_hd_request(); +} + +void do_hd_request(void) +{ + int i,r; + unsigned int block,dev; + unsigned int sec,head,cyl; + unsigned int nsect; + + INIT_REQUEST; + dev = MINOR(CURRENT->dev); + block = CURRENT->sector; + if (dev >= 5*NR_HD || block+2 > hd[dev].nr_sects) { + end_request(0); + goto repeat; + } + block += hd[dev].start_sect; + dev /= 5; + __asm__("divl %4":"=a" (block),"=d" (sec):"0" (block),"1" (0), + "r" (hd_info[dev].sect)); + __asm__("divl %4":"=a" (cyl),"=d" (head):"0" (block),"1" (0), + "r" (hd_info[dev].head)); + sec++; + nsect = CURRENT->nr_sectors; + if (reset) { + reset = 0; + recalibrate = 1; + reset_hd(CURRENT_DEV); + return; + } + if (recalibrate) { + recalibrate = 0; + hd_out(dev,hd_info[CURRENT_DEV].sect,0,0,0, + WIN_RESTORE,&recal_intr); + return; + } + if (CURRENT->cmd == WRITE) { + hd_out(dev,nsect,sec,head,cyl,WIN_WRITE,&write_intr); + for(i=0 ; i<3000 && !(r=inb_p(HD_STATUS)&DRQ_STAT) ; i++) + /* nothing */ ; + if (!r) { + bad_rw_intr(); + goto repeat; + } + port_write(HD_DATA,CURRENT->buffer,256); + } else if (CURRENT->cmd == READ) { + hd_out(dev,nsect,sec,head,cyl,WIN_READ,&read_intr); + } else + panic("unknown hd-command"); +} + +void hd_init(void) +{ + blk_dev[MAJOR_NR].request_fn = DEVICE_REQUEST; + set_intr_gate(0x2E,&hd_interrupt); + outb_p(inb_p(0x21)&0xfb,0x21); + outb(inb_p(0xA1)&0xbf,0xA1); +} diff --git a/linux-0.11-lab/1/linux/kernel/blk_drv/hd.o b/linux-0.11-lab/1/linux/kernel/blk_drv/hd.o new file mode 100644 index 0000000000000000000000000000000000000000..bf2b0d10bc58477ea1758f63f765ba3eab8d6225 GIT binary patch literal 15520 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 literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/kernel/blk_drv/ll_rw_blk.c b/linux-0.11-lab/1/linux/kernel/blk_drv/ll_rw_blk.c new file mode 100644 index 0000000..f57d998 --- /dev/null +++ b/linux-0.11-lab/1/linux/kernel/blk_drv/ll_rw_blk.c @@ -0,0 +1,165 @@ +/* + * linux/kernel/blk_dev/ll_rw.c + * + * (C) 1991 Linus Torvalds + */ + +/* + * This handles all read/write requests to block devices + */ +#include +#include +#include +#include + +#include "blk.h" + +/* + * The request-struct contains all necessary data + * to load a nr of sectors into memory + */ +struct request request[NR_REQUEST]; + +/* + * used to wait on when there are no free requests + */ +struct task_struct * wait_for_request = NULL; + +/* blk_dev_struct is: + * do_request-address + * next-request + */ +struct blk_dev_struct blk_dev[NR_BLK_DEV] = { + { NULL, NULL }, /* no_dev */ + { NULL, NULL }, /* dev mem */ + { NULL, NULL }, /* dev fd */ + { NULL, NULL }, /* dev hd */ + { NULL, NULL }, /* dev ttyx */ + { NULL, NULL }, /* dev tty */ + { NULL, NULL } /* dev lp */ +}; + +static inline void lock_buffer(struct buffer_head * bh) +{ + cli(); + while (bh->b_lock) + sleep_on(&bh->b_wait); + bh->b_lock=1; + sti(); +} + +static inline void unlock_buffer(struct buffer_head * bh) +{ + if (!bh->b_lock) + printk("ll_rw_block.c: buffer not locked\n\r"); + bh->b_lock = 0; + wake_up(&bh->b_wait); +} + +/* + * add-request adds a request to the linked list. + * It disables interrupts so that it can muck with the + * request-lists in peace. + */ +static void add_request(struct blk_dev_struct * dev, struct request * req) +{ + struct request * tmp; + + req->next = NULL; + cli(); + if (req->bh) + req->bh->b_dirt = 0; + if (!(tmp = dev->current_request)) { + dev->current_request = req; + sti(); + (dev->request_fn)(); + return; + } + for ( ; tmp->next ; tmp=tmp->next) + if ((IN_ORDER(tmp,req) || + !IN_ORDER(tmp,tmp->next)) && + IN_ORDER(req,tmp->next)) + break; + req->next=tmp->next; + tmp->next=req; + sti(); +} + +static void make_request(int major,int rw, struct buffer_head * bh) +{ + struct request * req; + int rw_ahead; + +/* WRITEA/READA is special case - it is not really needed, so if the */ +/* buffer is locked, we just forget about it, else it's a normal read */ + if (rw_ahead = (rw == READA || rw == WRITEA)) { + if (bh->b_lock) + return; + if (rw == READA) + rw = READ; + else + rw = WRITE; + } + if (rw!=READ && rw!=WRITE) + panic("Bad block dev command, must be R/W/RA/WA"); + lock_buffer(bh); + if ((rw == WRITE && !bh->b_dirt) || (rw == READ && bh->b_uptodate)) { + unlock_buffer(bh); + return; + } +repeat: +/* we don't allow the write-requests to fill up the queue completely: + * we want some room for reads: they take precedence. The last third + * of the requests are only for reads. + */ + if (rw == READ) + req = request+NR_REQUEST; + else + req = request+((NR_REQUEST*2)/3); +/* find an empty request */ + while (--req >= request) + if (req->dev<0) + break; +/* if none found, sleep on new requests: check for rw_ahead */ + if (req < request) { + if (rw_ahead) { + unlock_buffer(bh); + return; + } + sleep_on(&wait_for_request); + goto repeat; + } +/* fill up the request-info, and add it to the queue */ + req->dev = bh->b_dev; + req->cmd = rw; + req->errors=0; + req->sector = bh->b_blocknr<<1; + req->nr_sectors = 2; + req->buffer = bh->b_data; + req->waiting = NULL; + req->bh = bh; + req->next = NULL; + add_request(major+blk_dev,req); +} + +void ll_rw_block(int rw, struct buffer_head * bh) +{ + unsigned int major; + + if ((major=MAJOR(bh->b_dev)) >= NR_BLK_DEV || + !(blk_dev[major].request_fn)) { + printk("Trying to read nonexistent block-device\n\r"); + return; + } + make_request(major,rw,bh); +} + +void blk_dev_init(void) +{ + int i; + + for (i=0 ; iYkGs}N`|^F* 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 + +#include +#include +#include +#include +#include +#include +#include + +#define MAJOR_NR 1 +#include "blk.h" + +char *rd_start; +int rd_length = 0; + +void do_rd_request(void) +{ + int len; + char *addr; + + INIT_REQUEST; + addr = rd_start + (CURRENT->sector << 9); + len = CURRENT->nr_sectors << 9; + if ((MINOR(CURRENT->dev) != 1) || (addr+len > rd_start+rd_length)) { + end_request(0); + goto repeat; + } + if (CURRENT-> cmd == WRITE) { + (void ) memcpy(addr, + CURRENT->buffer, + len); + } else if (CURRENT->cmd == READ) { + (void) memcpy(CURRENT->buffer, + addr, + len); + } else + panic("unknown ramdisk-command"); + end_request(1); + goto repeat; +} + +/* + * Returns amount of memory which needs to be reserved. + */ +long rd_init(long mem_start, int length) +{ + int i; + char *cp; + + blk_dev[MAJOR_NR].request_fn = DEVICE_REQUEST; + rd_start = (char *) mem_start; + rd_length = length; + cp = rd_start; + for (i=0; i < length; i++) + *cp++ = '\0'; + return(length); +} + +/* + * If the root device is the ram disk, try to load it. + * In order to do this, the root device is originally set to the + * floppy, and we later change it to be ram disk. + */ +void rd_load(void) +{ + struct buffer_head *bh; + struct super_block s; + int block = 256; /* Start at block 256 */ + int i = 1; + int nblocks; + char *cp; /* Move pointer */ + + if (!rd_length) + return; + printk("Ram disk: %d bytes, starting at 0x%x\n", rd_length, + (int) rd_start); + if (MAJOR(ROOT_DEV) != 2) + return; + bh = breada(ROOT_DEV,block+1,block,block+2,-1); + if (!bh) { + printk("Disk error while looking for ramdisk!\n"); + return; + } + __asm__ volatile ("cld"); /* by wyj */ + *((struct d_super_block *) &s) = *((struct d_super_block *) bh->b_data); + brelse(bh); + if (s.s_magic != SUPER_MAGIC) + /* No ram disk image present, assume normal floppy boot */ + return; + nblocks = s.s_nzones << s.s_log_zone_size; + if (nblocks > (rd_length >> BLOCK_SIZE_BITS)) { + printk("Ram disk image too big! (%d blocks, %d avail)\n", + nblocks, rd_length >> BLOCK_SIZE_BITS); + return; + } + printk("Loading %d bytes into ram disk... 0000k", + nblocks << BLOCK_SIZE_BITS); + cp = rd_start; + while (nblocks) { + if (nblocks > 2) + bh = breada(ROOT_DEV, block, block+1, block+2, -1); + else + bh = bread(ROOT_DEV, block); + if (!bh) { + printk("I/O error on block %d, aborting load\n", + block); + return; + } + (void) memcpy(cp, bh->b_data, BLOCK_SIZE); + brelse(bh); + printk("\010\010\010\010\010%4dk",i); + cp += BLOCK_SIZE; + block++; + nblocks--; + i++; + } + printk("\010\010\010\010\010done \n"); + ROOT_DEV=0x0101; +} diff --git a/linux-0.11-lab/1/linux/kernel/blk_drv/ramdisk.o b/linux-0.11-lab/1/linux/kernel/blk_drv/ramdisk.o new file mode 100644 index 0000000000000000000000000000000000000000..d37a922496b20c46741e78e22466958ee16e9dcd GIT binary patch literal 10664 zcma)B4RjpUb$&BDt65fSS+-Un+cJ!)ln7(3WFw3*2K|=h6AVC->F(HH`P~#F3O5%{Dv?M5P?c&%W;q*8Skfu4!2?_MzKttO697s8+-}mN@ zw02L==^X8R_uhBkz4zUB=gpg^yVmrtH4H=fm!Se`ic{*HIbKVjhA!2rW~$M5+V`*S za2{Ab?cSrc$Vsb%ZEt-rF)=~$iRIH2ar9{OnAM@hqsQA{M5n_M=C&$2f&}{X8^70Jcs1O#j=X@Kb9?M%s|S_5%@9`qPMU>hfbdXZWLe_QQ#Z z)0?KoVX^0h>;;2SV03@0PWI;L{{D`(v6Ex3eek<4y?wdFYGI7?gpQ&|GkP?`Z+pEm z2mAm$>lp;is(5QL9lwg(=<$wQ0TT?n)B(w-;rAf* z*iT~Aky?w!9 z*i!$u!ekQL#hb*}@5gugVfOdpLzs_xoQ8+J{LcK2vM_9~zM;vaPbSx^7%^J*jqda8 zvEPJO2on$LQG;XANDkEW`+kEuM>hBRJx_8b6&K5W$621Y;0Y)v^66}4c&U>qyRMV0 zWioErNxIp>pi?X4im72Y9af^`tnazbam(dmIXq3J-JMQnZ{NrQCrLG@GYz5gRhK$t z_x74wsXDnVZfQ{E;%+xR)$a8w6rrKLs9IsTP~25;#94Q$n9nB)Y1rJH$U9z;ooOez zyXsaJIF)LmTxFDrs?$5tITD86Y7E4S&)GGU&AG5#9HvgDSoY1%gQ9QG$>tM-u2U@* zon&@!p5t`UKEr_nkcpj%Z0@44>MthJG~;`BvW04q26a@iSj_3gHLNDn;}i>%Sy|vD zl0`4n9PETuh*xJ{df21V#e(aE)sGMtW)zoYJd3-L!8Fx8iHhinLtR_;hY$y@fUWWGI07szge}W+R=cFzBTd)z_Ogd!GhV9_>q$Bn^>TEd|tA2C%Lee)--fV{7 zWrv%RV4`ODD`alwXxq&25~^vY-3)Jl%wrt0F4?G~!7 zHNzjF0nMy4!!u}FGaJnCH_2>gIQ?dL55xHwnE^9=f_*fz#SFhU$=qy)A7LNevfT`i zPqyqZ!w=EGt#q0;8>`jbD!7Ar8#2T9u_eKl9CEM=u_Zr_o+Y#}>J*u(8U7x}lO{7_ zhF@o{UFLeP89q&?nU7$4?lv29>8c72Edz53ekv6eyzPe#So}>?!UC8GS!3uGp}T(c zo3;f+NCkciyGyK(T?w!YkXt%bW&a8SD^6|Gz7*Z99bP$qi8=|=Av=y>tfW`A)U;Aw z*)F6`dKvCb_MI4tm0|Tcc9}YZ?Au|tu6kr1dYE*teVTNR z_7~aDk*I74wKr4#3DSLb zGv)VFXNx^dn_~?3W}9y_>jBc+?e}SOKW*-?A7|eOIVWj*7xfP?H$(Of)cGXotldxf zr%2zXB3x1SL7G`BBt4jJ}(jhC8EveuF z(h)0@!gJP5y4lJUiz*l+9R&?}59v1h53nEXrTKOhp@@&A&SZ-U+<_6j61;>3Jp1DJ~7rKByZQt4H}#iT>_LzG`eIs*AZ6+RP_&@=lT?Q+u5pnC=-BT|O%?bV zgdN6t$04$?Pg6#lE)gr0Pb*^@&+*FiH%Own@0D$pzW=+7Gtq0dpWK3=%Cb$``O?^ ztS-gRcx>i5O3kEQmv+sAO3j!?k9js9(khFg(&94IJj2#H+%uWy@#}3dwIBNmbfP)8 zpiDhX^WaeH*Jy7x2Vow}oqIVuwEq+x&U+Lh2gE1Qr?nG_HapneJeXE(C(w2Q+B|ue zC*PseENiwyOS+=Nh~-8o8IQfk(B7VGKxi$m&{3Zks1?mBbFoK{MDao~FZ1H5syQ|t zU$X8$E7^ zcCyKHvc0W3Tnop2O*jJ z9JGu+mcjYoqr)is20=kEokMA*1y7)i8AfMQOJksEPSXryW<&FNXzx&sjaNa0@w6C$ zrpCsljaM`pE$}@}1wv%jw=8Ld2~k8S4d<#rlh=YWf|@W?3r&Z;_2_<%wifiQ;bUY{ z4PiCb83!9NjP)&aI&Gd>-_ip+O|8a9XHkMd&|Gt?`sgeaVGJ?S=0|671k2kVS*f*V z1}B3x+c5WFB`C7dzB5`|!Pd2&8y0p3Qg>b>k~Fh{p4&VUMaD5HH9KZpJ%~%JhTKFNVpz>o zJglUKToF}wmt0B_W+gjVNaR4H>hM{KFEfuu&FDb{-c-hwN5)6r+<4Xao4>DpcVFm- zzZ*aDl4SA#+VM^piuOp>5{;mN!F#M`|_p4wR~anXio>GQ-GbC0^Kr&%lbR#PLa50&vyV zpSW?{Q^P8$CAcT538s%Mn##3Q6<^|&lux^bw5L-^#51`BUN_ZpBIU-D*(wcZ;{{C7 za0Nu7n$5eartf(9EmF07qB5*9iRzGBR<(+oj^{zEf;$2i@k*`amgD;4SY5N}24|Ji z7h4kRbGq}1a%$+x>?KPUgHGkrPWPbGohjzC)$R)bsOvX9aPkWfYViCyJq0;kFRIc@~21wUXD7aU-M1Z>gLumb3Wq%X+2i zO2J9V1#knk? zIuX%l)(`c>am1vGZQnIO;J=* zg)*v|rCvdXnRk^ga;~O|zEI11BbK#Jl?KZtvRkN5TF~)$ zwX1SSAA*rJL&f79Y_&M7dWMR5x2I4`S9^+;?t;6^TfMt`V+$8{=Mu@DUQf_7?3N2| zu18xa@04lb#Oo^4HQ^=7yC*PKEF{>34PyD28WbPFtXENaJkG2lJTI(q)Vh8Gkpmu) zF_Y4}3QPXvV01`iB0hve!5l|~vh*uD!A4{hVyvBvDCo=~op- z!zW7Dx2~yju~=2=npLZoI$bv;vCP!GC9Zo>O>+zHT-X=u?Yqd6@`V-U4VSTJvoiLE zj5!g@x*xAE%K1v=#qFzF)#TicGXTo_M8+*G<>nWgtS*rK_`QN3x3OwPQ|J@sil)fN z1FM>P12Lm1vf@NjXvImfF#;8T?+F`Gb90kLyPw9--$>TkSkcrxYOQTLY6K3MP0cG_ zth0s=vC8f|RxKdPLgSE6mEByd%H=<%UpuiRK5t@WE+Ppa8q;pFHi$%LicryXBAH}C z*R>|fiNYXeu1>_afZqYWRE$Txs9zPsaj+Z1>&1I1czxU}D$gd7w z%uW4vhHbp&;D?R-J(n@azXP8y#Dg-T?`@h>-DBKR8yO) zUg)rox8?Hev2Og!@3RboI0b=Ahm;-+t>p=T`K&r=Q zDD`xmz$dqzrMCu#9Cnb)*W?Kq?msJL&{JnMGT@y%E@B zK4}m8;YoYDL9-9@$m@Gir5>o86Snbpub{7Y-E8kO2x5KtdI!Lf_OIR0tH1oV!w{18 z=WQ?aj@K!2yu7$kt{=zU7)KXm90&8`=LPAXtQC-IISTTtB;@k_*85~r9}4^z5MtPh zHfWD_>C>-0kSaP){_92tmv7JGrtbA}Oa14>R159Zx00{-K;9p<*DIicdalTE?K9CI zA0e9Nnn#|`(<}IKts`H51tyT%ZuN6qW zwM1-cc2N$y`uq-fSoFRudPjxVhePQ11M-NE|LLQjc03fcKOab*=a=SO)IWLnbIGIM zlSKIY8t@^^**z3_h`4?BF%8F)8Fh*$z(LL*#joN6Mcf9>GrtJ}h`x z@auy7w-EdNQt(~D4+PI)-JpG=pgvFr?+SmrAphq;y)nVh3hMfV{D|=15oCQ*|3`xV zCdhw3QvL@)gY^Y|n&2$KPQitOR|#$qyiqVI$Rk+V*&}#B@biLC34T-X?*v~Gd{yvu z!T%6^UoePghxTU(&K0~!kpHD;`wGF0f?EY$!FvQhDfk7!FAIK4@b3kGAo!Z#F9qKf z{F7h<9#Hz9DR{o%e8KAkpA~#r@LvSq5d1(eivP>e-fF=Q1;ZgvzESXY!8-)U1V1Zy zSn%6|KNS3l;I9OKEBHquYO@8KE&88D1m7k6WrA0Ve4Fq?f(4OR1n(C4r-Xl0_-6#4 z6Zwn6|48tC!3k;a!rI4pRtkQMh`2Js?-aa8@NvPX1^-&`ABb2qj|+c_h;<%mR|b4> azd^gt2s%I$JikGRTt|uA(-65=A^s1$?rygL literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/kernel/chr_drv/Makefile b/linux-0.11-lab/1/linux/kernel/chr_drv/Makefile new file mode 100644 index 0000000..9d4d8d1 --- /dev/null +++ b/linux-0.11-lab/1/linux/kernel/chr_drv/Makefile @@ -0,0 +1,68 @@ +# +# Makefile for the FREAX-kernel character device drivers. +# +# Note! Dependencies are done automagically by 'make dep', which also +# removes any old dependencies. DON'T put your own dependencies here +# unless it's something special (ie not a .c file). +# + +AR =ar +AS =as +LD =ld +LDFLAGS =-s -x +CC =gcc -march=i386 +CFLAGS =-w -g -fstrength-reduce -fomit-frame-pointer -mcld \ + -finline-functions -nostdinc -fno-stack-protector -I../../include +CPP =gcc -E -nostdinc -I../../include + +.c.s: + $(CC) $(CFLAGS) \ + -S -o $*.s $< +.s.o: + $(AS) -o $*.o $< +.c.o: + $(CC) $(CFLAGS) \ + -c -o $*.o $< + +OBJS = tty_io.o console.o keyboard.2.o serial.o rs_io.o \ + tty_ioctl.o + +chr_drv.a: $(OBJS) + $(AR) rcs chr_drv.a $(OBJS) + sync + +keyboard.2.s: keyboard.S ../../include/linux/config.h + $(CPP) -traditional keyboard.S -o keyboard.2.s + +clean: + rm -f core *.o *.a tmp_make keyboard.2.s + for i in *.c;do rm -f `basename $$i .c`.s;done + +dep: + sed '/\#\#\# Dependencies/q' < Makefile > tmp_make + (for i in *.c;do echo -n `echo $$i | sed 's,\.c,\.s,'`" "; \ + $(CPP) -M $$i;done) >> tmp_make + cp tmp_make Makefile + +### Dependencies: +console.s console.o : console.c ../../include/linux/sched.h \ + ../../include/linux/head.h ../../include/linux/fs.h \ + ../../include/sys/types.h ../../include/linux/mm.h ../../include/signal.h \ + ../../include/linux/tty.h ../../include/termios.h ../../include/asm/io.h \ + ../../include/asm/system.h +serial.s serial.o : serial.c ../../include/linux/tty.h ../../include/termios.h \ + ../../include/linux/sched.h ../../include/linux/head.h \ + ../../include/linux/fs.h ../../include/sys/types.h ../../include/linux/mm.h \ + ../../include/signal.h ../../include/asm/system.h ../../include/asm/io.h +tty_io.s tty_io.o : tty_io.c ../../include/ctype.h ../../include/errno.h \ + ../../include/signal.h ../../include/sys/types.h \ + ../../include/linux/sched.h ../../include/linux/head.h \ + ../../include/linux/fs.h ../../include/linux/mm.h ../../include/linux/tty.h \ + ../../include/termios.h ../../include/asm/segment.h \ + ../../include/asm/system.h +tty_ioctl.s tty_ioctl.o : tty_ioctl.c ../../include/errno.h ../../include/termios.h \ + ../../include/linux/sched.h ../../include/linux/head.h \ + ../../include/linux/fs.h ../../include/sys/types.h ../../include/linux/mm.h \ + ../../include/signal.h ../../include/linux/kernel.h \ + ../../include/linux/tty.h ../../include/asm/io.h \ + ../../include/asm/segment.h ../../include/asm/system.h diff --git a/linux-0.11-lab/1/linux/kernel/chr_drv/chr_drv.a b/linux-0.11-lab/1/linux/kernel/chr_drv/chr_drv.a new file mode 100644 index 0000000000000000000000000000000000000000..d2f3869a9d5cd226117476be64275b50d1cf4aa7 GIT binary patch literal 68902 zcmeFa3w#yT)iypeXU@qaImrnm+@qX8P|%PI1PC`dK+u4oh^Pe65RwxT$&KV3F5bWf zDj{OQ*0#1-#7nDHTHC6nqLzyawrcUMR(-WCUQ3MHBDTd_^F7brYfesrR(;?1dw>7$ z_h*th&suA*z4m4Hp4oe5_L{6otYyKeYFFLGi!A;ONns z4+fVc8HUlvFw7gi++O-~!|1u+gSh+W>HUxI83y;)=S3oG$|B`UYr}^6Evv0*ju;fy z)YrH~q{&!SUK1&+YG^839$wSf6mD)dDjFIQv!Se_p<#KrQblPBmuq5GQ%xjnR5p}p zLy>S(Q?xN+R8%*WRfbn;(-qA%Wp%JpU#7K5sWh9{G%pQ@8=E5yjRuK|hG>1nK)OpC z%9|>oA~A7X!- zy@AYzJ&{RqY}=MX%P=I`_GPd%eaZL+UEI_=V$kCo$K#}sg|p<{Zp>_am!gZ-_K1D0 zhf0QZdQ=Xrj!FO4>M5TWx8?ZSl?UAf4%pdq9m6=X0F|WE%xSOks?z4Sg^Ey>`J0NZ z(8l8I!LUbBNM)dPAKBKqMeDB09-Ixyjz zqx4U#x8{Oe+a>K*0b7(FYv!xR2<0$=){N}VL)!X$90`4VrFyqeqQbhUbqgRv8=3Oi zaW<__TLJ~vg{tXDzqktMBNbrdXt%FLJBkZSmoN*J^EpXQ{E|tg$C=ehM!oH6NKVE7 z|9XA5S9NbS169RDdEUrB5E_o^G1{khR~gV<1sX z=_hqbzhu+bU0HRA6JxaRLm5<83w+~iQk=Gsf0%)KV0LbIWj#C8WnV5Io6y}`_JuY+ z%g(j&dewXXUCfR#U7?J!X?FJDFA+^e`ph02XM{abTW3e^UKg>hJ-1NXDnh3|O_5vJ z#k=CgpY{VAmVVUP$uRF?D78wPX?ZLMmkVCBid&1bbI`1^QH=&JLLqBa0-(fLle7!H zzO#J_`{DfTQ0pOck9lbCVQ=fcy{~!AL+b2`$iW?q*|u&rjt5wE3EC9u8+hW z(ID=Rq=K75{m?eS4Mz(7jmX7-;YRd)B(J&&*i0kRyA4AuRi6Ilp^30~b;2$*Iith7 zi*iKIhGMo6>8Ddpp%gjnZ~mrr3v+>_h9h3dHEdTUOs;(l#O?X`(J{}^G1-cO>gq8- z3v|Ns{OjKOGcL>RNr>QTqCn%A~v!_bhajhiSs?y-OKq+hr z>9c7h0sW_6QdDB;{>?^#2xLx(5FM=SyQS%c#B(4iW}e$~b-r?NifDygMMfpttr^)z z?)V3q%;u<|JIib=58#18|6|{w__!OfHAp9y#L5|-EO`#*8kKg?4 z%vjs#I!dW-xzLmPb_{komJ;n}_*GU%vdVwp8;^h5+1bOAW;q~>q`NUO*h|>O@neVI z713DBW0TO^Sc8SAsQ$2-uX|Zhte17LQh9a%oL-jE{&Q+zDC!O2q~3}~l7hO9%Y?W6 z`_O3T*%@m6sp0&+vr`5+7{S_V6ckwh61oe|rzz1sw5I|%o{>S=Ky`VDrpLm9Z2D@% zr9&2|MA57{1lG}Qs7yVe&Im|eWivLu$&e8dJ7b2H#x>cDRy87OZ*!wDn;46I(Rhw3 zGM+mUKc2%-x<49Vk?0mKPiOAm&r)>XP|2#YAx-9- z)RVckkBzZ(uk?XN??Au4-L+40Cu`tj4Vo5${lwtbf(%(VjPw5FK(R^UP! zP|N}=FeJt-wgOH}ZHX0FL<5&G(Ml@~i=hnP64qO_6*!L}u>xzEok}vRt-#lq(J<@!Dl2e36RjGB!?VsxtF4R}zUmS%hma1|iTN&n0dbC4 zXbD_%<7Ywx5u+Cyh+}xCA+#vr(qw?|LzqoanKXQP5G0gQ+wyhdH(?2rvwgXUn@~>L z@ug9J=~U2u-#F@2kWTSEN_k}xG*f-Qqn#?YyPz*bon?%h?fVBZlTb~1xR2{75^9)M zj_(%QznpZg?_$PXPCDN=k#sHXkMfzM>qw9GWztSP=|bNT{3bMz9^-qJbR+4pzL~VY zg7i4U8$kkT2@%$$uaAjNlU!BPX!vqS`;)6GaC}CRPD`$8XfS-a zq%%N6o=3XB?-1tZV6G>+#hnew7q=UX^s6Ux> zc5=9Uwc$I9^zh_xg-hoohbvt=KRLYAr3;h8&9F0t`bCg~4w0S&d5z(lN;-tNpr?^8 zhTQN?Cs~rr>MABV8@V)mGf2)&t^|2D$@$4uAkQJWAbA)_k+yy3lO9jn@o~kDGl8_<=OC^#aVqFE-w4u^Xr`Cpr|1zkku)Rq?^Ll9 z(-IP3xvzywLoZq|e1Al&#NMQB-}fj_C++wyK`MzE>~sF)rO_%Qu}?eXurvt)OZ$5Q_a zl8BA`vJM8mN6oLj4y|&fxh1CgHCMC$Lh4*!jOgh~XV6|++R6jB8!vd9+n$YOZmVQ2 zqr$MhNwKxH0pk(hZxJzb02-zB7Bkr!MW}~WbK9CkSiPMIyv6Yda@LQHz#4SBZq@k4u_bM#h}XK5L5CPWFB=iWHM_LYbRS-@ggxb}cBRTmjh%h=85?1WKh9`AG^2FqsXk^}W)03Ku^Iq3{AkI8O)8e9o z?WJPDPVZb~ig8XKFf*Nn3HATZG?kBZZ!CWndVEGN& zmSTHnrc*U21rat&3<*0#Dn;0#@pfayWVW+o6@V0DHHD^~g%){QSMH_^n1pIMeT=Hy z;qh{21_KbZH0)?u>X$$6>Pz5rbMx?DQ(sXVtqkXtH`f{6 zC2%^>UDBP)tF5Vzt~QM3@UpsaeI&PNuP68%LXOGOxZRgzU|KLH=SiKh{b42SC|t7?V*~z zz_-(>-rk}s5b35PBfCpg97oylDFe5hYYk0z(ib5IIxN>0)n)TJxxN>i3}@%gd=&y4 zJB46O%crdLNOAp}FYL~9vZ&`N%k>PsS6B8!zTHtAi}hXcR4GcG^xdVU$Fx2w=LJ?Z zYv~1@Q6#x+J8Ed5E^GHgHd~j?)8N)v#OFyzeH~LqJj)h%2Hm^c(`(jb=h&QdETcEg z=16%{qzu0m%ZS8A~g;5%@EZ$ zj8vH(+1S(&30FiKnpFP_R|YGp%Rz_XR;04LX$>;i91brB)G2o&NN=3#z$>ERXqcfj zSA>zla`-K&ZKz)sl-HIw!C^^R1M9&EbF!}^^E@EcRV9^FQC6X} zkgE#qQiTb+T4kz_8x2)eWf4PFRd{u{BC6f6R5U3Y-JPYxPBqHWN!bcxDGn42*Dp8d zbOnMQ?pT^}FdK28jA%X2N2m`L2zgQ2s)E-RI#sDbPI%N*iMwgml<_WwKJwKKO_5-? z(8eg7!8DgGU4z=fbSj@e1^gKWlhH;*Q+0_JRly2uY^rI1M;IOixPLL~;O3<+%BrkU zxe@;_wGGYTGB|-@T^Qlj@He9(N6KqzaZIlW^So#@Gg~N8b2x&!TUy&tLFY3yWmh!R zBP(dEDo&Von@@B=gNWs-=@<>QmHK$HK_H9GaA|`k#Tr5rb5G3%ZeX|vt)f{~6^?8L z(yLPp4~sr(<&~9a>26)Cwub}Cy8SHAIjDPdjH()V-MPG`s;UN4%&M|ROuF^asi|!= zmZ5-d6{DB2x~j|T>%-!|rXD_dRHLAmp5|J($w6h7h3gto%lZOjG%jmuG{USeUWFLF z$*2W|lw%R9qO~x{&Wb}*(*#rMJfJeJ%gaQRUmu(RR8v)9ILfe#)>FrG0FQ!E2WLB~ zCd;9Zp5BCX(7seVV+w9P=2bV;h4bp8m65!L=8^T`Rr=aGGC#MVU}SCi(!6{v$Xgz6 zLUHqy)1ao6s;&PtBYdSXbig|{4m17R_+xA9W^4(Dg!#Ec-rlvYA z*6jVMxSTUik;tiMOiy*@BY^U`*xi{R)U_|u4 z3-)#Fk!#Jz(|wEYL{vX*XBmTt0P7(DRr93 zU5Z;Onhh_FF2jMXYA|vu6d}+gva1dZ}1^d#M!89K|zY*?UlfXR|#aa$GEP&JkYf3+AA6rKThtV*{0mQf;6c2 zG-h}1=7zC+@#$_sx`&Y%(`6mF=@x@_>#boCxS$1u)-%-vkQRtQMD+gs3!-`ucUASCTp*%9cmFT0zYg_|LWFULld zV+mv|2kXbJ7v61(s|F)yreXXDGIw)L$EV4#%sD6E~@(u|Qjcm8T^e|9)y07FsFu++Cu&B^a$V9ga1Vj zo(}}wYYO8(4c@($kbk9z{%bw>_8$CE@b2}7@p-4s-I!mx^K!2_4Cg~ocVjr8mAKa( zhMxxBz21=5;~~z+Ti=htTC{2y7T&IOK@U&Q_^TE-k3{5_3jM&Y)q8@3Ij2Ena@>RN_)`-Fc}koV!3UaH_gLH1$FM+u%KsM-;4v_$zY1@{a7PVi;HzX%=^#0wfK zo*!+M@%syA3+4+>5~M>S>Mau7E%>6~8-jlm#NB+QkNe09=L#mF;nGfD!BWAn;0nR3 z1zQDg65Jv9sNin}Ul4p<@UMan&lgCqk6@PINWt-fGXyUXyiBk~a5E9dber(|1P_Y* zP2oQf{7B?po{x}zG7<5I3qM_OrpW0|k9u{2%_9Gr@LL7HBl6pXzf1V%gnvo!b& z{8XOzVE=r%9)61F@*M z16LX4{crD)M7TqQ)(}_0jlp5s|y8(wtrC~l^JFZIVRoKhxt~8k}|aQ$%&JY76~ra@F}};Wz~*sC1h=F zp4Hjb#{m)e>9eiRKHJ{bhXrjrg{E6yX#LYC$L?%PVfeACdvutpw-Nhx&@fWe_8G|y zV16Vks@7CCJBGNa(pcLmDq4yk^oZZKKHK`|PhkJZS~y&5e+n|uO$kxA59?&av#r00 z&+D^qx1GY+Z7B>5{Pd-^6lU4{trl!vVYVsjfuA0gkY{uXiAdk6a)JWlRl z_Q&sQ9;^f*>5M(wZHM>B8*sz8U%DxeD_U!oic``v4*l_|9*bB%K(j$CWl#6!Sm*&S z1>E+ljt&Qe!*@`z<%p%CD`|;3PbhioK3z>!t=9faF4T_1Gh2?EkuzJ4TamL7-|A?R z{zN-W>DeQ25b4*^ajxl@Bza+jj0-0VMW-WE_c+zD13%rTBD;ZG{?JNGM}mvZ zo>d#urO|(zV^kpg#ImCr9W!wvrt|eBU|Nn3S~W%-v3DMR0z(_T$IvlU6M>F_F40R9 zjUA5YY@yqAcwqGJC_xmo59NG4cGkvq)IA5Q=J3U5?ZD^6_>8kQyn&)HnT?3?QAZw1 z15fFN$V=v?B>d)YoNa|f80RY!?$ZmAXF5~O++?iZ6Fu-Tm0DxIBI#2yO*KQ-rrY|8 zvy2*SH>O|7VbD=x*9I$aJ6s!nQQz6`jvj2pPSfT5oY+74tk|k#NaG9BzW=jgGeHhwzA)|QJ}Wjm`R#Y$ zM<3F=K%rGRJ4m1zAiBgvNIcHlZ6P1qY&gYP^HU$lb;UlSp$jns8-L?h!^ z=0cC%x<)rj#`bsQ&JW>3SGB}__{UdWl!9RJ*14ZpN`|sGzUck2fWM~ z+d+FTktRh_8JMgbE)ViYla3T4f%f;ILwO1W+bMVz0{Tr>1>Y3XuJjRjI|CmRZ6|t$ zTxbI8?}M!8^~JsJw7-YSruoF^l}e}OaKgrY_c>C|XMwt=q zuP^27VfeZPRgW}(02j&^Gk8uk;mBAd(osUL7~K2tjomSU+`?!o8xEV|y>N2gF-({K z_&8`4!eMhqh6sv~ts)58AHzhu{nz+8;4NW7*g6KO)Bgc|F`-29q1&mT$d==Ql`nTi z&;@`ERiY_@Z|%XD{PtU^%^!6YU5sGnaAI_zm`Gif7H7AePe`bcca18^__d?k`ot1! z^KV!JORWd#KK&pL)n0wf4z?UYVQ*qs`$wojofA}YTrDfjmLs8-<6{EX@tsF>nCqd@ zd3XooA$Q4&D7l@ijE_jVo%;Cus3+b~5&fvv58Y0sIDHJ;*<{>kdl@bKxzQL|9cGy& zxzRQ;8ei)DtkhJ5wiL$I9U2ba(MVe1XM7&xaqYmriO1}<^t{Dkm~LipBde)|V*6CQ<_)iE_j@Ub{fgkYpgYlA2DS0qnGLxsCJK`n3pybAQNd+bA;w8_sYpzh9 zt~)N5W6`aQlILiW9vAe;G6wR)+WJtaubBH*^;JgnNP_a)L-^?kbfg?vio`p7M;ZZJ z(Cstz^){0;+&dsUGF@Gba`t0j+aDL`4Bo8V<--#sj&}AQaRR^GbGyTo_+#$5og>Ku zUS2GDdv=$tHE+uRQ+2?b4G1Q<@evoDyybX8GX19Ie1$iR)CsSn}=GCIB4x@9jBsV)AX<}4P&m1&9ltb+1VMJdT&g_ zuqzFr8EWA9V%KcEtq-d(b|-|DBUAYUUXBO3>0=)PwaY{e@sm7`Z$lF;wX(YU7LVwLI3JUxZ5Q5ie%_6IxfXWbFD`iY*5{-Hh*I z?|Nvuo7OHq1AJ&&jKxJ#*aK?D!h=EUxKpXO{SZHe{jah=A4mTwj&{TUJNOsa8?{nv{1@?Eb55*kmj|guA-VL4K0bj*_ z47(RRW!(G4(XQ;PAk$#FZk$E1&%C(ly7G7|`iwNEK(zGf+$1T5yMyn>7YMj%A+>@RZ}>841IKWe19~4cks= zv``Z~)|PJpetpC6Q;j`=Kb_P#A0q+4xlpui@3&2u)JslnE8#W@P3NCb@$y?Fp5RJE z!~3UKAUi%j<#_;mqO#>Nl59$n1IXsX9{apsBZ7Ym?Adb}%kZZll6`@);D3>p=aF{& ziz&a5wBOI=IrjX?$Z=W<*M!;^QJ!X{gveZSHJA)5Yekj~Jqud@H4bnNdukmGTpsR!otVa!V{^l9kH0 z%j|{g5i?|^>}DYqGtEl*A&Re=Vk?!e-Pwz%cD9vLO#_N4u~HV$v|?siDLZLkF|#w< zO1X~Nxs=RYE9F7PQOtZRg|DG#W`UJ*hz3;1Vk_mISjZCOng%XgkKalw6%T_AdkO2U z+Df^ZA>|CIMIB%@puIGJn2lD-&zb8AG7&2!jn!L8X0??vis^(|*H>97XF+CH&B5VW zXQgsIn_XQ2<`B}sYg_i^?;{**Jd(nVH?fAa~JKm*jp#6T?V^4~$aj`V2% z51F@m(uMwN(ha1?_~(&sBt6#u811hhJwdFUN~9d!yDsBQ$PnnpPc(?YK#yB=V@hiui_!(RjK;TlqV1Zਞ(_ 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 E8yu$yWB>pF literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/kernel/chr_drv/console.c b/linux-0.11-lab/1/linux/kernel/chr_drv/console.c new file mode 100644 index 0000000..a12ffbf --- /dev/null +++ b/linux-0.11-lab/1/linux/kernel/chr_drv/console.c @@ -0,0 +1,710 @@ +/* + * linux/kernel/console.c + * + * (C) 1991 Linus Torvalds + */ + +/* + * console.c + * + * This module implements the console io functions + * 'void con_init(void)' + * 'void con_write(struct tty_queue * queue)' + * Hopefully this will be a rather complete VT102 implementation. + * + * Beeping thanks to John T Kohl. + */ + +/* + * NOTE!!! We sometimes disable and enable interrupts for a short while + * (to put a word in video IO), but this will work even for keyboard + * interrupts. We know interrupts aren't enabled when getting a keyboard + * interrupt, as we use trap-gates. Hopefully all is well. + */ + +/* + * Code to check for different video-cards mostly by Galen Hunt, + * + */ + +#include +#include +#include +#include + +/* + * These are set up by the setup-routine at boot-time: + */ + +#define ORIG_X (*(unsigned char *)0x90000) +#define ORIG_Y (*(unsigned char *)0x90001) +#define ORIG_VIDEO_PAGE (*(unsigned short *)0x90004) +#define ORIG_VIDEO_MODE ((*(unsigned short *)0x90006) & 0xff) +#define ORIG_VIDEO_COLS (((*(unsigned short *)0x90006) & 0xff00) >> 8) +#define ORIG_VIDEO_LINES (25) +#define ORIG_VIDEO_EGA_AX (*(unsigned short *)0x90008) +#define ORIG_VIDEO_EGA_BX (*(unsigned short *)0x9000a) +#define ORIG_VIDEO_EGA_CX (*(unsigned short *)0x9000c) + +#define VIDEO_TYPE_MDA 0x10 /* Monochrome Text Display */ +#define VIDEO_TYPE_CGA 0x11 /* CGA Display */ +#define VIDEO_TYPE_EGAM 0x20 /* EGA/VGA in Monochrome Mode */ +#define VIDEO_TYPE_EGAC 0x21 /* EGA/VGA in Color Mode */ + +#define NPAR 16 + +extern void keyboard_interrupt(void); + +static unsigned char video_type; /* Type of display being used */ +static unsigned long video_num_columns; /* Number of text columns */ +static unsigned long video_size_row; /* Bytes per row */ +static unsigned long video_num_lines; /* Number of test lines */ +static unsigned char video_page; /* Initial video page */ +static unsigned long video_mem_start; /* Start of video RAM */ +static unsigned long video_mem_end; /* End of video RAM (sort of) */ +static unsigned short video_port_reg; /* Video register select port */ +static unsigned short video_port_val; /* Video register value port */ +static unsigned short video_erase_char; /* Char+Attrib to erase with */ + +static unsigned long origin; /* Used for EGA/VGA fast scroll */ +static unsigned long scr_end; /* Used for EGA/VGA fast scroll */ +static unsigned long pos; +static unsigned long x,y; +static unsigned long top,bottom; +static unsigned long state=0; +static unsigned long npar,par[NPAR]; +static unsigned long ques=0; +static unsigned char attr=0x07; + +static void sysbeep(void); + +/* + * this is what the terminal answers to a ESC-Z or csi0c + * query (= vt100 response). + */ +#define RESPONSE "\033[?1;2c" + +/* NOTE! gotoxy thinks x==video_num_columns is ok */ +static inline void gotoxy(unsigned int new_x,unsigned int new_y) +{ + if (new_x > video_num_columns || new_y >= video_num_lines) + return; + x=new_x; + y=new_y; + pos=origin + y*video_size_row + (x<<1); +} + +static inline void set_origin(void) +{ + cli(); + outb_p(12, video_port_reg); + outb_p(0xff&((origin-video_mem_start)>>9), video_port_val); + outb_p(13, video_port_reg); + outb_p(0xff&((origin-video_mem_start)>>1), video_port_val); + sti(); +} + +static void scrup(void) +{ + if (video_type == VIDEO_TYPE_EGAC || video_type == VIDEO_TYPE_EGAM) + { + if (!top && bottom == video_num_lines) { + origin += video_size_row; + pos += video_size_row; + scr_end += video_size_row; + if (scr_end > video_mem_end) { + __asm__("cld\n\t" + "rep\n\t" + "movsl\n\t" + "movl video_num_columns,%1\n\t" + "rep\n\t" + "stosw" + ::"a" (video_erase_char), + "c" ((video_num_lines-1)*video_num_columns>>1), + "D" (video_mem_start), + "S" (origin) + ); + scr_end -= origin-video_mem_start; + pos -= origin-video_mem_start; + origin = video_mem_start; + } else { + __asm__("cld\n\t" + "rep\n\t" + "stosw" + ::"a" (video_erase_char), + "c" (video_num_columns), + "D" (scr_end-video_size_row) + ); + } + set_origin(); + } else { + __asm__("cld\n\t" + "rep\n\t" + "movsl\n\t" + "movl video_num_columns,%%ecx\n\t" + "rep\n\t" + "stosw" + ::"a" (video_erase_char), + "c" ((bottom-top-1)*video_num_columns>>1), + "D" (origin+video_size_row*top), + "S" (origin+video_size_row*(top+1)) + ); + } + } + else /* Not EGA/VGA */ + { + __asm__("cld\n\t" + "rep\n\t" + "movsl\n\t" + "movl video_num_columns,%%ecx\n\t" + "rep\n\t" + "stosw" + ::"a" (video_erase_char), + "c" ((bottom-top-1)*video_num_columns>>1), + "D" (origin+video_size_row*top), + "S" (origin+video_size_row*(top+1)) + ); + } +} + +static void scrdown(void) +{ + if (video_type == VIDEO_TYPE_EGAC || video_type == VIDEO_TYPE_EGAM) + { + __asm__("std\n\t" + "rep\n\t" + "movsl\n\t" + "addl $2,%%edi\n\t" /* %edi has been decremented by 4 */ + "movl video_num_columns,%%ecx\n\t" + "rep\n\t" + "stosw" + ::"a" (video_erase_char), + "c" ((bottom-top-1)*video_num_columns>>1), + "D" (origin+video_size_row*bottom-4), + "S" (origin+video_size_row*(bottom-1)-4) + ); + } + else /* Not EGA/VGA */ + { + __asm__("std\n\t" + "rep\n\t" + "movsl\n\t" + "addl $2,%%edi\n\t" /* %edi has been decremented by 4 */ + "movl video_num_columns,%%ecx\n\t" + "rep\n\t" + "stosw" + ::"a" (video_erase_char), + "c" ((bottom-top-1)*video_num_columns>>1), + "D" (origin+video_size_row*bottom-4), + "S" (origin+video_size_row*(bottom-1)-4) + ); + } +} + +static void lf(void) +{ + if (y+1top) { + y--; + pos -= video_size_row; + return; + } + scrdown(); +} + +static void cr(void) +{ + pos -= x<<1; + x=0; +} + +static void del(void) +{ + if (x) { + pos -= 2; + x--; + *(unsigned short *)pos = video_erase_char; + } +} + +static void csi_J(int par) +{ + long count __asm__("cx"); + long start __asm__("di"); + + switch (par) { + case 0: /* erase from cursor to end of display */ + count = (scr_end-pos)>>1; + start = pos; + break; + case 1: /* erase from start to cursor */ + count = (pos-origin)>>1; + start = origin; + break; + case 2: /* erase whole display */ + count = video_num_columns * video_num_lines; + start = origin; + break; + default: + return; + } + __asm__("cld\n\t" + "rep\n\t" + "stosw\n\t" + ::"c" (count), + "D" (start),"a" (video_erase_char) + ); +} + +static void csi_K(int par) +{ + long count __asm__("cx"); + long start __asm__("di"); + + switch (par) { + case 0: /* erase from cursor to end of line */ + if (x>=video_num_columns) + return; + count = video_num_columns-x; + start = pos; + break; + case 1: /* erase from start of line to cursor */ + start = pos - (x<<1); + count = (x>9), video_port_val); + outb_p(15, video_port_reg); + outb_p(0xff&((pos-video_mem_start)>>1), video_port_val); + sti(); +} + +static void respond(struct tty_struct * tty) +{ + char * p = RESPONSE; + + cli(); + while (*p) { + PUTCH(*p,tty->read_q); + p++; + } + sti(); + copy_to_cooked(tty); +} + +static void insert_char(void) +{ + int i=x; + unsigned short tmp, old = video_erase_char; + unsigned short * p = (unsigned short *) pos; + + while (i++=video_num_columns) + return; + i = x; + while (++i < video_num_columns) { + *p = *(p+1); + p++; + } + *p = video_erase_char; +} + +static void delete_line(void) +{ + int oldtop,oldbottom; + + oldtop=top; + oldbottom=bottom; + top=y; + bottom = video_num_lines; + scrup(); + top=oldtop; + bottom=oldbottom; +} + +static void csi_at(unsigned int nr) +{ + if (nr > video_num_columns) + nr = video_num_columns; + else if (!nr) + nr = 1; + while (nr--) + insert_char(); +} + +static void csi_L(unsigned int nr) +{ + if (nr > video_num_lines) + nr = video_num_lines; + else if (!nr) + nr = 1; + while (nr--) + insert_line(); +} + +static void csi_P(unsigned int nr) +{ + if (nr > video_num_columns) + nr = video_num_columns; + else if (!nr) + nr = 1; + while (nr--) + delete_char(); +} + +static void csi_M(unsigned int nr) +{ + if (nr > video_num_lines) + nr = video_num_lines; + else if (!nr) + nr=1; + while (nr--) + delete_line(); +} + +static int saved_x=0; +static int saved_y=0; + +static void save_cur(void) +{ + saved_x=x; + saved_y=y; +} + +static void restore_cur(void) +{ + gotoxy(saved_x, saved_y); +} + +void con_write(struct tty_struct * tty) +{ + int nr; + char c; + + nr = CHARS(tty->write_q); + while (nr--) { + GETCH(tty->write_q,c); + switch(state) { + case 0: + if (c>31 && c<127) { + if (x>=video_num_columns) { + x -= video_num_columns; + pos -= video_size_row; + lf(); + } + __asm__("movb attr,%%ah\n\t" + "movw %%ax,%1\n\t" + ::"a" (c),"m" (*(short *)pos) + ); + pos += 2; + x++; + } else if (c==27) + state=1; + else if (c==10 || c==11 || c==12) + lf(); + else if (c==13) + cr(); + else if (c==ERASE_CHAR(tty)) + del(); + else if (c==8) { + if (x) { + x--; + pos -= 2; + } + } else if (c==9) { + c=8-(x&7); + x += c; + pos += c<<1; + if (x>video_num_columns) { + x -= video_num_columns; + pos -= video_size_row; + lf(); + } + c=9; + } else if (c==7) + sysbeep(); + break; + case 1: + state=0; + if (c=='[') + state=2; + else if (c=='E') + gotoxy(0,y+1); + else if (c=='M') + ri(); + else if (c=='D') + lf(); + else if (c=='Z') + respond(tty); + else if (x=='7') + save_cur(); + else if (x=='8') + restore_cur(); + break; + case 2: + for(npar=0;npar='0' && c<='9') { + par[npar]=10*par[npar]+c-'0'; + break; + } else state=4; + case 4: + state=0; + switch(c) { + case 'G': case '`': + if (par[0]) par[0]--; + gotoxy(par[0],y); + break; + case 'A': + if (!par[0]) par[0]++; + gotoxy(x,y-par[0]); + break; + case 'B': case 'e': + if (!par[0]) par[0]++; + gotoxy(x,y+par[0]); + break; + case 'C': case 'a': + if (!par[0]) par[0]++; + gotoxy(x+par[0],y); + break; + case 'D': + if (!par[0]) par[0]++; + gotoxy(x-par[0],y); + break; + case 'E': + if (!par[0]) par[0]++; + gotoxy(0,y+par[0]); + break; + case 'F': + if (!par[0]) par[0]++; + gotoxy(0,y-par[0]); + break; + case 'd': + if (par[0]) par[0]--; + gotoxy(x,par[0]); + break; + case 'H': case 'f': + if (par[0]) par[0]--; + if (par[1]) par[1]--; + gotoxy(par[1],par[0]); + break; + case 'J': + csi_J(par[0]); + break; + case 'K': + csi_K(par[0]); + break; + case 'L': + csi_L(par[0]); + break; + case 'M': + csi_M(par[0]); + break; + case 'P': + csi_P(par[0]); + break; + case '@': + csi_at(par[0]); + break; + case 'm': + csi_m(); + break; + case 'r': + if (par[0]) par[0]--; + if (!par[1]) par[1] = video_num_lines; + if (par[0] < par[1] && + par[1] <= video_num_lines) { + top=par[0]; + bottom=par[1]; + } + break; + case 's': + save_cur(); + break; + case 'u': + restore_cur(); + break; + } + } + } + set_cursor(); +} + +/* + * void con_init(void); + * + * This routine initalizes console interrupts, and does nothing + * else. If you want the screen to clear, call tty_write with + * the appropriate escape-sequece. + * + * Reads the information preserved by setup.s to determine the current display + * type and sets everything accordingly. + */ +void con_init(void) +{ + register unsigned char a; + char *display_desc = "????"; + char *display_ptr; + + video_num_columns = ORIG_VIDEO_COLS; + video_size_row = video_num_columns * 2; + video_num_lines = ORIG_VIDEO_LINES; + video_page = ORIG_VIDEO_PAGE; + video_erase_char = 0x0720; + + if (ORIG_VIDEO_MODE == 7) /* Is this a monochrome display? */ + { + video_mem_start = 0xb0000; + video_port_reg = 0x3b4; + video_port_val = 0x3b5; + if ((ORIG_VIDEO_EGA_BX & 0xff) != 0x10) + { + video_type = VIDEO_TYPE_EGAM; + video_mem_end = 0xb8000; + display_desc = "EGAm"; + } + else + { + video_type = VIDEO_TYPE_MDA; + video_mem_end = 0xb2000; + display_desc = "*MDA"; + } + } + else /* If not, it is color. */ + { + video_mem_start = 0xb8000; + video_port_reg = 0x3d4; + video_port_val = 0x3d5; + if ((ORIG_VIDEO_EGA_BX & 0xff) != 0x10) + { + video_type = VIDEO_TYPE_EGAC; + video_mem_end = 0xbc000; + display_desc = "EGAc"; + } + else + { + video_type = VIDEO_TYPE_CGA; + video_mem_end = 0xba000; + display_desc = "*CGA"; + } + } + + /* Let the user known what kind of display driver we are using */ + + display_ptr = ((char *)video_mem_start) + video_size_row - 8; + while (*display_desc) + { + *display_ptr++ = *display_desc++; + display_ptr++; + } + + /* Initialize the variables used for scrolling (mostly EGA/VGA) */ + + origin = video_mem_start; + scr_end = video_mem_start + video_num_lines * video_size_row; + top = 0; + bottom = video_num_lines; + + gotoxy(ORIG_X,ORIG_Y); + set_trap_gate(0x21,&keyboard_interrupt); + outb_p(inb_p(0x21)&0xfd,0x21); + a=inb_p(0x61); + outb_p(a|0x80,0x61); + outb(a,0x61); +} +/* from bsd-net-2: */ + +void sysbeepstop(void) +{ + /* disable counter 2 */ + outb(inb_p(0x61)&0xFC, 0x61); +} + +int beepcount = 0; + +static void sysbeep(void) +{ + /* enable counter 2 */ + outb_p(inb_p(0x61)|3, 0x61); + /* set command for counter 2, 2 byte write */ + outb_p(0xB6, 0x43); + /* send 0x637 for 750 HZ */ + outb_p(0x37, 0x42); + outb(0x06, 0x42); + /* 1/8 second */ + beepcount = HZ/8; +} diff --git a/linux-0.11-lab/1/linux/kernel/chr_drv/console.o b/linux-0.11-lab/1/linux/kernel/chr_drv/console.o new file mode 100644 index 0000000000000000000000000000000000000000..cdb09cf249a683c556a1bd6a57bcc3dbe96270a4 GIT binary patch literal 20896 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" +# 1 "" +# 1 "keyboard.S" + + + + + + + + + + + + + +# 1 "../../include/linux/config.h" 1 + + + + + + + + + + + + + + + + + + + + + +# 36 "../../include/linux/config.h" + +# 47 "../../include/linux/config.h" + +# 14 "keyboard.S" 2 + +.text +.globl keyboard_interrupt + + + + +size = 1024 + +head = 4 +tail = 8 +proc_list = 12 +buf = 16 + +mode: .byte 0 +leds: .byte 2 +e0: .byte 0 + + + + + + +keyboard_interrupt: + pushl %eax + pushl %ebx + pushl %ecx + pushl %edx + push %ds + push %es + movl $0x10,%eax + mov %ax,%ds + mov %ax,%es + xor %al,%al + inb $0x60,%al + cmpb $0xe0,%al + je set_e0 + cmpb $0xe1,%al + je set_e1 + call key_table(,%eax,4) + movb $0,e0 +e0_e1: inb $0x61,%al + jmp 1f +1: jmp 1f +1: orb $0x80,%al + jmp 1f +1: jmp 1f +1: outb %al,$0x61 + jmp 1f +1: jmp 1f +1: andb $0x7F,%al + outb %al,$0x61 + movb $0x20,%al + outb %al,$0x20 + pushl $0 + call do_tty_interrupt + addl $4,%esp + pop %es + pop %ds + popl %edx + popl %ecx + popl %ebx + popl %eax + iret +set_e0: movb $1,e0 + jmp e0_e1 +set_e1: movb $2,e0 + jmp e0_e1 + + + + + + +put_queue: + pushl %ecx + pushl %edx + movl table_list,%edx # read-queue for console + movl head(%edx),%ecx +1: movb %al,buf(%edx,%ecx) + incl %ecx + andl $size-1,%ecx + cmpl tail(%edx),%ecx # buffer full - discard everything + je 3f + shrdl $8,%ebx,%eax + je 2f + shrl $8,%ebx + jmp 1b +2: movl %ecx,head(%edx) + movl proc_list(%edx),%ecx + testl %ecx,%ecx + je 3f + movl $0,(%ecx) +3: popl %edx + popl %ecx + ret + +ctrl: movb $0x04,%al + jmp 1f +alt: movb $0x10,%al +1: cmpb $0,e0 + je 2f + addb %al,%al +2: orb %al,mode + ret +unctrl: movb $0x04,%al + jmp 1f +unalt: movb $0x10,%al +1: cmpb $0,e0 + je 2f + addb %al,%al +2: notb %al + andb %al,mode + ret + +lshift: + orb $0x01,mode + ret +unlshift: + andb $0xfe,mode + ret +rshift: + orb $0x02,mode + ret +unrshift: + andb $0xfd,mode + ret + +caps: testb $0x80,mode + jne 1f + xorb $4,leds + xorb $0x40,mode + orb $0x80,mode +set_leds: + call kb_wait + movb $0xed,%al + outb %al,$0x60 + call kb_wait + movb leds,%al + outb %al,$0x60 + ret +uncaps: andb $0x7f,mode + ret +scroll: + xorb $1,leds + jmp set_leds +num: xorb $2,leds + jmp set_leds + + + + + +cursor: + subb $0x47,%al + jb 1f + cmpb $12,%al + ja 1f + jne cur2 + testb $0x0c,mode + je cur2 + testb $0x30,mode + jne reboot +cur2: cmpb $0x01,e0 + je cur + testb $0x02,leds + je cur + testb $0x03,mode + jne cur + xorl %ebx,%ebx + movb num_table(%eax),%al + jmp put_queue +1: ret + +cur: movb cur_table(%eax),%al + cmpb $'9,%al + ja ok_cur + movb $'~,%ah +ok_cur: shll $16,%eax + movw $0x5b1b,%ax + xorl %ebx,%ebx + jmp put_queue + + + + + +num_table: + .ascii "789 456 1230," + +cur_table: + .ascii "HA5 DGC YB623" + + + + +func: + pushl %eax + pushl %ecx + pushl %edx + call show_stat + popl %edx + popl %ecx + popl %eax + subb $0x3B,%al + jb end_func + cmpb $9,%al + jbe ok_func + subb $18,%al + cmpb $10,%al + jb end_func + cmpb $11,%al + ja end_func +ok_func: + cmpl $4,%ecx + jl end_func + movl func_table(,%eax,4),%eax + xorl %ebx,%ebx + jmp put_queue +end_func: + ret + + + + +func_table: + .long 0x415b5b1b,0x425b5b1b,0x435b5b1b,0x445b5b1b + .long 0x455b5b1b,0x465b5b1b,0x475b5b1b,0x485b5b1b + .long 0x495b5b1b,0x4a5b5b1b,0x4b5b5b1b,0x4c5b5b1b + +# 294 "keyboard.S" + +key_map: + .byte 0,27 + .ascii "1234567890-=" + .byte 127,9 + .ascii "qwertyuiop[]" + .byte 13,0 + .ascii "asdfghjkl;'" + .byte '`,0 + .ascii "\\zxcvbnm,./" + .byte 0,'*,0,32 /* 36-39 */ + .fill 16,1,0 + .byte '-,0,0,0,'+ + .byte 0,0,0,0,0,0,0 + .byte '< + .fill 10,1,0 + + +shift_map: + .byte 0,27 + .ascii "!@#$%^&*()_+" + .byte 127,9 + .ascii "QWERTYUIOP{}" + .byte 13,0 + .ascii "ASDFGHJKL:\"" + .byte '~,0 + .ascii "|ZXCVBNM<>?" + .byte 0,'*,0,32 /* 36-39 */ + .fill 16,1,0 + .byte '-,0,0,0,'+ + .byte 0,0,0,0,0,0,0 + .byte '> + .fill 10,1,0 + +alt_map: + .byte 0,0 + .ascii "\0@\0$\0\0{[]}\\\0" + .byte 0,0 + .byte 0,0,0,0,0,0,0,0,0,0,0 + .byte '~,13,0 + .byte 0,0,0,0,0,0,0,0,0,0,0 + .byte 0,0 + .byte 0,0,0,0,0,0,0,0,0,0,0 + .byte 0,0,0,0 + .fill 16,1,0 + .byte 0,0,0,0,0 + .byte 0,0,0,0,0,0,0 + .byte '| + .fill 10,1,0 + +# 449 "keyboard.S" + + + + +do_self: + lea alt_map,%ebx + testb $0x20,mode + jne 1f + lea shift_map,%ebx + testb $0x03,mode + jne 1f + lea key_map,%ebx +1: movb (%ebx,%eax),%al + orb %al,%al + je none + testb $0x4c,mode + je 2f + cmpb $'a,%al + jb 2f + cmpb $'},%al + ja 2f + subb $32,%al +2: testb $0x0c,mode + je 3f + cmpb $64,%al + jb 3f + cmpb $64+32,%al + jae 3f + subb $64,%al +3: testb $0x10,mode + je 4f + orb $0x80,%al +4: andl $0xff,%eax + xorl %ebx,%ebx + call put_queue +none: ret + + + + + + +minus: cmpb $1,e0 + jne do_self + movl $'/,%eax + xorl %ebx,%ebx + jmp put_queue + + + + + + +key_table: + .long none,do_self,do_self,do_self + .long do_self,do_self,do_self,do_self + .long do_self,do_self,do_self,do_self + .long do_self,do_self,do_self,do_self + .long do_self,do_self,do_self,do_self + .long do_self,do_self,do_self,do_self + .long do_self,do_self,do_self,do_self + .long do_self,ctrl,do_self,do_self + .long do_self,do_self,do_self,do_self + .long do_self,do_self,do_self,do_self + .long do_self,do_self,lshift,do_self + .long do_self,do_self,do_self,do_self + .long do_self,do_self,do_self,do_self + .long do_self,minus,rshift,do_self + .long alt,do_self,caps,func + .long func,func,func,func + .long func,func,func,func + .long func,num,scroll,cursor + .long cursor,cursor,do_self,cursor + .long cursor,cursor,do_self,cursor + .long cursor,cursor,cursor,cursor + .long none,none,do_self,func + .long func,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,unctrl,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,unlshift,none + .long none,none,none,none + .long none,none,none,none + .long none,none,unrshift,none + .long unalt,none,uncaps,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + .long none,none,none,none + + + + + +kb_wait: + pushl %eax +1: inb $0x64,%al + testb $0x02,%al + jne 1b + popl %eax + ret + + + + +reboot: + call kb_wait + movw $0x1234,0x472 + movb $0xfc,%al + outb %al,$0x64 +die: jmp die diff --git a/linux-0.11-lab/1/linux/kernel/chr_drv/keyboard.S b/linux-0.11-lab/1/linux/kernel/chr_drv/keyboard.S new file mode 100644 index 0000000..25210b4 --- /dev/null +++ b/linux-0.11-lab/1/linux/kernel/chr_drv/keyboard.S @@ -0,0 +1,588 @@ +/* + * linux/kernel/keyboard.S + * + * (C) 1991 Linus Torvalds + */ + +/* + * Thanks to Alfred Leung for US keyboard patches + * Wolfgang Thiel for German keyboard patches + * Marc Corsini for the French keyboard + */ + +#include + +.text +.globl keyboard_interrupt + +/* + * these are for the keyboard read functions + */ +size = 1024 /* must be a power of two ! And MUST be the same + as in tty_io.c !!!! */ +head = 4 +tail = 8 +proc_list = 12 +buf = 16 + +mode: .byte 0 /* caps, alt, ctrl and shift mode */ +leds: .byte 2 /* num-lock, caps, scroll-lock mode (nom-lock on) */ +e0: .byte 0 + +/* + * con_int is the real interrupt routine that reads the + * keyboard scan-code and converts it into the appropriate + * ascii character(s). + */ +keyboard_interrupt: + pushl %eax + pushl %ebx + pushl %ecx + pushl %edx + push %ds + push %es + movl $0x10,%eax + mov %ax,%ds + mov %ax,%es + xor %al,%al /* %eax is scan code */ + inb $0x60,%al + cmpb $0xe0,%al + je set_e0 + cmpb $0xe1,%al + je set_e1 + call key_table(,%eax,4) + movb $0,e0 +e0_e1: inb $0x61,%al + jmp 1f +1: jmp 1f +1: orb $0x80,%al + jmp 1f +1: jmp 1f +1: outb %al,$0x61 + jmp 1f +1: jmp 1f +1: andb $0x7F,%al + outb %al,$0x61 + movb $0x20,%al + outb %al,$0x20 + pushl $0 + call do_tty_interrupt + addl $4,%esp + pop %es + pop %ds + popl %edx + popl %ecx + popl %ebx + popl %eax + iret +set_e0: movb $1,e0 + jmp e0_e1 +set_e1: movb $2,e0 + jmp e0_e1 + +/* + * This routine fills the buffer with max 8 bytes, taken from + * %ebx:%eax. (%edx is high). The bytes are written in the + * order %al,%ah,%eal,%eah,%bl,%bh ... until %eax is zero. + */ +put_queue: + pushl %ecx + pushl %edx + movl table_list,%edx # read-queue for console + movl head(%edx),%ecx +1: movb %al,buf(%edx,%ecx) + incl %ecx + andl $size-1,%ecx + cmpl tail(%edx),%ecx # buffer full - discard everything + je 3f + shrdl $8,%ebx,%eax + je 2f + shrl $8,%ebx + jmp 1b +2: movl %ecx,head(%edx) + movl proc_list(%edx),%ecx + testl %ecx,%ecx + je 3f + movl $0,(%ecx) +3: popl %edx + popl %ecx + ret + +ctrl: movb $0x04,%al + jmp 1f +alt: movb $0x10,%al +1: cmpb $0,e0 + je 2f + addb %al,%al +2: orb %al,mode + ret +unctrl: movb $0x04,%al + jmp 1f +unalt: movb $0x10,%al +1: cmpb $0,e0 + je 2f + addb %al,%al +2: notb %al + andb %al,mode + ret + +lshift: + orb $0x01,mode + ret +unlshift: + andb $0xfe,mode + ret +rshift: + orb $0x02,mode + ret +unrshift: + andb $0xfd,mode + ret + +caps: testb $0x80,mode + jne 1f + xorb $4,leds + xorb $0x40,mode + orb $0x80,mode +set_leds: + call kb_wait + movb $0xed,%al /* set leds command */ + outb %al,$0x60 + call kb_wait + movb leds,%al + outb %al,$0x60 + ret +uncaps: andb $0x7f,mode + ret +scroll: + xorb $1,leds + jmp set_leds +num: xorb $2,leds + jmp set_leds + +/* + * curosr-key/numeric keypad cursor keys are handled here. + * checking for numeric keypad etc. + */ +cursor: + subb $0x47,%al + jb 1f + cmpb $12,%al + ja 1f + jne cur2 /* check for ctrl-alt-del */ + testb $0x0c,mode + je cur2 + testb $0x30,mode + jne reboot +cur2: cmpb $0x01,e0 /* e0 forces cursor movement */ + je cur + testb $0x02,leds /* not num-lock forces cursor */ + je cur + testb $0x03,mode /* shift forces cursor */ + jne cur + xorl %ebx,%ebx + movb num_table(%eax),%al + jmp put_queue +1: ret + +cur: movb cur_table(%eax),%al + cmpb $'9,%al + ja ok_cur + movb $'~,%ah +ok_cur: shll $16,%eax + movw $0x5b1b,%ax + xorl %ebx,%ebx + jmp put_queue + +#if defined(KBD_FR) +num_table: + .ascii "789 456 1230." +#else +num_table: + .ascii "789 456 1230," +#endif +cur_table: + .ascii "HA5 DGC YB623" + +/* + * this routine handles function keys + */ +func: + pushl %eax + pushl %ecx + pushl %edx + call show_stat + popl %edx + popl %ecx + popl %eax + subb $0x3B,%al + jb end_func + cmpb $9,%al + jbe ok_func + subb $18,%al + cmpb $10,%al + jb end_func + cmpb $11,%al + ja end_func +ok_func: + cmpl $4,%ecx /* check that there is enough room */ + jl end_func + movl func_table(,%eax,4),%eax + xorl %ebx,%ebx + jmp put_queue +end_func: + ret + +/* + * function keys send F1:'esc [ [ A' F2:'esc [ [ B' etc. + */ +func_table: + .long 0x415b5b1b,0x425b5b1b,0x435b5b1b,0x445b5b1b + .long 0x455b5b1b,0x465b5b1b,0x475b5b1b,0x485b5b1b + .long 0x495b5b1b,0x4a5b5b1b,0x4b5b5b1b,0x4c5b5b1b + +#if defined(KBD_FINNISH) +key_map: + .byte 0,27 + .ascii "1234567890+'" + .byte 127,9 + .ascii "qwertyuiop}" + .byte 0,13,0 + .ascii "asdfghjkl|{" + .byte 0,0 + .ascii "'zxcvbnm,.-" + .byte 0,'*,0,32 /* 36-39 */ + .fill 16,1,0 /* 3A-49 */ + .byte '-,0,0,0,'+ /* 4A-4E */ + .byte 0,0,0,0,0,0,0 /* 4F-55 */ + .byte '< + .fill 10,1,0 + +shift_map: + .byte 0,27 + .ascii "!\"#$%&/()=?`" + .byte 127,9 + .ascii "QWERTYUIOP]^" + .byte 13,0 + .ascii "ASDFGHJKL\\[" + .byte 0,0 + .ascii "*ZXCVBNM;:_" + .byte 0,'*,0,32 /* 36-39 */ + .fill 16,1,0 /* 3A-49 */ + .byte '-,0,0,0,'+ /* 4A-4E */ + .byte 0,0,0,0,0,0,0 /* 4F-55 */ + .byte '> + .fill 10,1,0 + +alt_map: + .byte 0,0 + .ascii "\0@\0$\0\0{[]}\\\0" + .byte 0,0 + .byte 0,0,0,0,0,0,0,0,0,0,0 + .byte '~,13,0 + .byte 0,0,0,0,0,0,0,0,0,0,0 + .byte 0,0 + .byte 0,0,0,0,0,0,0,0,0,0,0 + .byte 0,0,0,0 /* 36-39 */ + .fill 16,1,0 /* 3A-49 */ + .byte 0,0,0,0,0 /* 4A-4E */ + .byte 0,0,0,0,0,0,0 /* 4F-55 */ + .byte '| + .fill 10,1,0 + +#elif defined(KBD_US) + +key_map: + .byte 0,27 + .ascii "1234567890-=" + .byte 127,9 + .ascii "qwertyuiop[]" + .byte 13,0 + .ascii "asdfghjkl;'" + .byte '`,0 + .ascii "\\zxcvbnm,./" + .byte 0,'*,0,32 /* 36-39 */ + .fill 16,1,0 /* 3A-49 */ + .byte '-,0,0,0,'+ /* 4A-4E */ + .byte 0,0,0,0,0,0,0 /* 4F-55 */ + .byte '< + .fill 10,1,0 + + +shift_map: + .byte 0,27 + .ascii "!@#$%^&*()_+" + .byte 127,9 + .ascii "QWERTYUIOP{}" + .byte 13,0 + .ascii "ASDFGHJKL:\"" + .byte '~,0 + .ascii "|ZXCVBNM<>?" + .byte 0,'*,0,32 /* 36-39 */ + .fill 16,1,0 /* 3A-49 */ + .byte '-,0,0,0,'+ /* 4A-4E */ + .byte 0,0,0,0,0,0,0 /* 4F-55 */ + .byte '> + .fill 10,1,0 + +alt_map: + .byte 0,0 + .ascii "\0@\0$\0\0{[]}\\\0" + .byte 0,0 + .byte 0,0,0,0,0,0,0,0,0,0,0 + .byte '~,13,0 + .byte 0,0,0,0,0,0,0,0,0,0,0 + .byte 0,0 + .byte 0,0,0,0,0,0,0,0,0,0,0 + .byte 0,0,0,0 /* 36-39 */ + .fill 16,1,0 /* 3A-49 */ + .byte 0,0,0,0,0 /* 4A-4E */ + .byte 0,0,0,0,0,0,0 /* 4F-55 */ + .byte '| + .fill 10,1,0 + +#elif defined(KBD_GR) + +key_map: + .byte 0,27 + .ascii "1234567890\\'" + .byte 127,9 + .ascii "qwertzuiop@+" + .byte 13,0 + .ascii "asdfghjkl[]^" + .byte 0,'# + .ascii "yxcvbnm,.-" + .byte 0,'*,0,32 /* 36-39 */ + .fill 16,1,0 /* 3A-49 */ + .byte '-,0,0,0,'+ /* 4A-4E */ + .byte 0,0,0,0,0,0,0 /* 4F-55 */ + .byte '< + .fill 10,1,0 + + +shift_map: + .byte 0,27 + .ascii "!\"#$%&/()=?`" + .byte 127,9 + .ascii "QWERTZUIOP\\*" + .byte 13,0 + .ascii "ASDFGHJKL{}~" + .byte 0,'' + .ascii "YXCVBNM;:_" + .byte 0,'*,0,32 /* 36-39 */ + .fill 16,1,0 /* 3A-49 */ + .byte '-,0,0,0,'+ /* 4A-4E */ + .byte 0,0,0,0,0,0,0 /* 4F-55 */ + .byte '> + .fill 10,1,0 + +alt_map: + .byte 0,0 + .ascii "\0@\0$\0\0{[]}\\\0" + .byte 0,0 + .byte '@,0,0,0,0,0,0,0,0,0,0 + .byte '~,13,0 + .byte 0,0,0,0,0,0,0,0,0,0,0 + .byte 0,0 + .byte 0,0,0,0,0,0,0,0,0,0,0 + .byte 0,0,0,0 /* 36-39 */ + .fill 16,1,0 /* 3A-49 */ + .byte 0,0,0,0,0 /* 4A-4E */ + .byte 0,0,0,0,0,0,0 /* 4F-55 */ + .byte '| + .fill 10,1,0 + + +#elif defined(KBD_FR) + +key_map: + .byte 0,27 + .ascii "&{\"'(-}_/@)=" + .byte 127,9 + .ascii "azertyuiop^$" + .byte 13,0 + .ascii "qsdfghjklm|" + .byte '`,0,42 /* coin sup gauche, don't know, [*|mu] */ + .ascii "wxcvbn,;:!" + .byte 0,'*,0,32 /* 36-39 */ + .fill 16,1,0 /* 3A-49 */ + .byte '-,0,0,0,'+ /* 4A-4E */ + .byte 0,0,0,0,0,0,0 /* 4F-55 */ + .byte '< + .fill 10,1,0 + +shift_map: + .byte 0,27 + .ascii "1234567890]+" + .byte 127,9 + .ascii "AZERTYUIOP<>" + .byte 13,0 + .ascii "QSDFGHJKLM%" + .byte '~,0,'# + .ascii "WXCVBN?./\\" + .byte 0,'*,0,32 /* 36-39 */ + .fill 16,1,0 /* 3A-49 */ + .byte '-,0,0,0,'+ /* 4A-4E */ + .byte 0,0,0,0,0,0,0 /* 4F-55 */ + .byte '> + .fill 10,1,0 + +alt_map: + .byte 0,0 + .ascii "\0~#{[|`\\^@]}" + .byte 0,0 + .byte '@,0,0,0,0,0,0,0,0,0,0 + .byte '~,13,0 + .byte 0,0,0,0,0,0,0,0,0,0,0 + .byte 0,0 + .byte 0,0,0,0,0,0,0,0,0,0,0 + .byte 0,0,0,0 /* 36-39 */ + .fill 16,1,0 /* 3A-49 */ + .byte 0,0,0,0,0 /* 4A-4E */ + .byte 0,0,0,0,0,0,0 /* 4F-55 */ + .byte '| + .fill 10,1,0 + +#else +#error "KBD-type not defined" +#endif +/* + * do_self handles "normal" keys, ie keys that don't change meaning + * and which have just one character returns. + */ +do_self: + lea alt_map,%ebx + testb $0x20,mode /* alt-gr */ + jne 1f + lea shift_map,%ebx + testb $0x03,mode + jne 1f + lea key_map,%ebx +1: movb (%ebx,%eax),%al + orb %al,%al + je none + testb $0x4c,mode /* ctrl or caps */ + je 2f + cmpb $'a,%al + jb 2f + cmpb $'},%al + ja 2f + subb $32,%al +2: testb $0x0c,mode /* ctrl */ + je 3f + cmpb $64,%al + jb 3f + cmpb $64+32,%al + jae 3f + subb $64,%al +3: testb $0x10,mode /* left alt */ + je 4f + orb $0x80,%al +4: andl $0xff,%eax + xorl %ebx,%ebx + call put_queue +none: ret + +/* + * minus has a routine of it's own, as a 'E0h' before + * the scan code for minus means that the numeric keypad + * slash was pushed. + */ +minus: cmpb $1,e0 + jne do_self + movl $'/,%eax + xorl %ebx,%ebx + jmp put_queue + +/* + * This table decides which routine to call when a scan-code has been + * gotten. Most routines just call do_self, or none, depending if + * they are make or break. + */ +key_table: + .long none,do_self,do_self,do_self /* 00-03 s0 esc 1 2 */ + .long do_self,do_self,do_self,do_self /* 04-07 3 4 5 6 */ + .long do_self,do_self,do_self,do_self /* 08-0B 7 8 9 0 */ + .long do_self,do_self,do_self,do_self /* 0C-0F + ' bs tab */ + .long do_self,do_self,do_self,do_self /* 10-13 q w e r */ + .long do_self,do_self,do_self,do_self /* 14-17 t y u i */ + .long do_self,do_self,do_self,do_self /* 18-1B o p } ^ */ + .long do_self,ctrl,do_self,do_self /* 1C-1F enter ctrl a s */ + .long do_self,do_self,do_self,do_self /* 20-23 d f g h */ + .long do_self,do_self,do_self,do_self /* 24-27 j k l | */ + .long do_self,do_self,lshift,do_self /* 28-2B { para lshift , */ + .long do_self,do_self,do_self,do_self /* 2C-2F z x c v */ + .long do_self,do_self,do_self,do_self /* 30-33 b n m , */ + .long do_self,minus,rshift,do_self /* 34-37 . - rshift * */ + .long alt,do_self,caps,func /* 38-3B alt sp caps f1 */ + .long func,func,func,func /* 3C-3F f2 f3 f4 f5 */ + .long func,func,func,func /* 40-43 f6 f7 f8 f9 */ + .long func,num,scroll,cursor /* 44-47 f10 num scr home */ + .long cursor,cursor,do_self,cursor /* 48-4B up pgup - left */ + .long cursor,cursor,do_self,cursor /* 4C-4F n5 right + end */ + .long cursor,cursor,cursor,cursor /* 50-53 dn pgdn ins del */ + .long none,none,do_self,func /* 54-57 sysreq ? < f11 */ + .long func,none,none,none /* 58-5B f12 ? ? ? */ + .long none,none,none,none /* 5C-5F ? ? ? ? */ + .long none,none,none,none /* 60-63 ? ? ? ? */ + .long none,none,none,none /* 64-67 ? ? ? ? */ + .long none,none,none,none /* 68-6B ? ? ? ? */ + .long none,none,none,none /* 6C-6F ? ? ? ? */ + .long none,none,none,none /* 70-73 ? ? ? ? */ + .long none,none,none,none /* 74-77 ? ? ? ? */ + .long none,none,none,none /* 78-7B ? ? ? ? */ + .long none,none,none,none /* 7C-7F ? ? ? ? */ + .long none,none,none,none /* 80-83 ? br br br */ + .long none,none,none,none /* 84-87 br br br br */ + .long none,none,none,none /* 88-8B br br br br */ + .long none,none,none,none /* 8C-8F br br br br */ + .long none,none,none,none /* 90-93 br br br br */ + .long none,none,none,none /* 94-97 br br br br */ + .long none,none,none,none /* 98-9B br br br br */ + .long none,unctrl,none,none /* 9C-9F br unctrl br br */ + .long none,none,none,none /* A0-A3 br br br br */ + .long none,none,none,none /* A4-A7 br br br br */ + .long none,none,unlshift,none /* A8-AB br br unlshift br */ + .long none,none,none,none /* AC-AF br br br br */ + .long none,none,none,none /* B0-B3 br br br br */ + .long none,none,unrshift,none /* B4-B7 br br unrshift br */ + .long unalt,none,uncaps,none /* B8-BB unalt br uncaps br */ + .long none,none,none,none /* BC-BF br br br br */ + .long none,none,none,none /* C0-C3 br br br br */ + .long none,none,none,none /* C4-C7 br br br br */ + .long none,none,none,none /* C8-CB br br br br */ + .long none,none,none,none /* CC-CF br br br br */ + .long none,none,none,none /* D0-D3 br br br br */ + .long none,none,none,none /* D4-D7 br br br br */ + .long none,none,none,none /* D8-DB br ? ? ? */ + .long none,none,none,none /* DC-DF ? ? ? ? */ + .long none,none,none,none /* E0-E3 e0 e1 ? ? */ + .long none,none,none,none /* E4-E7 ? ? ? ? */ + .long none,none,none,none /* E8-EB ? ? ? ? */ + .long none,none,none,none /* EC-EF ? ? ? ? */ + .long none,none,none,none /* F0-F3 ? ? ? ? */ + .long none,none,none,none /* F4-F7 ? ? ? ? */ + .long none,none,none,none /* F8-FB ? ? ? ? */ + .long none,none,none,none /* FC-FF ? ? ? ? */ + +/* + * kb_wait waits for the keyboard controller buffer to empty. + * there is no timeout - if the buffer doesn't empty, we hang. + */ +kb_wait: + pushl %eax +1: inb $0x64,%al + testb $0x02,%al + jne 1b + popl %eax + ret +/* + * This routine reboots the machine by asking the keyboard + * controller to pulse the reset-line low. + */ +reboot: + call kb_wait + movw $0x1234,0x472 /* don't do memory check */ + movb $0xfc,%al /* pulse reset and A20 low */ + outb %al,$0x64 +die: jmp die diff --git a/linux-0.11-lab/1/linux/kernel/chr_drv/rs_io.o b/linux-0.11-lab/1/linux/kernel/chr_drv/rs_io.o new file mode 100644 index 0000000000000000000000000000000000000000..9d7d5b3a22aa1a7d33dea95b723af176ee68e951 GIT binary patch literal 1320 zcma)5O=}ZT6upy7lN1_>vDAuUi$oC$(TZ-YF8rt{7SvR*(+bl`=7mYg$1w9^jTe}J1pL8J+VS-DUc@11#5ry}TuH|L!9&O7g8W*$#YU6UjU z!jd2kzZJlJAu zYUu}^X)*0615dy3#7CS5;3%o*n6o2-mX*|mBJ()SkJ>Kxy3mDOdS@N-cB{sLjja`nuw?{k1!T?BECWK1Ur++2eHxq=#!x{gli&& zBRH@@L{yj;>c8RMuaxqliKJ!!PW(mv0M`reH^_6neMo3eLAl-mBy=A^x!y36flz|$ z9Yaq056bmU5ZT?V>*Z0VgF%1b96oaqeG&Pkh$c>dL{JjkL^3ZF1^Vqn>-rt20MOw)mDl`5E4qoh_V zHiu%f3^vy+-ZaTqsdKQH=_9M_uuwBq{86e5Y7L#$RJ8J@4U1NVGqq%B7P>V(VAV>U z?KNO{nOQ2UnY@MR;}pv*t7+mQ_L+$Cmk2hbH&o7BkuiEb(opct5uPWFopkSn(*o}a PoD +#include +#include +#include + +#define WAKEUP_CHARS (TTY_BUF_SIZE/4) + +extern void rs1_interrupt(void); +extern void rs2_interrupt(void); + +static void init(int port) +{ + outb_p(0x80,port+3); /* set DLAB of line control reg */ + outb_p(0x30,port); /* LS of divisor (48 -> 2400 bps */ + outb_p(0x00,port+1); /* MS of divisor */ + outb_p(0x03,port+3); /* reset DLAB */ + outb_p(0x0b,port+4); /* set DTR,RTS, OUT_2 */ + outb_p(0x0d,port+1); /* enable all intrs but writes */ + (void)inb(port); /* read data port to reset things (?) */ +} + +void rs_init(void) +{ + set_intr_gate(0x24,rs1_interrupt); + set_intr_gate(0x23,rs2_interrupt); + init(tty_table[1].read_q.data); + init(tty_table[2].read_q.data); + outb(inb_p(0x21)&0xE7,0x21); +} + +/* + * This routine gets called when tty_write has put something into + * the write_queue. It must check wheter the queue is empty, and + * set the interrupt register accordingly + * + * void _rs_write(struct tty_struct * tty); + */ +void rs_write(struct tty_struct * tty) +{ + cli(); + if (!EMPTY(tty->write_q)) + outb(inb_p(tty->write_q.data+1)|0x02,tty->write_q.data+1); + sti(); +} diff --git a/linux-0.11-lab/1/linux/kernel/chr_drv/serial.o b/linux-0.11-lab/1/linux/kernel/chr_drv/serial.o new file mode 100644 index 0000000000000000000000000000000000000000..bf80e08be94a19c3982f10989e20a6e929a1d240 GIT binary patch literal 6752 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 +#include +#include + +#define ALRMMASK (1<<(SIGALRM-1)) +#define KILLMASK (1<<(SIGKILL-1)) +#define INTMASK (1<<(SIGINT-1)) +#define QUITMASK (1<<(SIGQUIT-1)) +#define TSTPMASK (1<<(SIGTSTP-1)) + +#include +#include +#include +#include + +#define _L_FLAG(tty,f) ((tty)->termios.c_lflag & f) +#define _I_FLAG(tty,f) ((tty)->termios.c_iflag & f) +#define _O_FLAG(tty,f) ((tty)->termios.c_oflag & f) + +#define L_CANON(tty) _L_FLAG((tty),ICANON) +#define L_ISIG(tty) _L_FLAG((tty),ISIG) +#define L_ECHO(tty) _L_FLAG((tty),ECHO) +#define L_ECHOE(tty) _L_FLAG((tty),ECHOE) +#define L_ECHOK(tty) _L_FLAG((tty),ECHOK) +#define L_ECHOCTL(tty) _L_FLAG((tty),ECHOCTL) +#define L_ECHOKE(tty) _L_FLAG((tty),ECHOKE) + +#define I_UCLC(tty) _I_FLAG((tty),IUCLC) +#define I_NLCR(tty) _I_FLAG((tty),INLCR) +#define I_CRNL(tty) _I_FLAG((tty),ICRNL) +#define I_NOCR(tty) _I_FLAG((tty),IGNCR) + +#define O_POST(tty) _O_FLAG((tty),OPOST) +#define O_NLCR(tty) _O_FLAG((tty),ONLCR) +#define O_CRNL(tty) _O_FLAG((tty),OCRNL) +#define O_NLRET(tty) _O_FLAG((tty),ONLRET) +#define O_LCUC(tty) _O_FLAG((tty),OLCUC) + +struct tty_struct tty_table[] = { + { + {ICRNL, /* change incoming CR to NL */ + OPOST|ONLCR, /* change outgoing NL to CRNL */ + 0, + ISIG | ICANON | ECHO | ECHOCTL | ECHOKE, + 0, /* console termio */ + INIT_C_CC}, + 0, /* initial pgrp */ + 0, /* initial stopped */ + con_write, + {0,0,0,0,""}, /* console read-queue */ + {0,0,0,0,""}, /* console write-queue */ + {0,0,0,0,""} /* console secondary queue */ + },{ + {0, /* no translation */ + 0, /* no translation */ + B2400 | CS8, + 0, + 0, + INIT_C_CC}, + 0, + 0, + rs_write, + {0x3f8,0,0,0,""}, /* rs 1 */ + {0x3f8,0,0,0,""}, + {0,0,0,0,""} + },{ + {0, /* no translation */ + 0, /* no translation */ + B2400 | CS8, + 0, + 0, + INIT_C_CC}, + 0, + 0, + rs_write, + {0x2f8,0,0,0,""}, /* rs 2 */ + {0x2f8,0,0,0,""}, + {0,0,0,0,""} + } +}; + +/* + * these are the tables used by the machine code handlers. + * you can implement pseudo-tty's or something by changing + * them. Currently not done. + */ +struct tty_queue * table_list[]={ + &tty_table[0].read_q, &tty_table[0].write_q, + &tty_table[1].read_q, &tty_table[1].write_q, + &tty_table[2].read_q, &tty_table[2].write_q + }; + +void tty_init(void) +{ + rs_init(); + con_init(); +} + +void tty_intr(struct tty_struct * tty, int mask) +{ + int i; + + if (tty->pgrp <= 0) + return; + for (i=0;ipgrp==tty->pgrp) + task[i]->signal |= mask; +} + +static void sleep_if_empty(struct tty_queue * queue) +{ + cli(); + while (!current->signal && EMPTY(*queue)) + interruptible_sleep_on(&queue->proc_list); + sti(); +} + +static void sleep_if_full(struct tty_queue * queue) +{ + if (!FULL(*queue)) + return; + cli(); + while (!current->signal && LEFT(*queue)<128) + interruptible_sleep_on(&queue->proc_list); + sti(); +} + +void wait_for_keypress(void) +{ + sleep_if_empty(&tty_table[0].secondary); +} + +void copy_to_cooked(struct tty_struct * tty) +{ + signed char c; + + while (!EMPTY(tty->read_q) && !FULL(tty->secondary)) { + GETCH(tty->read_q,c); + if (c==13) + if (I_CRNL(tty)) + c=10; + else if (I_NOCR(tty)) + continue; + else ; + else if (c==10 && I_NLCR(tty)) + c=13; + if (I_UCLC(tty)) + c=tolower(c); + if (L_CANON(tty)) { + if (c==KILL_CHAR(tty)) { + /* deal with killing the input line */ + while(!(EMPTY(tty->secondary) || + (c=LAST(tty->secondary))==10 || + c==EOF_CHAR(tty))) { + if (L_ECHO(tty)) { + if (c<32) + PUTCH(127,tty->write_q); + PUTCH(127,tty->write_q); + tty->write(tty); + } + DEC(tty->secondary.head); + } + continue; + } + if (c==ERASE_CHAR(tty)) { + if (EMPTY(tty->secondary) || + (c=LAST(tty->secondary))==10 || + c==EOF_CHAR(tty)) + continue; + if (L_ECHO(tty)) { + if (c<32) + PUTCH(127,tty->write_q); + PUTCH(127,tty->write_q); + tty->write(tty); + } + DEC(tty->secondary.head); + continue; + } + if (c==STOP_CHAR(tty)) { + tty->stopped=1; + continue; + } + if (c==START_CHAR(tty)) { + tty->stopped=0; + continue; + } + } + if (L_ISIG(tty)) { + if (c==INTR_CHAR(tty)) { + tty_intr(tty,INTMASK); + continue; + } + if (c==QUIT_CHAR(tty)) { + tty_intr(tty,QUITMASK); + continue; + } + } + if (c==10 || c==EOF_CHAR(tty)) + tty->secondary.data++; + if (L_ECHO(tty)) { + if (c==10) { + PUTCH(10,tty->write_q); + PUTCH(13,tty->write_q); + } else if (c<32) { + if (L_ECHOCTL(tty)) { + PUTCH('^',tty->write_q); + PUTCH(c+64,tty->write_q); + } + } else + PUTCH(c,tty->write_q); + tty->write(tty); + } + PUTCH(c,tty->secondary); + } + wake_up(&tty->secondary.proc_list); +} + +int tty_read(unsigned channel, char * buf, int nr) +{ + struct tty_struct * tty; + char c, * b=buf; + int minimum,time,flag=0; + long oldalarm; + + if (channel>2 || nr<0) return -1; + tty = &tty_table[channel]; + oldalarm = current->alarm; + time = 10L*tty->termios.c_cc[VTIME]; + minimum = tty->termios.c_cc[VMIN]; + if (time && !minimum) { + minimum=1; + if (flag=(!oldalarm || time+jiffiesalarm = time+jiffies; + } + if (minimum>nr) + minimum=nr; + while (nr>0) { + if (flag && (current->signal & ALRMMASK)) { + current->signal &= ~ALRMMASK; + break; + } + if (current->signal) + break; + if (EMPTY(tty->secondary) || (L_CANON(tty) && + !tty->secondary.data && LEFT(tty->secondary)>20)) { + sleep_if_empty(&tty->secondary); + continue; + } + do { + GETCH(tty->secondary,c); + if (c==EOF_CHAR(tty) || c==10) + tty->secondary.data--; + if (c==EOF_CHAR(tty) && L_CANON(tty)) + return (b-buf); + else { + put_fs_byte(c,b++); + if (!--nr) + break; + } + } while (nr>0 && !EMPTY(tty->secondary)); + if (time && !L_CANON(tty)) + if (flag=(!oldalarm || time+jiffiesalarm = time+jiffies; + else + current->alarm = oldalarm; + if (L_CANON(tty)) { + if (b-buf) + break; + } else if (b-buf >= minimum) + break; + } + current->alarm = oldalarm; + if (current->signal && !(b-buf)) + return -EINTR; + return (b-buf); +} + +int tty_write(unsigned channel, char * buf, int nr) +{ + static cr_flag=0; + struct tty_struct * tty; + char c, *b=buf; + + if (channel>2 || nr<0) return -1; + tty = channel + tty_table; + while (nr>0) { + sleep_if_full(&tty->write_q); + if (current->signal) + break; + while (nr>0 && !FULL(tty->write_q)) { + c=get_fs_byte(b); + if (O_POST(tty)) { + if (c=='\r' && O_CRNL(tty)) + c='\n'; + else if (c=='\n' && O_NLRET(tty)) + c='\r'; + if (c=='\n' && !cr_flag && O_NLCR(tty)) { + cr_flag = 1; + PUTCH(13,tty->write_q); + continue; + } + if (O_LCUC(tty)) + c=toupper(c); + } + b++; nr--; + cr_flag = 0; + PUTCH(c,tty->write_q); + } + tty->write(tty); + if (nr>0) + schedule(); + } + return (b-buf); +} + +/* + * Jeh, sometimes I really like the 386. + * This routine is called from an interrupt, + * and there should be absolutely no problem + * with sleeping even in an interrupt (I hope). + * Of course, if somebody proves me wrong, I'll + * hate intel for all time :-). We'll have to + * be careful and see to reinstating the interrupt + * chips before calling this, though. + * + * I don't think we sleep here under normal circumstances + * anyway, which is good, as the task sleeping might be + * totally innocent. + */ +void do_tty_interrupt(int tty) +{ + copy_to_cooked(tty_table+tty); +} + +void chr_dev_init(void) +{ +} diff --git a/linux-0.11-lab/1/linux/kernel/chr_drv/tty_io.o b/linux-0.11-lab/1/linux/kernel/chr_drv/tty_io.o new file mode 100644 index 0000000000000000000000000000000000000000..37e2b15961ebc5713d826d6c25e53571ac6fbb83 GIT binary patch literal 22504 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 O^kQA0pRj`M3jQCx0hyNo literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/kernel/chr_drv/tty_ioctl.c b/linux-0.11-lab/1/linux/kernel/chr_drv/tty_ioctl.c new file mode 100644 index 0000000..e4e3745 --- /dev/null +++ b/linux-0.11-lab/1/linux/kernel/chr_drv/tty_ioctl.c @@ -0,0 +1,204 @@ +/* + * linux/kernel/chr_drv/tty_ioctl.c + * + * (C) 1991 Linus Torvalds + */ + +#include +#include + +#include +#include +#include + +#include +#include +#include + +static unsigned short quotient[] = { + 0, 2304, 1536, 1047, 857, + 768, 576, 384, 192, 96, + 64, 48, 24, 12, 6, 3 +}; + +static void change_speed(struct tty_struct * tty) +{ + unsigned short port,quot; + + if (!(port = tty->read_q.data)) + return; + quot = quotient[tty->termios.c_cflag & CBAUD]; + cli(); + outb_p(0x80,port+3); /* set DLAB */ + outb_p(quot & 0xff,port); /* LS of divisor */ + outb_p(quot >> 8,port+1); /* MS of divisor */ + outb(0x03,port+3); /* reset DLAB */ + sti(); +} + +static void flush(struct tty_queue * queue) +{ + cli(); + queue->head = queue->tail; + sti(); +} + +static void wait_until_sent(struct tty_struct * tty) +{ + /* do nothing - not implemented */ +} + +static void send_break(struct tty_struct * tty) +{ + /* do nothing - not implemented */ +} + +static int get_termios(struct tty_struct * tty, struct termios * termios) +{ + int i; + + verify_area(termios, sizeof (*termios)); + for (i=0 ; i< (sizeof (*termios)) ; i++) + put_fs_byte( ((char *)&tty->termios)[i] , i+(char *)termios ); + return 0; +} + +static int set_termios(struct tty_struct * tty, struct termios * termios) +{ + int i; + + for (i=0 ; i< (sizeof (*termios)) ; i++) + ((char *)&tty->termios)[i]=get_fs_byte(i+(char *)termios); + change_speed(tty); + return 0; +} + +static int get_termio(struct tty_struct * tty, struct termio * termio) +{ + int i; + struct termio tmp_termio; + + verify_area(termio, sizeof (*termio)); + tmp_termio.c_iflag = tty->termios.c_iflag; + tmp_termio.c_oflag = tty->termios.c_oflag; + tmp_termio.c_cflag = tty->termios.c_cflag; + tmp_termio.c_lflag = tty->termios.c_lflag; + tmp_termio.c_line = tty->termios.c_line; + for(i=0 ; i < NCC ; i++) + tmp_termio.c_cc[i] = tty->termios.c_cc[i]; + for (i=0 ; i< (sizeof (*termio)) ; i++) + put_fs_byte( ((char *)&tmp_termio)[i] , i+(char *)termio ); + return 0; +} + +/* + * This only works as the 386 is low-byt-first + */ +static int set_termio(struct tty_struct * tty, struct termio * termio) +{ + int i; + struct termio tmp_termio; + + for (i=0 ; i< (sizeof (*termio)) ; i++) + ((char *)&tmp_termio)[i]=get_fs_byte(i+(char *)termio); + *(unsigned short *)&tty->termios.c_iflag = tmp_termio.c_iflag; + *(unsigned short *)&tty->termios.c_oflag = tmp_termio.c_oflag; + *(unsigned short *)&tty->termios.c_cflag = tmp_termio.c_cflag; + *(unsigned short *)&tty->termios.c_lflag = tmp_termio.c_lflag; + tty->termios.c_line = tmp_termio.c_line; + for(i=0 ; i < NCC ; i++) + tty->termios.c_cc[i] = tmp_termio.c_cc[i]; + change_speed(tty); + return 0; +} + +int tty_ioctl(int dev, int cmd, int arg) +{ + struct tty_struct * tty; + if (MAJOR(dev) == 5) { + dev=current->tty; + if (dev<0) + panic("tty_ioctl: dev<0"); + } else + dev=MINOR(dev); + tty = dev + tty_table; + switch (cmd) { + case TCGETS: + return get_termios(tty,(struct termios *) arg); + case TCSETSF: + flush(&tty->read_q); /* fallthrough */ + case TCSETSW: + wait_until_sent(tty); /* fallthrough */ + case TCSETS: + return set_termios(tty,(struct termios *) arg); + case TCGETA: + return get_termio(tty,(struct termio *) arg); + case TCSETAF: + flush(&tty->read_q); /* fallthrough */ + case TCSETAW: + wait_until_sent(tty); /* fallthrough */ + case TCSETA: + return set_termio(tty,(struct termio *) arg); + case TCSBRK: + if (!arg) { + wait_until_sent(tty); + send_break(tty); + } + return 0; + case TCXONC: + return -EINVAL; /* not implemented */ + case TCFLSH: + if (arg==0) + flush(&tty->read_q); + else if (arg==1) + flush(&tty->write_q); + else if (arg==2) { + flush(&tty->read_q); + flush(&tty->write_q); + } else + return -EINVAL; + return 0; + case TIOCEXCL: + return -EINVAL; /* not implemented */ + case TIOCNXCL: + return -EINVAL; /* not implemented */ + case TIOCSCTTY: + return -EINVAL; /* set controlling term NI */ + case TIOCGPGRP: + verify_area((void *) arg,4); + put_fs_long(tty->pgrp,(unsigned long *) arg); + return 0; + case TIOCSPGRP: + tty->pgrp=get_fs_long((unsigned long *) arg); + return 0; + case TIOCOUTQ: + verify_area((void *) arg,4); + put_fs_long(CHARS(tty->write_q),(unsigned long *) arg); + return 0; + case TIOCINQ: + verify_area((void *) arg,4); + put_fs_long(CHARS(tty->secondary), + (unsigned long *) arg); + return 0; + case TIOCSTI: + return -EINVAL; /* not implemented */ + case TIOCGWINSZ: + return -EINVAL; /* not implemented */ + case TIOCSWINSZ: + return -EINVAL; /* not implemented */ + case TIOCMGET: + return -EINVAL; /* not implemented */ + case TIOCMBIS: + return -EINVAL; /* not implemented */ + case TIOCMBIC: + return -EINVAL; /* not implemented */ + case TIOCMSET: + return -EINVAL; /* not implemented */ + case TIOCGSOFTCAR: + return -EINVAL; /* not implemented */ + case TIOCSSOFTCAR: + return -EINVAL; /* not implemented */ + default: + return -EINVAL; + } +} diff --git a/linux-0.11-lab/1/linux/kernel/chr_drv/tty_ioctl.o b/linux-0.11-lab/1/linux/kernel/chr_drv/tty_ioctl.o new file mode 100644 index 0000000000000000000000000000000000000000..6fcf766d95e129c53038533553e2124de8516b4b GIT binary patch literal 10648 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 literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/kernel/exit.c b/linux-0.11-lab/1/linux/kernel/exit.c new file mode 100644 index 0000000..2406ebe --- /dev/null +++ b/linux-0.11-lab/1/linux/kernel/exit.c @@ -0,0 +1,197 @@ +/* + * linux/kernel/exit.c + * + * (C) 1991 Linus Torvalds + */ + +#include +#include +#include + +#include +#include +#include +#include + +int sys_pause(void); +int sys_close(int fd); + +void release(struct task_struct * p) +{ + int i; + + if (!p) + return; + for (i=1 ; i32) + return -EINVAL; + if (priv || (current->euid==p->euid) || suser()) + p->signal |= (1<<(sig-1)); + else + return -EPERM; + return 0; +} + +static void kill_session(void) +{ + struct task_struct **p = NR_TASKS + task; + + while (--p > &FIRST_TASK) { + if (*p && (*p)->session == current->session) + (*p)->signal |= 1<<(SIGHUP-1); + } +} + +/* + * XXX need to check permissions needed to send signals to process + * groups, etc. etc. kill() permissions semantics are tricky! + */ +int sys_kill(int pid,int sig) +{ + struct task_struct **p = NR_TASKS + task; + int err, retval = 0; + + if (!pid) while (--p > &FIRST_TASK) { + if (*p && (*p)->pgrp == current->pid) + if (err=send_sig(sig,*p,1)) + retval = err; + } else if (pid>0) while (--p > &FIRST_TASK) { + if (*p && (*p)->pid == pid) + if (err=send_sig(sig,*p,0)) + retval = err; + } else if (pid == -1) while (--p > &FIRST_TASK) + if (err = send_sig(sig,*p,0)) + retval = err; + else while (--p > &FIRST_TASK) + if (*p && (*p)->pgrp == -pid) + if (err = send_sig(sig,*p,0)) + retval = err; + return retval; +} + +static void tell_father(int pid) +{ + int i; + + if (pid) + for (i=0;ipid != pid) + continue; + task[i]->signal |= (1<<(SIGCHLD-1)); + return; + } +/* if we don't find any fathers, we just release ourselves */ +/* This is not really OK. Must change it to make father 1 */ + printk("BAD BAD - no father found\n\r"); + release(current); +} + +int do_exit(long code) +{ + int i; + + free_page_tables(get_base(current->ldt[1]),get_limit(0x0f)); + free_page_tables(get_base(current->ldt[2]),get_limit(0x17)); + for (i=0 ; ifather == current->pid) { + task[i]->father = 1; + if (task[i]->state == TASK_ZOMBIE) + /* assumption task[1] is always init */ + (void) send_sig(SIGCHLD, task[1], 1); + } + for (i=0 ; ifilp[i]) + sys_close(i); + iput(current->pwd); + current->pwd=NULL; + iput(current->root); + current->root=NULL; + iput(current->executable); + current->executable=NULL; + if (current->leader && current->tty >= 0) + tty_table[current->tty].pgrp = 0; + if (last_task_used_math == current) + last_task_used_math = NULL; + if (current->leader) + kill_session(); + current->state = TASK_ZOMBIE; + current->exit_code = code; + tell_father(current->father); + schedule(); + return (-1); /* just to suppress warnings */ +} + +int sys_exit(int error_code) +{ + return do_exit((error_code&0xff)<<8); +} + +int sys_waitpid(pid_t pid,unsigned long * stat_addr, int options) +{ + int flag, code; + struct task_struct ** p; + + verify_area(stat_addr,4); +repeat: + flag=0; + for(p = &LAST_TASK ; p > &FIRST_TASK ; --p) { + if (!*p || *p == current) + continue; + if ((*p)->father != current->pid) + continue; + if (pid>0) { + if ((*p)->pid != pid) + continue; + } else if (!pid) { + if ((*p)->pgrp != current->pgrp) + continue; + } else if (pid != -1) { + if ((*p)->pgrp != -pid) + continue; + } + switch ((*p)->state) { + case TASK_STOPPED: + if (!(options & WUNTRACED)) + continue; + put_fs_long(0x7f,stat_addr); + return (*p)->pid; + case TASK_ZOMBIE: + current->cutime += (*p)->utime; + current->cstime += (*p)->stime; + flag = (*p)->pid; + code = (*p)->exit_code; + release(*p); + put_fs_long(code,stat_addr); + return flag; + default: + flag=1; + continue; + } + } + if (flag) { + if (options & WNOHANG) + return 0; + current->state=TASK_INTERRUPTIBLE; + schedule(); + if (!(current->signal &= ~(1<<(SIGCHLD-1)))) + goto repeat; + else + return -EINTR; + } + return -ECHILD; +} + + diff --git a/linux-0.11-lab/1/linux/kernel/exit.o b/linux-0.11-lab/1/linux/kernel/exit.o new file mode 100644 index 0000000000000000000000000000000000000000..97c5057fd4da000378b2c23ca0dba2b274e9b855 GIT binary patch literal 11164 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 + +#include +#include +#include +#include + +extern void write_verify(unsigned long address); + +long last_pid=0; + +void verify_area(void * addr,int size) +{ + unsigned long start; + + start = (unsigned long) addr; + size += start & 0xfff; + start &= 0xfffff000; + start += get_base(current->ldt[2]); + while (size>0) { + size -= 4096; + write_verify(start); + start += 4096; + } +} + +int copy_mem(int nr,struct task_struct * p) +{ + unsigned long old_data_base,new_data_base,data_limit; + unsigned long old_code_base,new_code_base,code_limit; + + code_limit=get_limit(0x0f); + data_limit=get_limit(0x17); + old_code_base = get_base(current->ldt[1]); + old_data_base = get_base(current->ldt[2]); + if (old_data_base != old_code_base) + panic("We don't support separate I&D"); + if (data_limit < code_limit) + panic("Bad data_limit"); + new_data_base = new_code_base = nr * 0x4000000; + p->start_code = new_code_base; + set_base(p->ldt[1],new_code_base); + set_base(p->ldt[2],new_data_base); + if (copy_page_tables(old_data_base,new_data_base,data_limit)) { + free_page_tables(new_data_base,data_limit); + return -ENOMEM; + } + return 0; +} + +/* + * Ok, this is the main fork-routine. It copies the system process + * information (task[nr]) and sets up the necessary registers. It + * also copies the data segment in it's entirety. + */ +int copy_process(int nr,long ebp,long edi,long esi,long gs,long none, + long ebx,long ecx,long edx, + long fs,long es,long ds, + long eip,long cs,long eflags,long esp,long ss) +{ + struct task_struct *p; + int i; + struct file *f; + + p = (struct task_struct *) get_free_page(); + if (!p) + return -EAGAIN; + task[nr] = p; + __asm__ volatile ("cld"); /* by wyj */ + *p = *current; /* NOTE! this doesn't copy the supervisor stack */ + p->state = TASK_UNINTERRUPTIBLE; + p->pid = last_pid; + p->father = current->pid; + p->counter = p->priority; + p->signal = 0; + p->alarm = 0; + p->leader = 0; /* process leadership doesn't inherit */ + p->utime = p->stime = 0; + p->cutime = p->cstime = 0; + p->start_time = jiffies; + p->tss.back_link = 0; + p->tss.esp0 = PAGE_SIZE + (long) p; + p->tss.ss0 = 0x10; + p->tss.eip = eip; + p->tss.eflags = eflags; + p->tss.eax = 0; + p->tss.ecx = ecx; + p->tss.edx = edx; + p->tss.ebx = ebx; + p->tss.esp = esp; + p->tss.ebp = ebp; + p->tss.esi = esi; + p->tss.edi = edi; + p->tss.es = es & 0xffff; + p->tss.cs = cs & 0xffff; + p->tss.ss = ss & 0xffff; + p->tss.ds = ds & 0xffff; + p->tss.fs = fs & 0xffff; + p->tss.gs = gs & 0xffff; + p->tss.ldt = _LDT(nr); + p->tss.trace_bitmap = 0x80000000; + if (last_task_used_math == current) + __asm__("clts ; fnsave %0"::"m" (p->tss.i387)); + if (copy_mem(nr,p)) { + task[nr] = NULL; + free_page((long) p); + return -EAGAIN; + } + for (i=0; ifilp[i]) + f->f_count++; + if (current->pwd) + current->pwd->i_count++; + if (current->root) + current->root->i_count++; + if (current->executable) + current->executable->i_count++; + set_tss_desc(gdt+(nr<<1)+FIRST_TSS_ENTRY,&(p->tss)); + set_ldt_desc(gdt+(nr<<1)+FIRST_LDT_ENTRY,&(p->ldt)); + p->state = TASK_RUNNING; /* do this last, just in case */ + return last_pid; +} + +int find_empty_process(void) +{ + int i; + + repeat: + if ((++last_pid)<0) last_pid=1; + for(i=0 ; ipid == last_pid) goto repeat; + for(i=1 ; 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 tmp_make + (for i in *.c;do echo -n `echo $$i | sed 's,\.c,\.s,'`" "; \ + $(CPP) -M $$i;done) >> tmp_make + cp tmp_make Makefile + +### Dependencies: diff --git a/linux-0.11-lab/1/linux/kernel/math/math.a b/linux-0.11-lab/1/linux/kernel/math/math.a new file mode 100644 index 0000000000000000000000000000000000000000..f92fb43a9c019f8e75bf744c65f88b59c8d4ba88 GIT binary patch literal 6628 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 + +#include +#include +#include + +void math_emulate(long edi, long esi, long ebp, long sys_call_ret, + long eax,long ebx,long ecx,long edx, + unsigned short fs,unsigned short es,unsigned short ds, + unsigned long eip,unsigned short cs,unsigned long eflags, + unsigned short ss, unsigned long esp) +{ + unsigned char first, second; + +/* 0x0007 means user code space */ + if (cs != 0x000F) { + printk("math_emulate: %04x:%08x\n\r",cs,eip); + panic("Math emulation needed in kernel"); + } + first = get_fs_byte((char *)((*&eip)++)); + second = get_fs_byte((char *)((*&eip)++)); + printk("%04x:%08x %02x %02x\n\r",cs,eip-2,first,second); + current->signal |= 1<<(SIGFPE-1); +} + +void math_error(void) +{ + __asm__("fnclex"); + if (last_task_used_math) + last_task_used_math->signal |= 1<<(SIGFPE-1); +} diff --git a/linux-0.11-lab/1/linux/kernel/math/math_emulate.o b/linux-0.11-lab/1/linux/kernel/math/math_emulate.o new file mode 100644 index 0000000000000000000000000000000000000000..8a98b22720edd26bc9b196e2d1b86549665ddef0 GIT binary patch literal 6464 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 + +/* + * This isn't the library routine, it is only used in the kernel. + * as such, we don't care about years<1970 etc, but assume everything + * is ok. Similarly, TZ etc is happily ignored. We just do everything + * as easily as possible. Let's find something public for the library + * routines (although I think minix times is public). + */ +/* + * PS. I hate whoever though up the year 1970 - couldn't they have gotten + * a leap-year instead? I also hate Gregorius, pope or no. I'm grumpy. + */ +#define MINUTE 60 +#define HOUR (60*MINUTE) +#define DAY (24*HOUR) +#define YEAR (365*DAY) + +/* interestingly, we assume leap-years */ +static int month[12] = { + 0, + DAY*(31), + DAY*(31+29), + DAY*(31+29+31), + DAY*(31+29+31+30), + DAY*(31+29+31+30+31), + DAY*(31+29+31+30+31+30), + DAY*(31+29+31+30+31+30+31), + DAY*(31+29+31+30+31+30+31+31), + DAY*(31+29+31+30+31+30+31+31+30), + DAY*(31+29+31+30+31+30+31+31+30+31), + DAY*(31+29+31+30+31+30+31+31+30+31+30) +}; + +long kernel_mktime(struct tm * tm) +{ + long res; + int year; + if (tm->tm_year < 70 ) tm->tm_year += 100; /* gohigh */ + year = tm->tm_year - 70; +/* magic offsets (y+1) needed to get leapyears right.*/ + res = YEAR*year + DAY*((year+1)/4); + res += month[tm->tm_mon]; +/* and (y+2) here. If it wasn't a leap-year, we have to adjust */ + if (tm->tm_mon>1 && ((year+2)%4)) + res -= DAY; + res += DAY*(tm->tm_mday-1); + res += HOUR*tm->tm_hour; + res += MINUTE*tm->tm_min; + res += tm->tm_sec; + return res; +} diff --git a/linux-0.11-lab/1/linux/kernel/mktime.o b/linux-0.11-lab/1/linux/kernel/mktime.o new file mode 100644 index 0000000000000000000000000000000000000000..6694bf8258168567f68b2aba8bfc5ed630e30698 GIT binary patch literal 2872 zcma)8U1%It6h3!mHraGH+f8=c=BL9R=z+QC zJLlZh2X+aMEv_t>trhe7 zs=+FMvsh7H_c`1WH#v6H&lF#_7Ezv9*R)o}g{=tMS}|I;&BYZj{7N|;Z9Xl?_laJb zy7!+sbi64(04lkZ^z#JEw@~X^<|*sGoj9@%qYI3-zKwt5w^gpqUj~T!PEd383^f<8 z5*2O|-T9N6-}eamWL(gJl4$n6A(|h2E>b)kOL|%2Nt}5PFW*T8(P1??!wQYF%COpD zFue+;jqZ;aTKk|*0Ft#II4RZEhrnBa!&WCpF}4Cntxo8-0mrQn^gX~ys}K5K;2vui za3An?3&%40fm0N+LM7Luwrebj!QH%qP@{PFZ$|B0mly;xE>pPX)Jg2cF5~jqj<1=E zhY-iO?9nD!cLZXD-J@6{INm?3=}2O4-(6lqCNC^>iQTb8#EkXFxcneQzY^j ztGFErVTL1-{gDF^k>ECTk{N?AnHY_52(>Xx)Mkr=y}s?i-pK?)jrF|qcrU!#Lu7`1 zFQbQ>HnKtNU{S?{b<<`}KFMAYAtn=WkM5+&M3&Rhc76;Lt)>d3#|T{J#~|E3A@0UH zd6kzHO|T+#TCCnYx$DpU%wJs-Bbgsx@RQRvR@s?bKYSJna`l3rj$BF>73&&%scXkDpCbUrK1xQ`%?p_ zW*V;7@Q;*vxFMzC3&SJ!(8!>#<*R`SFo|;~Nt_Rh{-|ZW&eP)8K+YOAIp2v`(i|5t zd6(__LdDC?kX`p`J}+uibIP{oob|{qJbHHN9lg{A-$Y1?s@gL!-S zBN1mE^5T3tFW>nM@!sQj^Q_aP`$J4UrLA^zH?rA;v#(!9l zgBc)OgxP>F5Bw(!k}2Q7b&W~#cYaM_$_cND?5(5uI+LR7MnXh#w zG`P#%nAqCq-~V;k_#GyCi}wmH8{YxJ+xEdL7= CPoF&i literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/kernel/panic.c b/linux-0.11-lab/1/linux/kernel/panic.c new file mode 100644 index 0000000..7d8a06b --- /dev/null +++ b/linux-0.11-lab/1/linux/kernel/panic.c @@ -0,0 +1,24 @@ +/* + * linux/kernel/panic.c + * + * (C) 1991 Linus Torvalds + */ + +/* + * This function is used through-out the kernel (includeinh mm and fs) + * to indicate a major problem. + */ +#include +#include + +void sys_sync(void); /* it's really int */ + +volatile void panic(const char * s) +{ + printk("Kernel panic: %s\n\r",s); + if (current == task[0]) + printk("In swapper task - not syncing\n\r"); + else + sys_sync(); + for(;;); +} diff --git a/linux-0.11-lab/1/linux/kernel/panic.o b/linux-0.11-lab/1/linux/kernel/panic.o new file mode 100644 index 0000000000000000000000000000000000000000..da42b57864ffc04172b2020b3f3f9096af53eb86 GIT binary patch literal 5424 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 D&gTd! literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/kernel/printk.c b/linux-0.11-lab/1/linux/kernel/printk.c new file mode 100644 index 0000000..0daa097 --- /dev/null +++ b/linux-0.11-lab/1/linux/kernel/printk.c @@ -0,0 +1,41 @@ +/* + * linux/kernel/printk.c + * + * (C) 1991 Linus Torvalds + */ + +/* + * When in kernel-mode, we cannot use printf, as fs is liable to + * point to 'interesting' things. Make a printf with fs-saving, and + * all is well. + */ +#include +#include + +#include + +static char buf[1024]; + +extern int vsprintf(char * buf, const char * fmt, va_list args); + +int printk(const char *fmt, ...) +{ + va_list args; + int i; + + va_start(args, fmt); + i=vsprintf(buf,fmt,args); + va_end(args); + __asm__("push %%fs\n\t" + "push %%ds\n\t" + "pop %%fs\n\t" + "pushl %0\n\t" + "pushl $buf\n\t" + "pushl $0\n\t" + "call tty_write\n\t" + "addl $8,%%esp\n\t" + "popl %0\n\t" + "pop %%fs" + ::"r" (i):"ax","cx","dx"); + return i; +} diff --git a/linux-0.11-lab/1/linux/kernel/printk.o b/linux-0.11-lab/1/linux/kernel/printk.o new file mode 100644 index 0000000000000000000000000000000000000000..93ce6e40ca451b8b2b024367e2fd7f575b694368 GIT binary patch literal 2424 zcma)7&2Jk;6o2DgCr+F=bwa44L}e?vC4jtkz$&FcNl74zT1BEwQKbUW+Fsk+*lV-9 zPLry@Ap#ObAoTzO!66j~E?kfhSCAS$gv5Ou_hxtEEfNw>nt8wXJ@aOE z_N^B#y(okrMS?WyOGHgQw3H>Ar3WZWSGNC{eQz;e-d)Vk>@DU?d#m}G-PL>wvi^gf zXV2gNK0G{xoZEXPpBvjhF?RP#ll3=3%l1L)`q*8>=C%)Juisi90ly z>aykdDJiyw91=P9O5ADEu%2|>07X85BF&XXc={4!l&3=tH3#1S8mjc_B(nQ}NevS+ zX2q$@L|V&CXR=~^;Mj4be2}!vx%AWNhz0-DrLfy04cA?ur zdfS82aa)dS7wSE?8aN%-hsx~~{J^TN7rI_2u&Y7GqgKal7(Lf_8m?V4_zbZkpEj(u zmg5KHJGbm$t7}uS*=gHFw^s{_9lzk(H;c&L+bopKxw%5isuWA1qPT8*uH6dra=N4a zR-2X=NkmHv3+Ig4tCgM`^uoOr9`8wM?#;QfSt>sgY6;&}NaEII61P)gdPLWE&{P9z zJ`yH*3>Pw~?ZiT+l(?8lUAUK#--hXLwF9d{rXP4AZz|;3Eiec z$O^M5i?7IF5RtO2K#teF2H_ZVT$lH!>e|3629V~E?;3-Ml+A)1&)0;&c{txNhRXLk zFvsw|nRb!ymk`RCZ9HyAT=~6`G|KE@(H-d7eQUg`kCXV589b>lVJwlj!6Ly5PP@Nmnz+;^@S&-W3E%tEI~ z@kn{1j;@ME+C(083(}ch`{!E#R3zOA&vW cIpTsy{wm_%F-Lt_7ZcwB_FIU!0iJ;T4?BzyrvLx| literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/kernel/sched.c b/linux-0.11-lab/1/linux/kernel/sched.c new file mode 100644 index 0000000..15d839b --- /dev/null +++ b/linux-0.11-lab/1/linux/kernel/sched.c @@ -0,0 +1,412 @@ +/* + * linux/kernel/sched.c + * + * (C) 1991 Linus Torvalds + */ + +/* + * 'sched.c' is the main kernel file. It contains scheduling primitives + * (sleep_on, wakeup, schedule etc) as well as a number of simple system + * call functions (type getpid(), which just extracts a field from + * current-task + */ +#include +#include +#include +#include +#include +#include +#include + +#include + +#define _S(nr) (1<<((nr)-1)) +#define _BLOCKABLE (~(_S(SIGKILL) | _S(SIGSTOP))) + +void show_task(int nr,struct task_struct * p) +{ + int i,j = 4096-sizeof(struct task_struct); + + printk("%d: pid=%d, state=%d, ",nr,p->pid,p->state); + i=0; + while (i>2 ] ; + +struct { + long * a; + short b; + } stack_start = { & user_stack [PAGE_SIZE>>2] , 0x10 }; +/* + * 'math_state_restore()' saves the current math information in the + * old math state array, and gets the new ones from the current task + */ +void math_state_restore() +{ + if (last_task_used_math == current) + return; + __asm__("fwait"); + if (last_task_used_math) { + __asm__("fnsave %0"::"m" (last_task_used_math->tss.i387)); + } + last_task_used_math=current; + if (current->used_math) { + __asm__("frstor %0"::"m" (current->tss.i387)); + } else { + __asm__("fninit"::); + current->used_math=1; + } +} + +/* + * 'schedule()' is the scheduler function. This is GOOD CODE! There + * probably won't be any reason to change this, as it should work well + * in all circumstances (ie gives IO-bound processes good response etc). + * The one thing you might take a look at is the signal-handler code here. + * + * NOTE!! Task 0 is the 'idle' task, which gets called when no other + * tasks can run. It can not be killed, and it cannot sleep. The 'state' + * information in task[0] is never used. + */ +void schedule(void) +{ + int i,next,c; + struct task_struct ** p; + +/* check alarm, wake up any interruptible tasks that have got a signal */ + + for(p = &LAST_TASK ; p > &FIRST_TASK ; --p) + if (*p) { + if ((*p)->alarm && (*p)->alarm < jiffies) { + (*p)->signal |= (1<<(SIGALRM-1)); + (*p)->alarm = 0; + } + if (((*p)->signal & ~(_BLOCKABLE & (*p)->blocked)) && + (*p)->state==TASK_INTERRUPTIBLE) + (*p)->state=TASK_RUNNING; + } + +/* this is the scheduler proper: */ + + while (1) { + c = -1; + next = 0; + i = NR_TASKS; + p = &task[NR_TASKS]; + while (--i) { + if (!*--p) + continue; + if ((*p)->state == TASK_RUNNING && (*p)->counter > c) + c = (*p)->counter, next = i; + } + if (c) break; + for(p = &LAST_TASK ; p > &FIRST_TASK ; --p) + if (*p) + (*p)->counter = ((*p)->counter >> 1) + + (*p)->priority; + } + switch_to(next); +} + +int sys_pause(void) +{ + current->state = TASK_INTERRUPTIBLE; + schedule(); + return 0; +} + +void sleep_on(struct task_struct **p) +{ + struct task_struct *tmp; + + if (!p) + return; + if (current == &(init_task.task)) + panic("task[0] trying to sleep"); + tmp = *p; + *p = current; + current->state = TASK_UNINTERRUPTIBLE; + schedule(); + if (tmp) + tmp->state=0; +} + +void interruptible_sleep_on(struct task_struct **p) +{ + struct task_struct *tmp; + + if (!p) + return; + if (current == &(init_task.task)) + panic("task[0] trying to sleep"); + tmp=*p; + *p=current; +repeat: current->state = TASK_INTERRUPTIBLE; + schedule(); + if (*p && *p != current) { + (**p).state=0; + goto repeat; + } + *p=NULL; + if (tmp) + tmp->state=0; +} + +void wake_up(struct task_struct **p) +{ + if (p && *p) { + (**p).state=0; + *p=NULL; + } +} + +/* + * OK, here are some floppy things that shouldn't be in the kernel + * proper. They are here because the floppy needs a timer, and this + * was the easiest way of doing it. + */ +static struct task_struct * wait_motor[4] = {NULL,NULL,NULL,NULL}; +static int mon_timer[4]={0,0,0,0}; +static int moff_timer[4]={0,0,0,0}; +unsigned char current_DOR = 0x0C; + +int ticks_to_floppy_on(unsigned int nr) +{ + extern unsigned char selected; + unsigned char mask = 0x10 << nr; + + if (nr>3) + panic("floppy_on: nr>3"); + moff_timer[nr]=10000; /* 100 s = very big :-) */ + cli(); /* use floppy_off to turn it off */ + mask |= current_DOR; + if (!selected) { + mask &= 0xFC; + mask |= nr; + } + if (mask != current_DOR) { + outb(mask,FD_DOR); + if ((mask ^ current_DOR) & 0xf0) + mon_timer[nr] = HZ/2; + else if (mon_timer[nr] < 2) + mon_timer[nr] = 2; + current_DOR = mask; + } + sti(); + return mon_timer[nr]; +} + +void floppy_on(unsigned int nr) +{ + cli(); + while (ticks_to_floppy_on(nr)) + sleep_on(nr+wait_motor); + sti(); +} + +void floppy_off(unsigned int nr) +{ + moff_timer[nr]=3*HZ; +} + +void do_floppy_timer(void) +{ + int i; + unsigned char mask = 0x10; + + for (i=0 ; i<4 ; i++,mask <<= 1) { + if (!(mask & current_DOR)) + continue; + if (mon_timer[i]) { + if (!--mon_timer[i]) + wake_up(i+wait_motor); + } else if (!moff_timer[i]) { + current_DOR &= ~mask; + outb(current_DOR,FD_DOR); + } else + moff_timer[i]--; + } +} + +#define TIME_REQUESTS 64 + +static struct timer_list { + long jiffies; + void (*fn)(); + struct timer_list * next; +} timer_list[TIME_REQUESTS], * next_timer = NULL; + +void add_timer(long jiffies, void (*fn)(void)) +{ + struct timer_list * p; + + if (!fn) + return; + cli(); + if (jiffies <= 0) + (fn)(); + else { + for (p = timer_list ; p < timer_list + TIME_REQUESTS ; p++) + if (!p->fn) + break; + if (p >= timer_list + TIME_REQUESTS) + panic("No more time requests free"); + p->fn = fn; + p->jiffies = jiffies; + p->next = next_timer; + next_timer = p; + while (p->next && p->next->jiffies < p->jiffies) { + p->jiffies -= p->next->jiffies; + fn = p->fn; + p->fn = p->next->fn; + p->next->fn = fn; + jiffies = p->jiffies; + p->jiffies = p->next->jiffies; + p->next->jiffies = jiffies; + p = p->next; + } + } + sti(); +} + +void do_timer(long cpl) +{ + extern int beepcount; + extern void sysbeepstop(void); + + if (beepcount) + if (!--beepcount) + sysbeepstop(); + + if (cpl) + current->utime++; + else + current->stime++; + + if (next_timer) { + next_timer->jiffies--; + while (next_timer && next_timer->jiffies <= 0) { + void (*fn)(void); + + fn = next_timer->fn; + next_timer->fn = NULL; + next_timer = next_timer->next; + (fn)(); + } + } + if (current_DOR & 0xf0) + do_floppy_timer(); + if ((--current->counter)>0) return; + current->counter=0; + if (!cpl) return; + schedule(); +} + +int sys_alarm(long seconds) +{ + int old = current->alarm; + + if (old) + old = (old - jiffies) / HZ; + current->alarm = (seconds>0)?(jiffies+HZ*seconds):0; + return (old); +} + +int sys_getpid(void) +{ + return current->pid; +} + +int sys_getppid(void) +{ + return current->father; +} + +int sys_getuid(void) +{ + return current->uid; +} + +int sys_geteuid(void) +{ + return current->euid; +} + +int sys_getgid(void) +{ + return current->gid; +} + +int sys_getegid(void) +{ + return current->egid; +} + +int sys_nice(long increment) +{ + if (current->priority-increment>0) + current->priority -= increment; + return 0; +} + +void sched_init(void) +{ + int i; + struct desc_struct * p; + + if (sizeof(struct sigaction) != 16) + panic("Struct sigaction MUST be 16 bytes"); + set_tss_desc(gdt+FIRST_TSS_ENTRY,&(init_task.task.tss)); + set_ldt_desc(gdt+FIRST_LDT_ENTRY,&(init_task.task.ldt)); + p = gdt+2+FIRST_TSS_ENTRY; + for(i=1;ia=p->b=0; + p++; + p->a=p->b=0; + p++; + } +/* Clear NT, so that we won't have troubles with that later on */ + __asm__("pushfl ; andl $0xffffbfff,(%esp) ; popfl"); + ltr(0); + lldt(0); + outb_p(0x36,0x43); /* binary, mode 3, LSB/MSB, ch 0 */ + outb_p(LATCH & 0xff , 0x40); /* LSB */ + outb(LATCH >> 8 , 0x40); /* MSB */ + set_intr_gate(0x20,&timer_interrupt); + outb(inb_p(0x21)&~0x01,0x21); + set_system_gate(0x80,&system_call); +} diff --git a/linux-0.11-lab/1/linux/kernel/sched.o b/linux-0.11-lab/1/linux/kernel/sched.o new file mode 100644 index 0000000000000000000000000000000000000000..f8659586c4602c8d89fa2d360bb31b1da3110c8d GIT binary patch literal 22944 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 +#include +#include +#include +#include + +volatile void do_exit(int error_code); + +int sys_sgetmask() +{ + return current->blocked; +} + +int sys_ssetmask(int newmask) +{ + int old=current->blocked; + + current->blocked = newmask & ~(1<<(SIGKILL-1)); + return old; +} + +int sys_sigpending() +{ + return -ENOSYS; +} + +int sys_sigsuspend() +{ + return -ENOSYS; +} + +static inline void save_old(char * from,char * to) +{ + int i; + + verify_area(to, sizeof(struct sigaction)); + for (i=0 ; i< sizeof(struct sigaction) ; i++) { + put_fs_byte(*from,to); + from++; + to++; + } +} + +static inline void get_new(char * from,char * to) +{ + int i; + + for (i=0 ; i< sizeof(struct sigaction) ; i++) + *(to++) = get_fs_byte(from++); +} + +int sys_signal(int signum, long handler, long restorer) +{ + struct sigaction tmp; + + if (signum<1 || signum>32 || signum==SIGKILL) + return -1; + tmp.sa_handler = (void (*)(int)) handler; + tmp.sa_mask = 0; + tmp.sa_flags = SA_ONESHOT | SA_NOMASK; + tmp.sa_restorer = (void (*)(void)) restorer; + handler = (long) current->sigaction[signum-1].sa_handler; + current->sigaction[signum-1] = tmp; + return handler; +} + +int sys_sigaction(int signum, const struct sigaction * action, + struct sigaction * oldaction) +{ + struct sigaction tmp; + + if (signum<1 || signum>32 || signum==SIGKILL) + return -1; + tmp = current->sigaction[signum-1]; + get_new((char *) action, + (char *) (signum-1+current->sigaction)); + if (oldaction) + save_old((char *) &tmp,(char *) oldaction); + if (current->sigaction[signum-1].sa_flags & SA_NOMASK) + current->sigaction[signum-1].sa_mask = 0; + else + current->sigaction[signum-1].sa_mask |= (1<<(signum-1)); + return 0; +} + +void do_signal(long signr,long eax, long ebx, long ecx, long edx, + long fs, long es, long ds, + long eip, long cs, long eflags, + unsigned long * esp, long ss) +{ + unsigned long sa_handler; + long old_eip=eip; + struct sigaction * sa = current->sigaction + signr - 1; + int longs; + unsigned long * tmp_esp; + + sa_handler = (unsigned long) sa->sa_handler; + if (sa_handler==1) + return; + if (!sa_handler) { + if (signr==SIGCHLD) + return; + else + do_exit(1<<(signr-1)); + } + if (sa->sa_flags & SA_ONESHOT) + sa->sa_handler = NULL; + *(&eip) = sa_handler; + longs = (sa->sa_flags & SA_NOMASK)?7:8; + *(&esp) -= longs; + verify_area(esp,longs*4); + tmp_esp=esp; + put_fs_long((long) sa->sa_restorer,tmp_esp++); + put_fs_long(signr,tmp_esp++); + if (!(sa->sa_flags & SA_NOMASK)) + put_fs_long(current->blocked,tmp_esp++); + put_fs_long(eax,tmp_esp++); + put_fs_long(ecx,tmp_esp++); + put_fs_long(edx,tmp_esp++); + put_fs_long(eflags,tmp_esp++); + put_fs_long(old_eip,tmp_esp++); + current->blocked |= sa->sa_mask; +} diff --git a/linux-0.11-lab/1/linux/kernel/signal.o b/linux-0.11-lab/1/linux/kernel/signal.o new file mode 100644 index 0000000000000000000000000000000000000000..1970f39f72c6b0c63a277c6955a88089975ca4d3 GIT binary patch literal 8960 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 literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/kernel/sys.c b/linux-0.11-lab/1/linux/kernel/sys.c new file mode 100644 index 0000000..695f287 --- /dev/null +++ b/linux-0.11-lab/1/linux/kernel/sys.c @@ -0,0 +1,292 @@ +/* + * linux/kernel/sys.c + * + * (C) 1991 Linus Torvalds + */ + +#include + +#include +#include +#include +#include +#include +#include + +int sys_ftime() +{ + return -ENOSYS; +} + +int sys_break() +{ + return -ENOSYS; +} + +int sys_ptrace() +{ + return -ENOSYS; +} + +int sys_stty() +{ + return -ENOSYS; +} + +int sys_gtty() +{ + return -ENOSYS; +} + +int sys_rename() +{ + return -ENOSYS; +} + +int sys_prof() +{ + return -ENOSYS; +} + +int sys_setregid(int rgid, int egid) +{ + if (rgid>0) { + if ((current->gid == rgid) || + suser()) + current->gid = rgid; + else + return(-EPERM); + } + if (egid>0) { + if ((current->gid == egid) || + (current->egid == egid) || + suser()) { + current->egid = egid; + current->sgid = egid; + } else + return(-EPERM); + } + return 0; +} + +int sys_setgid(int gid) +{ +/* return(sys_setregid(gid, gid)); */ + if (suser()) + current->gid = current->egid = current->sgid = gid; + else if ((gid == current->gid) || (gid == current->sgid)) + current->egid = gid; + else + return -EPERM; + return 0; +} + +int sys_acct() +{ + return -ENOSYS; +} + +int sys_phys() +{ + return -ENOSYS; +} + +int sys_lock() +{ + return -ENOSYS; +} + +int sys_mpx() +{ + return -ENOSYS; +} + +int sys_ulimit() +{ + return -ENOSYS; +} + +int sys_time(long * tloc) +{ + int i; + + i = CURRENT_TIME; + if (tloc) { + verify_area(tloc,4); + put_fs_long(i,(unsigned long *)tloc); + } + return i; +} + +/* + * Unprivileged users may change the real user id to the effective uid + * or vice versa. + */ +int sys_setreuid(int ruid, int euid) +{ + int old_ruid = current->uid; + + if (ruid>0) { + if ((current->euid==ruid) || + (old_ruid == ruid) || + suser()) + current->uid = ruid; + else + return(-EPERM); + } + if (euid>0) { + if ((old_ruid == euid) || + (current->euid == euid) || + suser()) { + current->euid = euid; + current->suid = euid; + } else { + current->uid = old_ruid; + return(-EPERM); + } + } + return 0; +} + +int sys_setuid(int uid) +{ +/* return(sys_setreuid(uid, uid)); */ + if (suser()) + current->uid = current->euid = current->suid = uid; + else if ((uid == current->uid) || (uid == current->suid)) + current->euid = uid; + else + return -EPERM; + return(0); +} + +int sys_stime(long * tptr) +{ + if (!suser()) + return -EPERM; + startup_time = get_fs_long((unsigned long *)tptr) - jiffies/HZ; + return 0; +} + +int sys_times(struct tms * tbuf) +{ + if (tbuf) { + verify_area(tbuf,sizeof *tbuf); + put_fs_long(current->utime,(unsigned long *)&tbuf->tms_utime); + put_fs_long(current->stime,(unsigned long *)&tbuf->tms_stime); + put_fs_long(current->cutime,(unsigned long *)&tbuf->tms_cutime); + put_fs_long(current->cstime,(unsigned long *)&tbuf->tms_cstime); + } + return jiffies; +} + +int sys_brk(unsigned long end_data_seg) +{ + if (end_data_seg >= current->end_code && + end_data_seg < current->start_stack - 16384) + current->brk = end_data_seg; + return current->brk; +} + +/* + * This needs some heave checking ... + * I just haven't get the stomach for it. I also don't fully + * understand sessions/pgrp etc. Let somebody who does explain it. + */ +int sys_setpgid(int pid, int pgid) +{ + int i; + + if (!pid) + pid = current->pid; + if (!pgid) + pgid = current->pid; + for (i=0 ; ipid==pid) { + if (task[i]->leader) + return -EPERM; + if (task[i]->session != current->session) + return -EPERM; + task[i]->pgrp = pgid; + return 0; + } + return -ESRCH; +} + +int sys_getpgrp(void) +{ + return current->pgrp; +} + +int sys_setsid(void) +{ + if (current->leader && !suser()) + return -EPERM; + current->leader = 1; + current->session = current->pgrp = current->pid; + current->tty = -1; + return current->pgrp; +} + +int sys_getgroups() +{ + return -ENOSYS; +} + +int sys_setgroups() +{ + return -ENOSYS; +} + +int sys_uname(struct utsname * name) +{ + static struct utsname thisname = { + "linux .0","nodename","release ","version ","machine " + }; + int i; + + if (!name) return -ERROR; + verify_area(name,sizeof *name); + for(i=0;iumask; + + current->umask = mask & 0777; + return (old); +} diff --git a/linux-0.11-lab/1/linux/kernel/sys.o b/linux-0.11-lab/1/linux/kernel/sys.o new file mode 100644 index 0000000000000000000000000000000000000000..a691166c6ad2230733c9baaa0609d3b8fe779594 GIT binary patch literal 13088 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 M35GC+)VB!!4-!@J2mk;8 literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/kernel/system_call.o b/linux-0.11-lab/1/linux/kernel/system_call.o new file mode 100644 index 0000000000000000000000000000000000000000..919bcc3518c8bd4e0b1b42591e855666ec42ac38 GIT binary patch literal 2640 zcma)8U1%It6h523R*BhEqxGkn6(hzr#w1#;R>d@%)WS+PS(M+@z?XKC~S!V9W zEC?do5H%zOA4(s5NMHPUQwkD;*u@AcKBPvFDhj1ywFDm)6nzlJ@66BcbxPC&cfRkt z_ndRjJ$o~gmxm)Gfk1#f3s57~6;ZgsS$WuoZrV=Gv|_>5Q%mW?n7sNIL~5!0=fsOY z-_;Ua9vh9Vwqt(ryTwmdcQUyg{e^wvR>v$SiJs+Wc^?(emuH$td}!)@!9H2&PN zV())(v9ewBzP@#AsJ}927d%@jHm`7;b)go;hlsCJuUX0obrL8H2h$!i zv}~`?W(4&nRiRSvq-k=F|7)Fa)RC_h7L9fBEf@d_e7deN0^QN@bL{I)%g)jBS|bGje@=1^Eo#o}d(l z!>APK<>R%j?4N&)oKMcky2x)Y?slUNUd-zw>Qz;{XdKJbvFcY}9Hx*xn-()+-BB>hy4GpSl(JmvZ$&~p7p zpym1}pym2gtZRL*T6yTYRjm?)oc|SQIsfa>a{klMComkVT5oyO#sHlI*5d>8F*Ls_ z9ShI}5U-!@`1QVrj<}bB^-s{hInFpofPM$>k=8LqPe{5IJSpkhz?UVx8~htdKM8KX zG?16`k3pZ2_VaS_6!$Ub#(H|%r)Pb7!KdHw={J4)ZJ%EC>Cb$6-KQ`5^ktv^)u-h@ zUOwLqwY%Y*_a>j-r{Mz_Lm1&Wjl^g;MqxY;MQI2y5*a)g zqr;K#a4gCYi;*c*p;1CF=7nZZ!N}-FMwH0RoXo3P1~nlvdY&e;dSXgTlBp_bHJ{AF z88oMwQ;eysdeUTKXr|B&EanZxESW;fDG4>3HEB{!@`SAjUWv4pEM_%Op`;8wS6`IE zh$B+EF-0Pi(+nlUMH)-S(P9&T6ih<)7e%Oe&SpOb)gW%fvlljSWyLlTRvIt{_T^TO(In7jR7{shHPh z3R*&FNhtZWI({i`itKSsn{X%j+rj^q4FDVP0)3n{K4ecb;$<0iah&l1qB&qgFVXv~ z5%;x=n>>#fZX4zTNY)8#cnEnJ@c}--xR>Zz#z%-I7#~GGU;r=XCC0~y&NHHj&l&e4 SALqTF=mW+FiGF14Bl;Vw9TZFe literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/kernel/system_call.s b/linux-0.11-lab/1/linux/kernel/system_call.s new file mode 100755 index 0000000..18e762b --- /dev/null +++ b/linux-0.11-lab/1/linux/kernel/system_call.s @@ -0,0 +1,298 @@ +/* + * linux/kernel/system_call.s + * + * (C) 1991 Linus Torvalds + */ + +/* + * system_call.s contains the system-call low-level handling routines. + * This also contains the timer-interrupt handler, as some of the code is + * the same. The hd- and flopppy-interrupts are also here. + * + * NOTE: This code handles signal-recognition, which happens every time + * after a timer-interrupt and after each system call. Ordinary interrupts + * don't handle signal-recognition, as that would clutter them up totally + * unnecessarily. + * + * Stack layout in 'ret_from_system_call': + * + * 0(%esp) - %eax + * 4(%esp) - %ebx + * 8(%esp) - %ecx + * C(%esp) - %edx + * 10(%esp) - %fs + * 14(%esp) - %es + * 18(%esp) - %ds + * 1C(%esp) - %eip + * 20(%esp) - %cs + * 24(%esp) - %eflags + * 28(%esp) - %oldesp + * 2C(%esp) - %oldss + */ + +SIG_CHLD = 17 + +EAX = 0x00 +EBX = 0x04 +ECX = 0x08 +EDX = 0x0C +FS = 0x10 +ES = 0x14 +DS = 0x18 +EIP = 0x1C +CS = 0x20 +EFLAGS = 0x24 +OLDESP = 0x28 +OLDSS = 0x2C + +state = 0 # these are offsets into the task-struct. +counter = 4 +priority = 8 +signal = 12 +sigaction = 16 # MUST be 16 (=len of sigaction) +blocked = (33*16) + +# offsets within sigaction +sa_handler = 0 +sa_mask = 4 +sa_flags = 8 +sa_restorer = 12 + +nr_system_calls = 93 /* 72 */ + +/* + * Ok, I get parallel printer interrupts while using the floppy for some + * strange reason. Urgel. Now I just ignore them. + */ +.globl system_call,sys_fork,timer_interrupt,sys_execve,sys_execve2 +.globl hd_interrupt,floppy_interrupt,parallel_interrupt +.globl device_not_available, coprocessor_error + +.align 4 +bad_sys_call: + movl $-1,%eax + iret +.align 4 +reschedule: + pushl $ret_from_sys_call + jmp schedule +.align 4 +system_call: + cmpl $nr_system_calls-1,%eax + ja bad_sys_call + push %ds + push %es + push %fs + pushl %edx + pushl %ecx # push %ebx,%ecx,%edx as parameters + pushl %ebx # to the system call + movl $0x10,%edx # set up ds,es to kernel space + mov %dx,%ds + mov %dx,%es + movl $0x17,%edx # fs points to local data space + mov %dx,%fs + + pushl %eax #by wyj + call print_nr + popl %eax + + call sys_call_table(,%eax,4) + pushl %eax + movl current,%eax + cmpl $0,state(%eax) # state + jne reschedule + cmpl $0,counter(%eax) # counter + je reschedule +ret_from_sys_call: + movl current,%eax # task[0] cannot have signals + cmpl task,%eax + je 3f + cmpw $0x0f,CS(%esp) # was old code segment supervisor ? + jne 3f + cmpw $0x17,OLDSS(%esp) # was stack segment = 0x17 ? + jne 3f + movl signal(%eax),%ebx + movl blocked(%eax),%ecx + notl %ecx + andl %ebx,%ecx + bsfl %ecx,%ecx + je 3f + btrl %ecx,%ebx + movl %ebx,signal(%eax) + incl %ecx + pushl %ecx + call do_signal + popl %eax +3: popl %eax + popl %ebx + popl %ecx + popl %edx + pop %fs + pop %es + pop %ds + iret + +.align 4 +coprocessor_error: + push %ds + push %es + push %fs + pushl %edx + pushl %ecx + pushl %ebx + pushl %eax + movl $0x10,%eax + mov %ax,%ds + mov %ax,%es + movl $0x17,%eax + mov %ax,%fs + pushl $ret_from_sys_call + jmp math_error + +.align 2 +device_not_available: + push %ds + push %es + push %fs + pushl %edx + pushl %ecx + pushl %ebx + pushl %eax + movl $0x10,%eax + mov %ax,%ds + mov %ax,%es + movl $0x17,%eax + mov %ax,%fs + pushl $ret_from_sys_call + clts # clear TS so that we can use math + movl %cr0,%eax + testl $0x4,%eax # EM (math emulation bit) + je math_state_restore + pushl %ebp + pushl %esi + pushl %edi + call math_emulate + popl %edi + popl %esi + popl %ebp + ret + +.align 4 +timer_interrupt: + push %ds # save ds,es and put kernel data space + push %es # into them. %fs is used by _system_call + push %fs + pushl %edx # we save %eax,%ecx,%edx as gcc doesn't + pushl %ecx # save those across function calls. %ebx + pushl %ebx # is saved as we use that in ret_sys_call + pushl %eax + movl $0x10,%eax + mov %ax,%ds + mov %ax,%es + movl $0x17,%eax + mov %ax,%fs + incl jiffies + movb $0x20,%al # EOI to interrupt controller #1 + outb %al,$0x20 + movl CS(%esp),%eax + andl $3,%eax # %eax is CPL (0 or 3, 0=supervisor) + pushl %eax + call do_timer # 'do_timer(long CPL)' does everything from + addl $4,%esp # task switching to accounting ... + jmp ret_from_sys_call + +.align 4 +sys_execve: + lea EIP(%esp),%eax + pushl %eax + call do_execve + addl $4,%esp + ret + +.align 4 +sys_execve2: + lea EIP(%esp),%eax + pushl %eax + call do_execve2 + addl $4,%esp + ret + +.align 4 +sys_fork: + call find_empty_process + testl %eax,%eax + js 1f + push %gs + pushl %esi + pushl %edi + pushl %ebp + pushl %eax + call copy_process + addl $20,%esp +1: ret + +hd_interrupt: + pushl %eax + pushl %ecx + pushl %edx + push %ds + push %es + push %fs + movl $0x10,%eax + mov %ax,%ds + mov %ax,%es + movl $0x17,%eax + mov %ax,%fs + movb $0x20,%al + outb %al,$0xA0 # EOI to interrupt controller #1 + jmp 1f # give port chance to breathe +1: jmp 1f +1: xorl %edx,%edx + xchgl do_hd,%edx + testl %edx,%edx + jne 1f + movl $unexpected_hd_interrupt,%edx +1: outb %al,$0x20 + call *%edx # "interesting" way of handling intr. + pop %fs + pop %es + pop %ds + popl %edx + popl %ecx + popl %eax + iret + +floppy_interrupt: + pushl %eax + pushl %ecx + pushl %edx + push %ds + push %es + push %fs + movl $0x10,%eax + mov %ax,%ds + mov %ax,%es + movl $0x17,%eax + mov %ax,%fs + movb $0x20,%al + outb %al,$0x20 # EOI to interrupt controller #1 + xorl %eax,%eax + xchgl do_floppy,%eax + testl %eax,%eax + jne 1f + movl $unexpected_floppy_interrupt,%eax +1: call *%eax # "interesting" way of handling intr. + pop %fs + pop %es + pop %ds + popl %edx + popl %ecx + popl %eax + iret + +parallel_interrupt: + pushl %eax + movb $0x20,%al + outb %al,$0x20 + popl %eax + iret diff --git a/linux-0.11-lab/1/linux/kernel/traps.c b/linux-0.11-lab/1/linux/kernel/traps.c new file mode 100644 index 0000000..f9bd8f1 --- /dev/null +++ b/linux-0.11-lab/1/linux/kernel/traps.c @@ -0,0 +1,208 @@ +/* + * linux/kernel/traps.c + * + * (C) 1991 Linus Torvalds + */ + +/* + * 'Traps.c' handles hardware traps and faults after we have saved some + * state in 'asm.s'. Currently mostly a debugging-aid, will be extended + * to mainly kill the offending process (probably by giving it a signal, + * but possibly by killing it outright if necessary). + */ +#include + +#include +#include +#include +#include +#include +#include + +#define get_seg_byte(seg,addr) ({ \ +register char __res; \ +__asm__("push %%fs;mov %%ax,%%fs;movb %%fs:%2,%%al;pop %%fs" \ + :"=a" (__res):"0" (seg),"m" (*(addr))); \ +__res;}) + +#define get_seg_long(seg,addr) ({ \ +register unsigned long __res; \ +__asm__("push %%fs;mov %%ax,%%fs;movl %%fs:%2,%%eax;pop %%fs" \ + :"=a" (__res):"0" (seg),"m" (*(addr))); \ +__res;}) + +#define _fs() ({ \ +register unsigned short __res; \ +__asm__("mov %%fs,%%ax":"=a" (__res):); \ +__res;}) + +int do_exit(long code); + +void page_exception(void); + +void divide_error(void); +void debug(void); +void nmi(void); +void int3(void); +void overflow(void); +void bounds(void); +void invalid_op(void); +void device_not_available(void); +void double_fault(void); +void coprocessor_segment_overrun(void); +void invalid_TSS(void); +void segment_not_present(void); +void stack_segment(void); +void general_protection(void); +void page_fault(void); +void coprocessor_error(void); +void reserved(void); +void parallel_interrupt(void); +void irq13(void); + +static void die(char * str,long esp_ptr,long nr) +{ + long * esp = (long *) esp_ptr; + int i; + + printk("%s: %04x\n\r",str,nr&0xffff); + printk("EIP:\t%04x:%p\nEFLAGS:\t%p\nESP:\t%04x:%p\n", + esp[1],esp[0],esp[2],esp[4],esp[3]); + printk("fs: %04x\n",_fs()); + printk("base: %p, limit: %p\n",get_base(current->ldt[1]),get_limit(0x17)); + if (esp[4] == 0x17) { + printk("Stack: "); + for (i=0;i<4;i++) + printk("%p ",get_seg_long(0x17,i+(long *)esp[3])); + printk("\n"); + } + str(i); + printk("Pid: %d, process nr: %d\n\r",current->pid,0xffff & i); + for(i=0;i<10;i++) + printk("%02x ",0xff & get_seg_byte(esp[1],(i+(char *)esp[0]))); + printk("\n\r"); + do_exit(11); /* play segment exception */ +} + +void do_double_fault(long esp, long error_code) +{ + die("double fault",esp,error_code); +} + +void do_general_protection(long esp, long error_code) +{ + die("general protection",esp,error_code); +} + +void do_divide_error(long esp, long error_code) +{ + die("divide error",esp,error_code); +} + +void do_int3(long * esp, long error_code, + long fs,long es,long ds, + long ebp,long esi,long edi, + long edx,long ecx,long ebx,long eax) +{ + int tr; + + __asm__("str %%ax":"=a" (tr):"0" (0)); + printk("eax\t\tebx\t\tecx\t\tedx\n\r%8x\t%8x\t%8x\t%8x\n\r", + eax,ebx,ecx,edx); + printk("esi\t\tedi\t\tebp\t\tesp\n\r%8x\t%8x\t%8x\t%8x\n\r", + esi,edi,ebp,(long) esp); + printk("\n\rds\tes\tfs\ttr\n\r%4x\t%4x\t%4x\t%4x\n\r", + ds,es,fs,tr); + printk("EIP: %8x CS: %4x EFLAGS: %8x\n\r",esp[0],esp[1],esp[2]); +} + +void do_nmi(long esp, long error_code) +{ + die("nmi",esp,error_code); +} + +void do_debug(long esp, long error_code) +{ + die("debug",esp,error_code); +} + +void do_overflow(long esp, long error_code) +{ + die("overflow",esp,error_code); +} + +void do_bounds(long esp, long error_code) +{ + die("bounds",esp,error_code); +} + +void do_invalid_op(long esp, long error_code) +{ + die("invalid operand",esp,error_code); +} + +void do_device_not_available(long esp, long error_code) +{ + die("device not available",esp,error_code); +} + +void do_coprocessor_segment_overrun(long esp, long error_code) +{ + die("coprocessor segment overrun",esp,error_code); +} + +void do_invalid_TSS(long esp,long error_code) +{ + die("invalid TSS",esp,error_code); +} + +void do_segment_not_present(long esp,long error_code) +{ + die("segment not present",esp,error_code); +} + +void do_stack_segment(long esp,long error_code) +{ + die("stack segment",esp,error_code); +} + +void do_coprocessor_error(long esp, long error_code) +{ + if (last_task_used_math != current) + return; + die("coprocessor error",esp,error_code); +} + +void do_reserved(long esp, long error_code) +{ + die("reserved (15,17-47) error",esp,error_code); +} + +void trap_init(void) +{ + int i; + + set_trap_gate(0,÷_error); + set_trap_gate(1,&debug); + set_trap_gate(2,&nmi); + set_system_gate(3,&int3); /* int3-5 can be called from all */ + set_system_gate(4,&overflow); + set_system_gate(5,&bounds); + set_trap_gate(6,&invalid_op); + set_trap_gate(7,&device_not_available); + set_trap_gate(8,&double_fault); + set_trap_gate(9,&coprocessor_segment_overrun); + set_trap_gate(10,&invalid_TSS); + set_trap_gate(11,&segment_not_present); + set_trap_gate(12,&stack_segment); + set_trap_gate(13,&general_protection); + set_trap_gate(14,&page_fault); + set_trap_gate(15,&reserved); + set_trap_gate(16,&coprocessor_error); + for (i=17;i<48;i++) + set_trap_gate(i,&reserved); + set_trap_gate(45,&irq13); + outb_p(inb_p(0x21)&0xfb,0x21); + outb(inb_p(0xA1)&0xdf,0xA1); + set_trap_gate(39,¶llel_interrupt); +} diff --git a/linux-0.11-lab/1/linux/kernel/traps.o b/linux-0.11-lab/1/linux/kernel/traps.o new file mode 100644 index 0000000000000000000000000000000000000000..51de46fe88ac98ea479385c2c283bf030d1f46cd GIT binary patch literal 12972 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 +#include + +/* we use this so that we can do without the ctype library */ +#define is_digit(c) ((c) >= '0' && (c) <= '9') + +static int skip_atoi(const char **s) +{ + int i=0; + + while (is_digit(**s)) + i = i*10 + *((*s)++) - '0'; + return i; +} + +#define ZEROPAD 1 /* pad with zero */ +#define SIGN 2 /* unsigned/signed long */ +#define PLUS 4 /* show plus */ +#define SPACE 8 /* space if plus */ +#define LEFT 16 /* left justified */ +#define SPECIAL 32 /* 0x */ +#define SMALL 64 /* use 'abcdef' instead of 'ABCDEF' */ + +#define do_div(n,base) ({ \ +int __res; \ +__asm__("divl %4":"=a" (n),"=d" (__res):"0" (n),"1" (0),"r" (base)); \ +__res; }) + +static char * number(char * str, int num, int base, int size, int precision + ,int type) +{ + char c,sign,tmp[36]; + const char *digits="0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ"; + int i; + + if (type&SMALL) digits="0123456789abcdefghijklmnopqrstuvwxyz"; + if (type&LEFT) type &= ~ZEROPAD; + if (base<2 || base>36) + return 0; + c = (type & ZEROPAD) ? '0' : ' ' ; + if (type&SIGN && num<0) { + sign='-'; + num = -num; + } else + sign=(type&PLUS) ? '+' : ((type&SPACE) ? ' ' : 0); + if (sign) size--; + if (type&SPECIAL) + if (base==16) size -= 2; + else if (base==8) size--; + i=0; + if (num==0) + tmp[i++]='0'; + else while (num!=0) + tmp[i++]=digits[do_div(num,base)]; + if (i>precision) precision=i; + size -= precision; + if (!(type&(ZEROPAD+LEFT))) + while(size-->0) + *str++ = ' '; + if (sign) + *str++ = sign; + if (type&SPECIAL) + if (base==8) + *str++ = '0'; + else if (base==16) { + *str++ = '0'; + *str++ = digits[33]; + } + if (!(type&LEFT)) + while(size-->0) + *str++ = c; + while(i0) + *str++ = tmp[i]; + while(size-->0) + *str++ = ' '; + return str; +} + +int vsprintf(char *buf, const char *fmt, va_list args) +{ + int len; + int i; + char * str; + char *s; + int *ip; + + int flags; /* flags to number() */ + + int field_width; /* width of output field */ + int precision; /* min. # of digits for integers; max + number of chars for from string */ + int qualifier; /* 'h', 'l', or 'L' for integer fields */ + + for (str=buf ; *fmt ; ++fmt) { + if (*fmt != '%') { + *str++ = *fmt; + continue; + } + + /* process flags */ + flags = 0; + repeat: + ++fmt; /* this also skips first '%' */ + switch (*fmt) { + case '-': flags |= LEFT; goto repeat; + case '+': flags |= PLUS; goto repeat; + case ' ': flags |= SPACE; goto repeat; + case '#': flags |= SPECIAL; goto repeat; + case '0': flags |= ZEROPAD; goto repeat; + } + + /* get field width */ + field_width = -1; + if (is_digit(*fmt)) + field_width = skip_atoi(&fmt); + else if (*fmt == '*') { + /* it's the next argument */ + field_width = va_arg(args, int); + if (field_width < 0) { + field_width = -field_width; + flags |= LEFT; + } + } + + /* get the precision */ + precision = -1; + if (*fmt == '.') { + ++fmt; + if (is_digit(*fmt)) + precision = skip_atoi(&fmt); + else if (*fmt == '*') { + /* it's the next argument */ + precision = va_arg(args, int); + } + if (precision < 0) + precision = 0; + } + + /* get the conversion qualifier */ + qualifier = -1; + if (*fmt == 'h' || *fmt == 'l' || *fmt == 'L') { + qualifier = *fmt; + ++fmt; + } + + switch (*fmt) { + case 'c': + if (!(flags & LEFT)) + while (--field_width > 0) + *str++ = ' '; + *str++ = (unsigned char) va_arg(args, int); + while (--field_width > 0) + *str++ = ' '; + break; + + case 's': + s = va_arg(args, char *); + len = strlen(s); + if (precision < 0) + precision = len; + else if (len > precision) + len = precision; + + if (!(flags & LEFT)) + while (len < field_width--) + *str++ = ' '; + for (i = 0; i < len; ++i) + *str++ = *s++; + while (len < field_width--) + *str++ = ' '; + break; + + case 'o': + str = number(str, va_arg(args, unsigned long), 8, + field_width, precision, flags); + break; + + case 'p': + if (field_width == -1) { + field_width = 8; + flags |= ZEROPAD; + } + str = number(str, + (unsigned long) va_arg(args, void *), 16, + field_width, precision, flags); + break; + + case 'x': + flags |= SMALL; + case 'X': + str = number(str, va_arg(args, unsigned long), 16, + field_width, precision, flags); + break; + + case 'd': + case 'i': + flags |= SIGN; + case 'u': + str = number(str, va_arg(args, unsigned long), 10, + field_width, precision, flags); + break; + + case 'n': + ip = va_arg(args, int *); + *ip = (str - buf); + break; + + default: + if (*fmt != '%') + *str++ = '%'; + if (*fmt) + *str++ = *fmt; + else + --fmt; + break; + } + } + *str = '\0'; + return str-buf; +} diff --git a/linux-0.11-lab/1/linux/kernel/vsprintf.o b/linux-0.11-lab/1/linux/kernel/vsprintf.o new file mode 100644 index 0000000000000000000000000000000000000000..5acfe6576413e77d5a31e400e048fdd1e4ad4bf8 GIT binary patch literal 6156 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 tmp_make + (for i in *.c;do $(CPP) -M $$i;done) >> tmp_make + cp tmp_make Makefile + +### Dependencies: +memory.o : memory.c ../include/signal.h ../include/sys/types.h \ + ../include/asm/system.h ../include/linux/sched.h ../include/linux/head.h \ + ../include/linux/fs.h ../include/linux/mm.h ../include/linux/kernel.h diff --git a/linux-0.11-lab/1/linux/mm/memory.c b/linux-0.11-lab/1/linux/mm/memory.c new file mode 100755 index 0000000..e4494dd --- /dev/null +++ b/linux-0.11-lab/1/linux/mm/memory.c @@ -0,0 +1,470 @@ +/* + * linux/mm/memory.c + * + * (C) 1991 Linus Torvalds + */ + +/* + * demand-loading started 01.12.91 - seems it is high on the list of + * things wanted, and it should be easy to implement. - Linus + */ + +/* + * Ok, demand-loading was easy, shared pages a little bit tricker. Shared + * pages started 02.12.91, seems to work. - Linus. + * + * Tested sharing by executing about 30 /bin/sh: under the old kernel it + * would have taken more than the 6M I have free, but it worked well as + * far as I could see. + * + * Also corrected some "invalidate()"s - I wasn't doing enough of them. + */ + +#include + +#include + +#include +#include +#include + +volatile void do_exit(long code); + +static inline volatile void oom(void) +{ + printk("out of memory\n\r"); + do_exit(SIGSEGV); +} + +#define invalidate() \ +__asm__("movl %%eax,%%cr3"::"a" (0)) + +/* these are not to be changed without changing head.s etc */ +#define LOW_MEM 0x100000 +#define PAGING_MEMORY (15*1024*1024) +#define PAGING_PAGES (PAGING_MEMORY>>12) +#define MAP_NR(addr) (((addr)-LOW_MEM)>>12) +#define USED 100 + +#define CODE_SPACE(addr) ((((addr)+4095)&~4095) < \ +current->start_code + current->end_code) + +static long HIGH_MEMORY = 0; + +#define copy_page(from,to) \ +__asm__("cld ; rep ; movsl"::"S" (from),"D" (to),"c" (1024)) + +static unsigned char mem_map [ PAGING_PAGES ] = {0,}; + +/* + * Get physical address of first (actually last :-) free page, and mark it + * used. If no free pages left, return 0. + */ +unsigned long get_free_page(void) +{ +register unsigned long __res asm("ax"); + +__asm__("std ; repne ; scasb\n\t" + "jne 1f\n\t" + "movb $1,1(%%edi)\n\t" + "sall $12,%%ecx\n\t" + "addl %2,%%ecx\n\t" + "movl %%ecx,%%edx\n\t" + "movl $1024,%%ecx\n\t" + "leal 4092(%%edx),%%edi\n\t" + "rep ; stosl\n\t" + "movl %%edx,%%eax\n\t" + "1:" + "cld\n\t" /* by wyj */ + :"=a" (__res) + :"0" (0),"i" (LOW_MEM),"c" (PAGING_PAGES), + "D" (mem_map+PAGING_PAGES-1) + ); +return __res; +} + +/* + * Free a page of memory at physical address 'addr'. Used by + * 'free_page_tables()' + */ +void free_page(unsigned long addr) +{ + if (addr < LOW_MEM) return; + if (addr >= HIGH_MEMORY) + panic("trying to free nonexistent page"); + addr -= LOW_MEM; + addr >>= 12; + if (mem_map[addr]--) return; + mem_map[addr]=0; + panic("trying to free free page"); +} + +/* + * This function frees a continuos block of page tables, as needed + * by 'exit()'. As does copy_page_tables(), this handles only 4Mb blocks. + */ +int free_page_tables(unsigned long from,unsigned long size) +{ + unsigned long *pg_table; + unsigned long * dir, nr; + + if (from & 0x3fffff) + panic("free_page_tables called with wrong alignment"); + if (!from) + panic("Trying to free up swapper memory space"); + size = (size + 0x3fffff) >> 22; + dir = (unsigned long *) ((from>>20) & 0xffc); /* _pg_dir = 0 */ + for ( ; size-->0 ; dir++) { + if (!(1 & *dir)) + continue; + pg_table = (unsigned long *) (0xfffff000 & *dir); + for (nr=0 ; nr<1024 ; nr++) { + if (1 & *pg_table) + free_page(0xfffff000 & *pg_table); + *pg_table = 0; + pg_table++; + } + free_page(0xfffff000 & *dir); + *dir = 0; + } + invalidate(); + return 0; +} + +/* + * Well, here is one of the most complicated functions in mm. It + * copies a range of linerar addresses by copying only the pages. + * Let's hope this is bug-free, 'cause this one I don't want to debug :-) + * + * Note! We don't copy just any chunks of memory - addresses have to + * be divisible by 4Mb (one page-directory entry), as this makes the + * function easier. It's used only by fork anyway. + * + * NOTE 2!! When from==0 we are copying kernel space for the first + * fork(). Then we DONT want to copy a full page-directory entry, as + * that would lead to some serious memory waste - we just copy the + * first 160 pages - 640kB. Even that is more than we need, but it + * doesn't take any more memory - we don't copy-on-write in the low + * 1 Mb-range, so the pages can be shared with the kernel. Thus the + * special case for nr=xxxx. + */ +int copy_page_tables(unsigned long from,unsigned long to,long size) +{ + unsigned long * from_page_table; + unsigned long * to_page_table; + unsigned long this_page; + unsigned long * from_dir, * to_dir; + unsigned long nr; + + if ((from&0x3fffff) || (to&0x3fffff)) + panic("copy_page_tables called with wrong alignment"); + from_dir = (unsigned long *) ((from>>20) & 0xffc); /* _pg_dir = 0 */ + to_dir = (unsigned long *) ((to>>20) & 0xffc); + size = ((unsigned) (size+0x3fffff)) >> 22; + for( ; size-->0 ; from_dir++,to_dir++) { + if (1 & *to_dir) + panic("copy_page_tables: already exist"); + if (!(1 & *from_dir)) + continue; + from_page_table = (unsigned long *) (0xfffff000 & *from_dir); + if (!(to_page_table = (unsigned long *) get_free_page())) + return -1; /* Out of memory, see freeing */ + *to_dir = ((unsigned long) to_page_table) | 7; + nr = (from==0)?0xA0:1024; + for ( ; nr-- > 0 ; from_page_table++,to_page_table++) { + this_page = *from_page_table; + if (!(1 & this_page)) + continue; + this_page &= ~2; + *to_page_table = this_page; + if (this_page > LOW_MEM) { + *from_page_table = this_page; + this_page -= LOW_MEM; + this_page >>= 12; + mem_map[this_page]++; + } + } + } + invalidate(); + return 0; +} + +/* + * This function puts a page in memory at the wanted address. + * It returns the physical address of the page gotten, 0 if + * out of memory (either when trying to access page-table or + * page.) + */ +unsigned long put_page(unsigned long page,unsigned long address) +{ + unsigned long tmp, *page_table; + +/* NOTE !!! This uses the fact that _pg_dir=0 */ + + if (page < LOW_MEM || page >= HIGH_MEMORY) + printk("Trying to put page %p at %p\n",page,address); + if (mem_map[(page-LOW_MEM)>>12] != 1) + printk("mem_map disagrees with %p at %p\n",page,address); + page_table = (unsigned long *) ((address>>20) & 0xffc); + if ((*page_table)&1) + page_table = (unsigned long *) (0xfffff000 & *page_table); + else { + if (!(tmp=get_free_page())) + return 0; + *page_table = tmp|7; + page_table = (unsigned long *) tmp; + } + page_table[(address>>12) & 0x3ff] = page | 7; +/* no need for invalidate */ + return page; +} + +void un_wp_page(unsigned long * table_entry) +{ + unsigned long old_page,new_page; + + old_page = 0xfffff000 & *table_entry; + if (old_page >= LOW_MEM && mem_map[MAP_NR(old_page)]==1) { + *table_entry |= 2; + invalidate(); + return; + } + if (!(new_page=get_free_page())) + oom(); + if (old_page >= LOW_MEM) + mem_map[MAP_NR(old_page)]--; + *table_entry = new_page | 7; + invalidate(); + copy_page(old_page,new_page); +} + +/* + * This routine handles present pages, when users try to write + * to a shared page. It is done by copying the page to a new address + * and decrementing the shared-page counter for the old page. + * + * If it's in code space we exit with a segment error. + */ +void do_wp_page(unsigned long error_code,unsigned long address) +{ +#if 0 +/* we cannot do this yet: the estdio library writes to code space */ +/* stupid, stupid. I really want the libc.a from GNU */ + if (CODE_SPACE(address)) + do_exit(SIGSEGV); +#endif + un_wp_page((unsigned long *) + (((address>>10) & 0xffc) + (0xfffff000 & + *((unsigned long *) ((address>>20) &0xffc))))); + +} + +void write_verify(unsigned long address) +{ + unsigned long page; + + if (!( (page = *((unsigned long *) ((address>>20) & 0xffc)) )&1)) + return; + page &= 0xfffff000; + page += ((address>>10) & 0xffc); + if ((3 & *(unsigned long *) page) == 1) /* non-writeable, present */ + un_wp_page((unsigned long *) page); + return; +} + +void get_empty_page(unsigned long address) +{ + unsigned long tmp; + + if (!(tmp=get_free_page()) || !put_page(tmp,address)) { + free_page(tmp); /* 0 is ok - ignored */ + oom(); + } +} + +/* + * try_to_share() checks the page at address "address" in the task "p", + * to see if it exists, and if it is clean. If so, share it with the current + * task. + * + * NOTE! This assumes we have checked that p != current, and that they + * share the same executable. + */ +static int try_to_share(unsigned long address, struct task_struct * p) +{ + unsigned long from; + unsigned long to; + unsigned long from_page; + unsigned long to_page; + unsigned long phys_addr; + + from_page = to_page = ((address>>20) & 0xffc); + from_page += ((p->start_code>>20) & 0xffc); + to_page += ((current->start_code>>20) & 0xffc); +/* is there a page-directory at from? */ + from = *(unsigned long *) from_page; + if (!(from & 1)) + return 0; + from &= 0xfffff000; + from_page = from + ((address>>10) & 0xffc); + phys_addr = *(unsigned long *) from_page; +/* is the page clean and present? */ + if ((phys_addr & 0x41) != 0x01) + return 0; + phys_addr &= 0xfffff000; + if (phys_addr >= HIGH_MEMORY || phys_addr < LOW_MEM) + return 0; + to = *(unsigned long *) to_page; + if (!(to & 1)) + if (to = get_free_page()) + *(unsigned long *) to_page = to | 7; + else + oom(); + to &= 0xfffff000; + to_page = to + ((address>>10) & 0xffc); + if (1 & *(unsigned long *) to_page) + panic("try_to_share: to_page already exists"); +/* share them: write-protect */ + *(unsigned long *) from_page &= ~2; + *(unsigned long *) to_page = *(unsigned long *) from_page; + invalidate(); + phys_addr -= LOW_MEM; + phys_addr >>= 12; + mem_map[phys_addr]++; + return 1; +} + +/* + * share_page() tries to find a process that could share a page with + * the current one. Address is the address of the wanted page relative + * to the current data space. + * + * We first check if it is at all feasible by checking executable->i_count. + * It should be >1 if there are other tasks sharing this inode. + */ +static int share_page(unsigned long address) +{ + struct task_struct ** p; + + if (!current->executable) + return 0; + if (current->executable->i_count < 2) + return 0; + for (p = &LAST_TASK ; p > &FIRST_TASK ; --p) { + if (!*p) + continue; + if (current == *p) + continue; + if ((*p)->executable != current->executable) + continue; + if (try_to_share(address,*p)) + return 1; + } + return 0; +} + +void do_no_page(unsigned long error_code,unsigned long address) +{ + int nr[4]; + unsigned long tmp; + unsigned long page; + int block,i; + + if (current->pid > 5) + printk(" --do_no_page: address=%x, pid=%d\n", address, current->pid); + + address &= 0xfffff000; + tmp = address - current->start_code; + if (!current->executable || tmp >= current->end_data) { + get_empty_page(address); + return; + } + if (share_page(tmp)) + return; + if (!(page = get_free_page())) + oom(); +/* remember that 1 block is used for header */ + block = 1 + tmp/BLOCK_SIZE; + for (i=0 ; i<4 ; block++,i++) + nr[i] = bmap(current->executable,block); + bread_page(page,current->executable->i_dev,nr); + i = tmp + 4096 - current->end_data; + tmp = page + 4096; + while (i-- > 0) { + tmp--; + *(char *)tmp = 0; + } + if (put_page(page,address)) + return; + free_page(page); + oom(); +} + +/* by lzh */ +void do_no_page_my(unsigned long error_code,unsigned long address) +{ + int nr[4]; + unsigned long tmp; + unsigned long page; + int block,i; + + address &= 0xfffff000; + tmp = address - current->start_code; + if (!current->executable || tmp >= current->end_data) { + get_empty_page(address); + return; + } + if (share_page(tmp)) + return; + if (!(page = get_free_page())) + oom(); +/* remember that 1 block is used for header */ + block = 1 + tmp/BLOCK_SIZE; + for (i=0 ; i<4 ; block++,i++) + nr[i] = bmap(current->executable,block); + bread_page(page,current->executable->i_dev,nr); + i = tmp + 4096 - current->end_data; + tmp = page + 4096; + while (i-- > 0) { + tmp--; + *(char *)tmp = 0; + } + if (put_page(page,address)) + return; + free_page(page); + oom(); +} +/* by lzh */ + +void mem_init(long start_mem, long end_mem) +{ + int i; + + HIGH_MEMORY = end_mem; + for (i=0 ; i>= 12; + while (end_mem-->0) + mem_map[i++]=0; +} + +void calc_mem(void) +{ + int i,j,k,free=0; + long * pg_tbl; + + for(i=0 ; iR+&YJN*HS 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 literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/mm/mm.o b/linux-0.11-lab/1/linux/mm/mm.o new file mode 100644 index 0000000000000000000000000000000000000000..1874ff6c28f6bcad4ee0cf8736ef991fedb0c2bd GIT binary patch literal 13954 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 N^|Cbi(V*L${{d;jp)>#h literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/tools/build.c b/linux-0.11-lab/1/linux/tools/build.c new file mode 100644 index 0000000..8b8c7ab --- /dev/null +++ b/linux-0.11-lab/1/linux/tools/build.c @@ -0,0 +1,171 @@ +/* + * linux/tools/build.c + * + * (C) 1991 Linus Torvalds + */ + +/* + * This file builds a disk-image from three different files: + * + * - bootsect: max 510 bytes of 8086 machine code, loads the rest + * - setup: max 4 sectors of 8086 machine code, sets up system parm + * - system: 80386 code for actual system + * + * It does some checking that all files are of the correct type, and + * just writes the result to stdout, removing headers and padding to + * the right amount. It also writes some system data to stderr. + */ + +/* + * Changes by tytso to allow root device specification + */ + +#include /* fprintf */ +#include +#include /* contains exit */ +#include /* unistd.h needs this */ +#include +#include +#include /* contains read/write */ +#include + +#define MAJOR(a) (((unsigned)(a))>>8) +#define MINOR(a) ((a)&0xff) + +#define MINIX_HEADER 32 +#define GCC_HEADER 0x80 /* 0x1000 */ /* by wyj */ + +#define SYS_SIZE 0x3000 + +#define DEFAULT_MAJOR_ROOT 0x03 //0x02 /* by wyj */ +#define DEFAULT_MINOR_ROOT 0x00 //0x1d + +/* max nr of sectors of setup: don't change unless you also change + * bootsect etc */ +#define SETUP_SECTS 4 + +#define STRINGIFY(x) #x + +void die(char * str) +{ + fprintf(stderr,"%s\n",str); + exit(1); +} + +void usage(void) +{ + die("Usage: build bootsect setup system [rootdev] [> image]"); +} + +int main(int argc, char ** argv) +{ + int i,c,id; + char buf[1024*4]; /* by wyj */ + char major_root, minor_root; + struct stat sb; + + if ((argc != 4) && (argc != 5)) + usage(); + if (argc == 5) { + if (strcmp(argv[4], "FLOPPY")) { + if (stat(argv[4], &sb)) { + perror(argv[4]); + die("Couldn't stat root device."); + } + major_root = MAJOR(sb.st_rdev); + minor_root = MINOR(sb.st_rdev); + } else { + major_root = 0; + minor_root = 0; + } + } else { + major_root = DEFAULT_MAJOR_ROOT; + minor_root = DEFAULT_MINOR_ROOT; + } + fprintf(stderr, "Root device is (%d, %d)\n", major_root, minor_root); + if ((major_root != 2) && (major_root != 3) && + (major_root != 0)) { + fprintf(stderr, "Illegal root device (major = %d)\n", + major_root); + die("Bad root device --- major #"); + } + for (i=0;i0 ; i+=c ) + if (write(1,buf,c)!=c) + die("Write call failed"); + close (id); + if (i > SETUP_SECTS*512) + die("Setup exceeds " STRINGIFY(SETUP_SECTS) + " sectors - rewrite build/boot/setup"); + fprintf(stderr,"Setup is %d bytes.\n",i); + for (c=0 ; c sizeof(buf)) + c = sizeof(buf); + if (write(1,buf,c) != c) + die("Write call failed"); + i += c; + } + + if ((id=open(argv[3],O_RDONLY,0))<0) + die("Unable to open 'system'"); + if (read(id,buf,GCC_HEADER) != GCC_HEADER) + die("Unable to read header of 'system'"); +// if (((long *) buf)[5] != 0) +// die("Non-GCC header of 'system'"); + for (i=0 ; (c=read(id,buf,sizeof buf))>0 ; i+=c ) + if (write(1,buf,c)!=c) + die("Write call failed"); + close(id); + fprintf(stderr,"System is %d bytes.\n",i); + if (i > SYS_SIZE*16) + die("System is too big"); + return(0); +} diff --git a/linux-0.11-lab/1/linux/tools/system b/linux-0.11-lab/1/linux/tools/system new file mode 100755 index 0000000000000000000000000000000000000000..cead7ad034e50008add7c748aef397adb4113bac GIT binary patch literal 300866 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�We>m3*yY4la^fSX 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"s":""); diff --git a/linux-0.11-lab/1/Source-Insight/Linux-0.11.WK3 b/linux-0.11-lab/1/Source-Insight/Linux-0.11.WK3 new file mode 100755 index 0000000000000000000000000000000000000000..83b8a91bcf60093c431c8bf17f52b9cdc811bb72 GIT binary patch literal 8851 zcmeHNU1%It6u!xtnA*~$Xr-XiX~mKsXS%y>wTU7LiNV&UjmC=9Tf^+^Bs*kwCd^Nh zNHH%WJ_tr%)Hh!O;vWHv7Hr6aFTp&hPb#}85ivdp6{-&+7{4=fr9)zRgG?RtEm05vc5+GbvNT<&w* z<)&fz<8oTbWMos#@iZT>eMi&fW0q?S7d(FA>iI1m%3F5%YvsY`|HEoNyN$6Q?_z8j zAd%4K;Pc=~;B{aMXuCT&9q`+s8XUhs|4A%n*B-{cM$aO64&&dwkFhJ@jbwRl^3?Km zayiyBIT>pRb>;k8ag5E`*snUC;Tg6id1}to+5Q)J^Yg0wVwZg8tkTL`n$b+l?Pr4n z+AT_J%zQ#ZlkJAniukVJ1g#6y4t$bcjC zR@lD;z7DSPI9l z-cPH|97$!<=~O12KG5C4PrI~*ecZQn-eYTiQMWu->|IM@@469JO4uQ;cxHB*jel7R zGKNXmd_?5F!nrOm=@hwPAP4;ea4$FuyaS!yq{$Cq9_UB^ESTPoX$*}&4Yq)fp*Mk_ z1;~Fl_%(q1Q?y@!PUHUsXkOAg!EXZO^E~(xPy;*;(D=*frym7SgEcjRqc`?f|0pqO z>HFYZ9|p|=^H^)=juQI^CF24x473B^!a)Og8vGD^JPM}Lu>iaU&|AJolR&Z|G5Ji# z^`8k`M+-Z7&bGba;Od&ExQei9scdCfhR4IlrcGEJsBF=vj_5;%si(#8wl#(;S-x^% zu_>yy2^NFLIIp7qmTvOcgRi)Uh4H~EjibfUuQ-zCjqDxRenDuPpV^!!WcB6ZRv#w1$ zi!SR);i-4io;=$&DeQ)sS2W~YkieA0QR2>wm)JZ&`F2F$==&vh@tHE)hc+cS$@Y*~ z{itJD-pEeT+~#=`gJX{2=}n?1UVNj8XtHR+emL)32q%0B{eQ9m=Svid9Z=Bb7QMLj7RH!n^7ZcDFEkY#pO2pW3A8 L(|=0vYl{BA4o;%1 literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/.DS_Store b/linux-0.11-lab/1/linux/.DS_Store new file mode 100755 index 0000000000000000000000000000000000000000..9b68e59c3c90bd843a4c672bc9c58590794488da GIT binary patch literal 14340 zcmeHN4R91^8GfH5z#X^1LMf@|rM)(VkeZex(2!t(BMF3%Ae01>043bz7T9vRi?^4A zkfu!?ZB?jNtA$#%RY$Gj_&0^tpVmrstkO|iu@$t=NINs=okBtZ4$SD_gvoj zTqiOq-PMpv#FL3#Lq-p6@NkoupCfmZ5{~(J9-c`#lc!Ae`g~sBbl*)4yOZ4w=}5ZM zs*DW1oZI3?z>R<#0XG6}1l$OWAp(MXdGq>}b&qZY+z7Z47>Iy)K7@D|Hf-B|W#yxT z52Az@{i1}I8=tcdkZmE`hHcxgtenboaZjkeFtE);m?>U-r{?x!C#5BKudZ1=a?b^EfR$cG3jEzP- zk~X`H>PXtKTJ@P0N20bZnb?pry4dTcwq(4sJ;6P*+9L6`P9AKmjK>?yeQI=DDjAP& zNLpsvOeR{I)5hMk=o1$j)YZJjN~Y3P@?y;y@o}mk0dYV(i7bWK3KwrXTUD@mF0Q2y7KSRVjmy zF?+)Nf`Gr#VxRPgJ@9Qset+X0{@HcQzEyFFKd>nti5hV|=2Q2%zRVwJ>QXN0b#~*@ zIsQO%Te7{KU9s%8}cZ(&$7NZo{2;AKs7s z_y|6MPvQYQgh%iVd=uZo_wZx<1V6fCc1+Vrp(sZx<=r0Hs`ZyPKsNRC$wO+68QGLb1QXj)# zpQQS(_b>4>(Dlixcd7pdAE$zzqk32PS9%%o`V`fh=U?UX=`?oejtbl#(zEm%2JIX4 zPfTXO&StQN7^v5wTmrQcRak|0Fj#NIMl|9kY{w1;tbl7f66in=_Td)vF=*e*pxuuH z_y7*#5I%M7eakCSRS@B&f@FE}N9>rnAwJrsznk&tioOK|;em zD~6$?fhX#4w4`b0k(RVUsXqo<(wwxUX--FG!FO>CB9ouvzhr)alQ@mv z<2AfKCOY~zmPaKbZMq~Pt#I69`9cwr_TLkdHVPqWPD0YM2}xV34JITln~=0TEkj6W z0j(sWks$jFouZfN3_O_1HPdVa7^VvtqGbq6h^|E)*G!ukrY&4EZG(ZG*v(KCKovF9 zUfhm%;oW!-!}V^4>pfgM-OH8JgZMN)!?67_zJjme>v$NC;c*+j$8iEL;Iw)k57bY? z5s?j82L*Yko!YYqXd;Ot>6^n}6)5*O!6Pt@{qr!VSQ8f7>|1teC7sPGtPW=i$!wi3 z3#*#iwOXq_Oj&cmmHv>m1|4oiHHy&B&r|EfmfqqASqSu7Dr`MUN{8HS{#ATQ##eE@4rDh7FmKBo__ZzX5)shhRF;+{K zB&u%ovr-b`{s2BI#r=bH&aX9Jv@Aa zt7}%TsU64g9aKaWUR%24hL!&lRex?plwYWNrOXS0MFW~%TNo_K*7S?DvMf!nRcLR| z*7VD@aF(X$5~^Bh`g205sQOPcLf_HTnFA_Yn{~E;ajD2*-g|2leDg z>fu+DCnD*bmp?~c{h!H*i^@(`-WH4Z|5lCs{{KZ46W3Wc0vB5ZkW<}IUCCZ&{-tyV zz{3q8-godW#yr8h*!Wyd;e!|=KFHVc_=9*IuUxccHtq|HbGH4;@)>Uz{6)abn=fbm YSD*hxarM8e|NoP>%p8U2c-H^_0_^xf2LJ#7 literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/._.DS_Store b/linux-0.11-lab/1/linux/._.DS_Store new file mode 100755 index 0000000..e69de29 diff --git a/linux-0.11-lab/1/linux/._execve2.patch b/linux-0.11-lab/1/linux/._execve2.patch new file mode 100755 index 0000000000000000000000000000000000000000..9c208f113f6370ca29c0d9545924ea666230e20e GIT binary patch literal 4096 zcmZQz6=P>$Vqox1Ojhs@R)|o50+1L3ClDJkFz{^v(m+1nBL)UWIUt(=a103vVi5A! z4bj0c1E^dSO$#HC4;2?p&d=3LEGWoH)hjGbEK1BP$;?Y-Ffgz%vNkhFHBL)3HnI*+ zb% zWMmdA6r~pDmlh?bDx~EXWh-Rnm81f@o%wl*IXRUIIjLzS3Q0MMdD+0eFjUu&rcnJ4 L_lgXI-2eXoaHlI- literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/Image b/linux-0.11-lab/1/linux/Image new file mode 100644 index 0000000000000000000000000000000000000000..6b21367e96426db0453d9d83361acebdc63e903a GIT binary patch literal 138372 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%0DgzU?N|sP{RZIYeg|WV z#C3a@#J2!H3cSLkUm)=g;Dyc6I%6NQA9x$^M@f(JMs$O_LXq2#LKYS#d9`6+njrco zEM*Ej6L=!-pEq2VA@A$WMod{%FC;q*0zaj4tgzMQCRnMP-X878Z>)AC_ z(otbO3tiKY_z8!$Sg)r;ejvHF}2rdFX zaGha1qioeWHcd+DusMEgk7>PfKS3+f1s;g+Q@xD1dk`nau?ceiNEzN#IHveQk2k3L zJObPYdY{C@Ym3ecp*P?K64!l-J`?yc;H3(;-!5$~ANW=4qwR$a( zpc%;iA8~IyY#7z7Lk`Aw%JnLyTaCEv?;FMdyGoZL{REb!6>);NbKD0$SoutnihCcr> zwWbq8Z~r)oT*xsK^q2lnwRxncY>R;15Q8lTRs#&xB7UUX0BkuhF^9u7?Qb)%$ACRV zDl>n!w@iB=w!L+N)&T9VPNsd@N=x0I0PUK`;ro!5whG6DGNfn0hJc$oBW(__i+%*Z zPtv;WxFJj21H1xwnZ(o0^|V>Qp95ZG;vPv~3;bQ+vHjj!;KQDXrl%~ez^4HheGsmR zJr8VI47L~8rWouUV6Vnt$AEnSY#`;rk7aOXV;%|&T_*M5!f-2WHWRo3{J}l~cRSYg z5%#R(vH)>+J*DOqs1uGS7%aoSD*4U@&FY^T#&CqGU)*vO`T2l90z6g+4*>t&v*GpB zbUU0U9Z5F>KW{7MspO;b%Cz4b)u-(R%`(v3KpNKNWI3K61pd?K;`bjX5ceO5J4dBK zS0&_2zX;%9Izdwin!PfuhkIa{HVFI(@Lj}J z+FbkZ!)aMo7aa5ler*^%c3iOk`cn2ojLSh>^$REKk?pexaq|)P4}{4(JjRvS4_L=I z>Yx_1gMO>lJ#kImtAPyz#&{{)jXP;*Ixbrky;#>(a%aHSOuq$gt+op^g-9=aSd&KW zyJP$z#LqzdScJ{8XEaC_jOQR%dy4d|k1WLBkNA;Hk2>Z)GNvm8{=_%%os0OFP7zPO z%MrgH@#u!gH;wzAbObj7{|9j9L3!0!Im;YpNz)FR1E7HkTWLy78boXF;NLr-xip$a z^z&Xzw@unaG*a>tzF#CyL0e;?)j^vN+C!j)TCI7PnR%0D7HIwnn!IS5J53svZ8>N@ z2F(aX!}+CaA?gM5M#evm_#VUyy+bAuUn%2hH!mYTxjj;^_u20e^HRp`M_k@1;yy*( zG{l+qa-ZEV(&|1r6yf^(=ILn?>gwgSUY8bdkLJ81nct9ruFhKzZ3ZP zf!8^30mrhBW3hC!aB2RwJi^SemZHuK|5k-NEEw^4zss((X~Tbnw$*?!U>nNwGW?t0 z(BAMI1@Qhj+j8(G)@+;hGH4e68tau0LpA5wv>DH9+P`o#ZqT&<3Sv(UXjl3$H#>kj z_#5`oeGg*~uHVIZ1!y#cukFGZQLSkoJcqs#*g72Fg@f}J;_492{UiFBN8vjmT%U<| zzT>9WuSeOm`}<-)^+xCe_!~Ii3pUP5bb>Htp+&Y}#mSI+z=$5^yV5 zf1n6Z}c#bWM9TGMM8Htm<=Y}(b8wx)9*wl)3a#gi(l6&udB-pob5Q~wTr z5Q%&IeXKX*IMr{_YMaL6+kSjDx*v#`vzq&Am)QTV%?HS}B;qAF_#3SKU5lk>4y12Q zi10D#iN~WKW{Xcx+|wV=_<(10zOUg44f$*B!Y5e}e^SW+Km_sYpM;YmbLBuM$j&Y-3oBG10>0jBjT8CY0>TBn# z?#*96t<%-dEQ0yD)99uua+mT7u45ldHkZ5`Znz877bhE#Qrz4 z?wW9IKEF#IrmoIHm^PBn&+?hc2Ri3s%g4PFdS#fKsxO#yH<*0YY{KxPgiF?2T%Fj>Y8*+YyKE# S9)g#OSO>Z*O(I3Z%l{2|_`iz) literal 0 HcmV?d00001 diff --git a/linux-0.11-lab/1/linux/Image.bkp b/linux-0.11-lab/1/linux/Image.bkp new file mode 100644 index 0000000000000000000000000000000000000000..9869a43badb77318312737429c1972e920db1e68 GIT binary patch literal 131556 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