Initial Spring 2016 commit.

This commit is contained in:
Geoffrey Challen 2015-12-23 00:50:04 +00:00
commit cafa9f5690
732 changed files with 92195 additions and 0 deletions

11
.gitignore vendored Normal file
View File

@ -0,0 +1,11 @@
/.depend
/.settings
/.project
/.cproject
/kern/compile/
/defs.mk
build
/userland/testbin/randcall/calls.c
/root/
*.swo
*.swp

689
CHANGES Normal file
View File

@ -0,0 +1,689 @@
OS/161 was written by David A. Holland, with contributions from
Amos Blackman
Alexandra Fedorova
Ada T. Lim
Georgi Matev
Jay Moorthi
Geoffrey Werner-Allen
Additional small patches and bug reports have been contributed by
various other people, all of whom are (hopefully) listed below.
------------------------------------------------------------
20150805 dholland OS/161 2.0.1 released.
20150804 dholland Improve multiexec's error reporting.
20150804 dholland Minor fixes to frack check.
20150722 dholland Add assertions to dumbvm to check that sleeping is ok
........ in various contexts real VM systems typically sleep.
20150722 dholland Initialize curcpu/curthread a bit earlier.
20150721 dholland Remove proc->p_threads[] array. Just count the number
........ of threads in each proc. This is enough to get going
........ on, and it's easy for students to add and synchronize
........ an explicit array of threads themselves if they want
........ it. (It needs a sleeplock; but by that point they'll
........ have those. We don't out of the box though.)
20150713 dholland Make all sfs prints/panics include the volume name.
20150713 dholland Have sfsck print invalid inode type values.
20150713 dholland Have forktest print ABCD instead of 1234 for clarity.
20150713 dholland Kill off allwchans[]; in practice it isn't useful.
20150710 dholland Split out the pieces of sys_sync for reusability.
20150706 dholland Add support for new sys161 profiler control registers.
20150625 dholland Fix frack "writetruncseq" workload.
20150605 dholland Have semfs update uio_offset; increases robustness.
20150605 dholland Don't do semfs I/O from NULL. It causes consternation.
20150605 dholland Warn that copying threadlist structures breaks them.
20150605 dholland New test: schedpong, an actual scheduler workload, now
........ possible because we have semfs.
20150603 dholland Add example unit tests for the provided semaphores.
20150603 dholland In panic, drop to the debugger before sync, not after.
........ Otherwise, the sync complicates postmortem analysis.
20150603 dholland Make "dumpsfs -i N -a image" work.
20150603 dholland Improve the printouts of testbin/badcall.
20150603 dholland Make kernel config script reject duplicate .o names.
20150603 dholland Improve printouts of testbin/crash for legibility.
20150528 dholland Comment up testbin/frack/check.c. Badly needed.
20150527 dholland Fix various minor bugs found by clang-static-analyzer.
........ From Keno Fischer.
20150527 dholland Make the skeleton userland stdio less needlessly dumb.
20150527 dholland New kernel menu test: at2; tests arrays > 1 page.
20150519 dholland New test: bigfork, intended mostly for performance
........ testing.
20150513 dholland Fix "unexpected EOF" bug in frack check.
20150513 dholland Fix flagrantly wrong assert in frack check.
20150513 dholland Fix fd leaks in frack check.
20150428 dholland Fix error-path assertions in sfs_domount; from
........ Sam Fishman and Michelle Deng.
20150422 dholland Re-enable ftruncate in frack by default.
20150417 dholland Fix configure test for ntohll. From Nikhil Benesch.
20150417 dholland Use printf instead of echo -n in shell scripts; it
........ seems that even in 2015 Mac OS X comes with a broken
........ echo, and we don't care about OSes too old to have
........ printf in sh. From Nikhil Benesch.
20150322 dholland Fix typos in non-dumbvm addrspace.h; from Anne Madoff.
20150322 dholland Fix some typos in comments.
20150127 dholland Patch more Linux build problems caused by glibc bugs.
20150115 dholland OS/161 2.0 released.
20150113 dholland Drop to the debugger on panic.
20150113 dholland Document parallelvm -w.
20150113 dholland Better man page typesetting. From Katherine Flavel.
20150108 dholland Fix FSOP_GETROOT signature/usage so it can fail.
20150108 dholland Add several missing man pages for testbin programs.
20150108 dholland Fix naming of semaphores in testbin/multiexec.
20150107 dholland Also change malloctest* symbols to kmalloctest*.
20150107 dholland Rename kern/malloctest.c to kmalloctest.c for clarity.
20140924 dholland Print the kernel build number after linking.
20140924 dholland OS/161 1.99.08 released. Consider this 2.0-RC1.
20140924 dholland Make km3 rotate object sizes as originally intended.
20140924 dholland Make frack print a visible divider when it syncs.
20140922 dholland Add /bin/tac, which uses unlinked scratch files.
20140919 dholland Allow giving testbin/bigfile the chunk size to write.
20140919 dholland Add a design doc about the structure of assignments.
20140919 dholland Make certain sfsck checks set the exit status properly.
20140918 dholland Provide general-purpose metadata I/O function in sfs.
20140916 dholland Remove size workaround in bigexec; fixed solution set.
20140904 dholland Fix problem with stray symlinks in $(OSTREE)/include.
20140904 dholland Change sfs_vnode->sv_v to sv_absvn for consistency.
20140904 dholland Add bloat test; it uses all available memory rapidly.
20140904 dholland Fix testbin/crash for gcc 4.8.
20140904 dholland Make testbin/filetest do something useful if no argv.
20140904 dholland Declare userland err* __DEAD.
20140904 dholland Add sys/cdefs.h and move userland __DEAD there.
20140903 dholland Simplify ram.c interface as suggested by my students.
20140829 dholland Add km4: a kmalloc test for multipage allocations.
20140829 dholland Add multiexec test for lots of procs in exec at once.
20140828 dholland Tighten asm constraints for gcc 4.8.
20140828 dholland Fix inlining for gcc 4.8, and a few other build issues.
20140825 dholland Remove vnode open count and VOP_INC/DECOPEN.
20140825 dholland Remove VOP_LASTCLOSE; nothing uses it any more.
20140825 dholland Don't fsync in sfs_lastclose; it's outdated practice.
20140825 dholland Remove DEVOP_LASTCLOSE; nothing uses it and we will
........ never add rewind-on-close tape devices.
20140825 dholland Use a separate spinlock for vnode refcounts. (Using
........ vfs_biglock causes sleeping while holding spinlocks.)
20140825 dholland Don't use sfs_io() for directory entries.
20140821 dholland Replace VOP_TRYSEEK with static VOP_ISSEEKABLE.
20140821 dholland Make devices check seek position validity on the fly.
20140806 dholland Make sfs_link reject directories. From Anne Madoff.
20140730 dholland Make testbin/hog run longer.
20140729 dholland Document psort's sizing knobs.
20140729 dholland Make psort big enough to be useful as a fs test.
20140729 dholland Add ARRAYCOUNT() macro for static array length.
20140729 dholland Add array_preallocate().
20140729 dholland Make npages argument of alloc_kpages() unsigned.
20140729 dholland Tidy up construction/destruction of struct sfs_fs.
20140728 dholland Make sfs_read/writeblock take the buffer length.
........ (Always do that, even if it's the same everywhere.)
20140728 dholland struct sfs_super -> struct sfs_superblock.
20140728 dholland Adjust SFS code to make it more readily extensible.
20140728 dholland Always call SFS's free block bitmap the "freemap".
20140728 dholland Rename a bunch of the SFS constants for clarity.
20140725 dholland Add usemtest for checking the semfs semaphores.
20140724 dholland Make failed SFS writes not increase the file size.
20140724 dholland Distinguish MIPS 512M RAM limit and LAMEbus 508M limit.
20140722 dholland sfs_dir -> sfs_direntry, by popular demand.
20140722 dholland Add some notes about the atomicity of dup2().
20140722 dholland Add notes about the limits of syscall atomicity in
........ multithreaded processes. From Jared Pochtar.
20140722 dholland Add redirect test to check stdin/stdout redirection.
20140722 dholland Fix emufs handling of seek positions beyond 2^32.
20140722 dholland Add bigseek test for checking seeks beyond 2^32.
20140721 dholland Add file open mode checks to badcall.
20140721 dholland Fix interaction of kmalloc guards and kmalloc labels.
20140721 dholland Be more conservative about panic on stray interrupt.
20140721 dholland Fix userland build to not rebuild unnecessarily.
20140721 dholland Fix userland build to not belch on removed .h files.
20140721 dholland In badcall, don't shout if mkdir isn't implemented.
20140717 dholland Fix misleading comments and variable names in proc.c.
20140716 dholland Add -w option to parallelvm to wait for forking.
20140716 dholland Replace a busywait in badcall with the new semaphores.
20140716 dholland Provide userlevel semaphores via semfs filesystem.
........ Open "sem:<name>", then read to P() and write to V().
20140716 dholland Move the just-fail vnode op stubs to VFS.
20140710 dholland Added new test program: sbrktest.
20140710 dholland Make the libc qsort() actually quicksort.
20140709 dholland Ship qsort() in libc, not in sfsck's compat code.
20140709 dholland SWAP{S,L,LL} -> SWAP{16,32,64} in sfs tools.
20140709 dholland Fix reversed found/expected printout in frack check.
20140518 dholland Fix embarrasing sort bugs in native sfsck.
20140430 dholland Add poisondisk tool for testing file system recovery.
20140428 dholland Add hostcompat logic for 64-bit byte-swapping.
20140417 dholland Fix zero to use page-sized sbrk calls.
20140415 dholland Rewrite dumpsfs and make it much more useful.
20140414 dholland Fix missing initialization of cpu->c_spinlocks.
20140410 dholland Fix bug in malloc changes. Add assertion to malloctest.
20140326 dholland Make userlevel malloc allocate in page-sized chunks.
20140326 dholland Fix the (unused) 64-bit userlevel malloc code.
20140314 dholland Make forktest show how much output is expected.
20140220 dholland Add new sy4 test for CVs.
20140211 dholland Tidy some logic in thread_make_runnable.
20140211 dholland Mark threads READY when waking them. From Anne Madoff.
20140201 dholland Fix some outdated comments, reported by Emmet Jao.
20140128 dholland Fix default OSTREE in configure script.
20140123 dholland OS/161 1.99.07 released.
20140123 dholland Add "frack" test (filesystem recover and check).
20140123 dholland Add factorial test that computes using execv.
20140123 dholland Add fs6 test that creates lots of small files.
20140122 dholland Mark enter_new_process and related code __DEAD.
20140122 dholland Make the semaphore counter unsigned.
20140122 dholland When kmalloc gets a page, assert that it's aligned.
20140122 dholland Fix error leak in sfs_balloc; from Christian Anderson.
20140122 dholland Use ssize_t and pid_t more in unistd.h.
20140122 dholland Add discussion of ARG_MAX to execv man page.
20140122 dholland Add missing <stdbool.h> for userland.
20140122 dholland Added sparsefile test program for making sparse files.
20140122 dholland splx() needs to work before curcpu/curthread exists.
20140122 dholland Clarify that proc_remthread requires splhigh.
20140115 dholland Remove VOP_INIT/CLEANUP macros. Use vnode_init/cleanup.
20140115 dholland Make device open/close eachopen/lastclose like vnodes.
20140115 dholland Move vfs-level device ops to an ops table struct.
20140115 dholland Clarify/correct comments pertaining to O_APPEND.
20140114 dholland Reorganize SFS sources.
20131112 dholland In SFS, always provide N{,D,T}INDIRECT macros.
20131112 dholland Reorganize sfsck sources; rework and improve sfsck.
20131110 dholland Don't use uninitialized file permissions in badcall.
20131110 dholland Provide __UNUSED along with __PF and __DEAD.
20131108 dholland Rearrange (and fix) hacks for _exit() returning.
........ It now faults on "0xeeeee00f" if it can't exit.
20131107 dholland Handle TLB pipeline hazards correctly.
20131107 dholland Add some sample/experimental gdb scripts.
20131107 dholland Make the console polling logic not use internal vars.
20131107 dholland Have wchan_sleep assert if holding extra spinlocks.
20131107 dholland Don't use assignment numbers for kernel configs.
20131107 dholland Remove the synch problems from the base system.
20131107 dholland Rename src/user -> src/userland. Seems to be the best
........ choice among a number of unappealing alternatives.
20131105 dholland Disallow EINVAL for "no such process" in badcall.
20131105 dholland Clean up sh's use of exit codes.
20131105 dholland Have testbin/crash check the signal numbers produced.
20131105 dholland Create an array of all wchans for debug purposes.
20131105 dholland Rearranged wchan API to make wchans more like CVs.
20131105 dholland Print the processor ID and version correctly.
20131105 dholland Fix boot on pre-multiprocessor System/161.
20131105 dholland Parallelize the kernel depend logic.
20131104 dholland Add and use memory barrier ops header. Minor impact.
20131104 dholland Rename sfs_inode to sfs_dinode.
20131101 dholland Edit and revise the man pages. Add some missing ones.
20131101 dholland Updated the docs and specs for waitpid.
20131030 dholland Use execvp() in sh. Don't have to type /bin/cat now.
20131030 dholland Provide getenv() and execvp() in libc.
20131030 dholland enter_user_process() now accepts an environ pointer.
20131030 dholland Add quinthuge, quintmat, quintsort tests.
20131030 dholland Added a libtest with common stuff for testbin/.
20131030 dholland Rewrote the .depend-munging script to be readable.
20131030 dholland Use ENOSYS (standard) instead of EUNIMP (which isn't).
20131030 dholland Fix badcall to expect with null status to succeed.
20131030 dholland Don't use unportable function casts in sfs.
20131029 dholland Add a memory leak detection mode to kmalloc.
20131029 dholland Add more kmalloc debugging modes and checks.
20131028 dholland Move the whole-filesystem ops to an ops table struct.
20131028 dholland Use designated initializers for the vnode ops tables.
20131028 dholland Fix the way thread_panic zaps the run queue.
20131028 dholland Moved memset.c to common/ for use in the kernel.
20131028 dholland Mark thread_exit() __DEAD.
20131028 dholland Fix addrspace handling in proc_destroy().
20131025 dholland Improved kmalloc to support larger kernel heaps.
20131025 dholland Add another kmalloc test, this one of variable size.
20131025 dholland Make printf accept %zd/%zu for size_t.
20130531 dholland Add tests for the threadlist code.
20130531 dholland Fix threadlist iterators again. From Steven Talbot.
20130531 dholland Do thread migration *before* running the scheduler.
20130531 dholland Add some more assertions to kfree.
20130531 dholland Make badcall understand wait-for-any waitpid().
20130531 dholland Provide a predepend: hook for makefiles.
20130531 dholland Put .depend files in build tree where they belong.
20130531 dholland Fix depends bug in os161.hostcompile.mk.
20130531 dholland Remove getinterval(); replace with timespec arithmetic.
20130531 dholland Use struct timespec inside the kernel.
20130531 dholland Move kern/startup -> kern/main, like it was in 1.x.
20130531 dholland Add "zero" test; checks if the VM system zeros pages.
20130531 dholland Change as_activate() to always activate curproc's AS.
20130531 dholland Provide both thread and process structures by default.
20130530 dholland Fix the scheme for probing LAMEbus device versions;
........ don't require lockstep upgrades for System/161 changes.
20130530 dholland Fix typo in comment, from Saagar Deshpande.
20130530 dholland Add comment warning against borrowing from dumbvm.
20130530 dholland Increase DUMBVM_STACKPAGES so 64K argv blocks will fit.
20130514 dholland Teach sfsck to handle dirs with invalid inode numbers.
20130503 dholland Fix another problem in the inode array in sfsck.
........ Reported by multiple students.
20130429 dholland Fix sfsck bitmap-checking problem.
20130311 dholland Declare panic() and badassert() noreturn.
20130308 dholland Fix fd leak in badcall, found by George Kulakowski.
20130306 dholland Fix off_t printing in randcall, found by David Palmer.
20110427 dholland Fix typo in badcall, from Andy Brody.
20110425 dholland Fix catastrophic bug in sfsck. Found by Jim Danz.
20110420 dholland Add new bigexec test for checking large argvs.
20110319 dholland Use va_copy() in __printf. (At least if available.)
20110223 dholland array.h needs cdefs.h and lib.h. Caught by Amy Tai.
20110127 dholland Fix host-psort build problem caused by glibc on Linux.
20110126 dholland OS/161 1.99.06 released.
20110126 dholland Fix some parallel build problems.
20110126 dholland Rename fs5 test to "long stress test".
20110126 dholland Clarify that struct tlbshootdown is a placeholder.
20110126 dholland Fix randcall makefile to put calls.c in the build dir.
20110126 dholland VOP_OPEN -> VOP_EACHOPEN; VOP_CLOSE -> VOP_LASTCLOSE.
20110126 dholland Name struct spinlock's members splk_*, not lk_*.
20110126 dholland sfs_fs.c -> sfs_fsops.c, sfs_vnode.c -> sfs_vnops.c
20100819 dholland Fix the stray console IRQs problem properly. This
........ requires System/161 1.99.05 or higher.
20100819 dholland Revert start/endpolling hack for stray console IRQs.
........ (But keep the code for masking interrupts.)
20100819 dholland Don't leave the IPI spinlock dangling on a panic IPI.
20100108 dholland OS/161 1.99.05 released.
20100108 dholland Don't cut corners with relocs in mips-exception1.S.
20100108 dholland Rearrange how curthread/curcpu get defined, so the
........ mips gdb can see curthread.
20100108 dholland Disable BSS zeroing in loadelf, because VM systems
........ should already provide zeroed pages. Make dumbvm do so.
20100108 dholland Add ASST3-OPT optimizing config.
20100108 dholland Add the usermalloc design doc to design/.
20100108 dholland Add the shell's design doc to design/.
20100108 dholland Fix outdated comment in start.S.
20100108 dholland Move clocksleep() decl to <clock.h>.
20100107 dholland Clarify various comments that seem lacking.
20090427 dholland Fix miscommented uio direction constants. Doh.
........ Found by the students...
20090424 dholland Add missing as_activate(NULL) during thread exit.
20090416 dholland Fix err/warn vs. errx/warnx usage in various tests.
........ Mostly from Robert J. Helblin and Peter Salas.
20090413 dholland Use EFBIG, not EINVAL, for "file too large".
20090402 dholland Make sbrk badcall "unaligned negative" really negative.
20090402 dholland Add clarifying comments to struct tlbshootdown.
20090320 dholland Fix DEBUG() so it accepts zero vararg parameters.
20090214 dholland Remove some references to obsolete name "md_usermode".
20090213 dholland Note that wchans don't promise to be FIFO.
20090205 dholland Add missing 'volatile' to spinlock.h.
20090414 dholland OS/161 1.99.04 released.
20090414 dholland Fix typo in kern/sfs.h.
20090414 dholland Fix testbin/psort up so it works adequately on sfs.
20090413 dholland Make sfsck track indirect blocks in the free map right.
20090413 dholland Fix bug where sfsck chokes on size 0 directories.
20090413 dholland Fix case where sfsck can't add missing ./.. entries.
20090413 dholland Add sfsck, simple check/recovery tool for sfs.
20090402 dholland OS/161 1.99.03 released.
20090402 dholland Fix build of testbin/malloctest.
20090320 dholland Check CURCPU_EXISTS in spinlock_do_i_hold.
20090313 dholland Fix threadlist iterator macros.
20090219 dholland OS/161 1.99.02 released.
20090219 dholland Add missing W* macros with waitpid in testbin progs.
20090219 dholland Work around gcc tailcall bug affecting testbin/crash.
20090219 dholland Fix missing vfs_biglock ops in vfs_getcwd().
20090219 dholland Fix bad userland declaration of lseek().
20090219 dholland Fix userland .depend file generation.
20090219 dholland Add join32to64 and split64to32.
20090219 dholland Clarify some comments in the mips syscall.c.
20090219 dholland Make stack frames in assembly code 64-bit aligned.
20090217 dholland Fix some glitches in the shell.
20090210 dholland Fix interrupt level management in trap handling.
20090209 dholland The on-chip timers can't be used for clocksleep().
20090203 dholland OS/161 1.99.01 released.
20090202 dholland Don't ever migrate curthread to another cpu.
20090202 dholland Use the W* wait macros in the shell.
20090202 dholland Document the W* wait macros.
20090202 dholland OS/161 1.99.00 released.
20090201 dholland Fix some bugs.
20090201 dholland Add an input buffer to the console device.
20090201 dholland Change kernel load address to waste less low memory.
20090201 dholland Implement kernel-side support for the GP register.
20090201 dholland Update man pages for 2.x.
20090201 dholland Remove the built-in copy of make. Too much realism;
it creates unnecessary hassles. Just ship make with
the toolchain.
200901** dholland Assorted major hacking to prepare first pre-2.0 tree.
Multiprocessor support.
Improve organization of source tree.
Add the shell and user malloc to the base system.
20081224 dholland Begin importing OS/161 1.x bits.
(OS/161 2.x branches off from what's projected to be
OS/161 1.x release 1.12.)
OS/161 1.x change log:
------------------------------------------------------------
20090115 dholland Fix wrong comment in lib.h.
20090106 dholland Fix typo in error message in newvers.sh.
20080825 dholland Fix typo in comment in start.S.
20080825 dholland Add curspl assertion to thread_yield.
(Reported by Melissa O'Neill a long time ago.)
20050913 dholland OS/161 1.11 released.
20050907 dholland Minor changes for clean build under gcc 4.0.1.
20050321 dholland Add volatile to testbin/ctest. (found by Qicheng Ma)
20050307 dholland Create <machine/ktypes.h> for vaddr_t/paddr_t.
20050228 dholland Some standards compliance. (found by R.L. West)
20040510 dholland Fix args handling in testbin/tail. (Lukasz Strozek)
20040204 dholland Be more consistent about refcounts in vfscwd.c.
20040203 dholland OS/161 1.10 released.
20040203 dholland Support for hosting OS/161 on Solaris.
20040202 dholland Update stdarg.h for gcc 3.x; remove machine/stdarg.h.
20031227 dholland OS/161 1.09 released.
20031224 dholland Add missing man page for triplesort.
20031224 dholland Fix failed compile in lnet.c, currently a null driver.
20031224 dholland Fix badcall so it doesn't blow up on empty stdin.
20031224 dholland Fix argument handling in bin/ln. (Hassan Sultan)
20031224 dholland Fix link count leak in sfs_rename. (Brian Greenberg)
20031224 dholland Fix silly use-after-free in an SFS mount error path.
20031224 dholland Fix unaligned sections in dumbvm. (Mike Hamburg)
20031224 dholland Change "asst1probs" to "synchprobs".
20031224 dholland Refer to assts by content, not number, where possible.
20031224 dholland Fix some nonsensical but working code in /bin/pwd.
20031224 dholland Update stack assertions in mips/trap.c for 4k stacks.
20031224 dholland Install kernels using their configuration name.
20031224 dholland Clarify some aspects of the locks/CVs API.
20031224 dholland Fix assorted comment typos and glitches.
20030626 dholland Commit the fix for a refcounting mistake in SFS.
20030626 dholland Fix glitch in one of the dup2 tests in testbin/badcall.
20030626 dholland Add missing sized type in mksfs/support.h.
20030626 dholland Fix "make depend" glitch in dumpsfs.
20030626 dholland Fix minor off-by-one error in menu code.
20030421 dholland Fix assertion failure in kernel heap dump code.
20030421 dholland Fix crash in testbin/dirconc.
20030309 dholland Make shell accept being run with argc==0.
20030309 dholland Add support for WNOHANG to shell.
20030221 dholland OS/161 1.08 released.
20030221 dholland Fix broken hostcompat build with some Linux libcs.
20030207 gwa/dholland Fix broken ASST1 build caused by rushed release.
20030131 dholland OS/161 1.07 released.
20030131 gwa New assignment 1 problems for 2003.
20030129 dholland Make console device full-duplex.
20030129 dholland Check for short reads when loading executable headers.
20030129 dholland Make rmtest a single standalone executable.
20030129 dholland Make first thread stack also 4k rather than 8k.
20030129 dholland Fix minor VFS bug handling multiple leading slashes.
20030129 dholland Remove code duplication in triple* tests.
20030129 dholland Add triplesort test (like triplemat).
20030128 dholland Make f_test a single standalone executable.
20030128 dholland Add t_ prefix to struct thread members for consistency.
20030128 dholland bzero by words instead of bytes when properly aligned.
20030128 dholland Add memcmp() to libc.
20030127 dholland Minor fixes to parallelvm.
20030117 dholland OS/161 1.06 released.
20030110 dholland Fix bug in setjmp/longjmp.
20030110 dholland Add small explanatory comment to dev/lamebus/emu.c.
20021120 dholland Have configure script provide NM and HOST_NM.
20021120 dholland Merge hostcompat fixes for Mac OS X.
20021001 dholland Avoid undefined C behavior in atoi().
20020920 dholland Provide string names for mips trap codes.
20020920 dholland Fix handling of boot-time kernel memory faults.
20020917 dholland OS/161 1.05 released.
20020913 dholland Created this changelog from CVS log data.
20020904 dholland Cleanup/improvement for testbin/malloctest.
20020904 dholland Add code to shell to do timing of subprocesses.
20020904 dholland Adjust prototype for __time() for hostcompat reasons.
20020904 dholland Add parallelvm and dirconc to the default build.
20020904 dholland Add mode to testbin/crash to fork and run everything.
20020904 dholland Retry certain I/O errors in emufs and sfs.
20020904 dholland Make vfs_close not fail.
20020830 dholland Prohibit slashes and colons in volume names in mksfs.
20020830 dholland _O_RDWRMASK -> O_ACCMODE, per POSIX.
20020830 dholland Shrink kernel stacks from 8k to 4k.
20020830 dholland Merge the code for the 'p' and 's' menu commands.
20020830 dholland Don't use OPEN_MAX in the base system.
20020829 dholland Include a copy of the error strings in the kernel.
20020829 dholland Assert that spl is 0 on syscall entry and exit.
20020829 dholland Fixes and new tests for testbin/badcall.
20020829 dholland Add code and menu command for dumping kernel heap.
20020827 dholland Close current directory at shutdown time.
20020827 dholland Clear bootfs at shutdown time.
20020827 dholland Remove extraneous magic argument from free_kpages().
20020827 dholland Fix dangling lock bug in emufs.
20020826 dholland Man page fixes for read, write, waitpid.
20020808 dholland Make Ant-32 port mostly work.
20020625 dholland Kernel makefile tweak for stupid makes.
20020618 dholland Fixes to the Ant-32 port.
20020617 dholland Update the (unreleased) Ant-32 port.
20020523 dholland Make matmult exit 1 on failure.
20020523 dholland Fix various forking userlevel tests to wait properly.
20020523 dholland Check for short reads when loading executables.
20020523 dholland Fix bug in tt3 test.
20020523 dholland Some make/build fixes.
20020523 dholland More mips calling conventions fixes.
20020522 dholland Fix bug in new mips exception code.
20020522 dholland Revamp testbin/badcall.
20020515 dholland Various accumulated minor cleanups and fixes.
20020515 dholland New tests: dirconc, parallelvm.
20020515 dholland Add missing V() in lhd driver.
20020515 dholland Fixes for the thread code.
20020515 dholland Tweak mips exception code for gdb's benefit.
20020515 dholland Clean up dumbvm code.
20020515 dholland Initialize mips stacks better, for gdb's benefit.
20020425 dholland Fixes for testbin/f_test.
20020424 dholland Fix kmalloc bug (found by Richard Eisenberg).
20020424 dholland Fix incorrect error codes in testbin/badcall.
20020424 dholland Move stray assert in vfs code.
20020407 dholland Fix off-by-one error in lhd driver.
20020325 dholland Fix memory leak in malloctest.
20020318 dholland Patch for race in thread_exit (fixed properly 5/15).
20020305 dholland Fix spl leak on thread_fork failure.
20020305 dholland Fix for testbin/crash.
20020216 dholland OS/161 1.04 released.
20020216 dholland Fix warning in kmalloc debugging code.
20020216 dholland Adjust testbin/badcall to assignment 2 requirements.
20020215 dholland Add cpu_halt() to supplement cpu_idle(), to fix crash.
20020215 dholland Fixes for matmult.
20020215 dholland Fix garbled comment in vm.h.
20020215 dholland Fix prototype of _exit().
20020208 dholland Fix stack frame of mips __start for gdb's benefit.
20020208 dholland Fix queue bug.
20020208 dholland Fix bug in testbin/{badcall,crash,faulter}.
20020131 dholland OS/161 1.03 released.
20020131 dholland Yield more on thread start (OPT_ASST1PROBS only).
20020131 dholland Fix whalemating code to match assignment.
20020131 dholland New asst1 problems for 2002.
20020131 dholland Include fix in mips pcb.h.
20020130 fedorova Adjust tt3 iteration counts/sizes.
20020129 georgi Fix broken mksfs and dumpsfs build.
20020124 dholland Put time() in libc; add __time() syscall.
20020124 dholland Have hostcompat make stdout and stderr unbuffered.
20020124 dholland Add sample optimizing config (ASST2-OPT).
20020124 dholland New tests: dirseek, rmdirtest, triplemat.
20020123 dholland Move matmult2 over original matmult.
20020123 dholland Assert nobody's waiting when destroying a semaphore.
20020123 dholland Add driver for new ltrace device.
20020123 dholland Fix cosmetic bug in hardclock config.
20020121 dholland Support ls over emufs.
20020121 dholland Fix bug in copyinstr/copyoutstr code.
20020121 dholland Fix broken Linux build of libhostcompat.
20020119 dholland Alter dumbvm and loadelf for new toolchain.
20020117 dholland Check for stack overflow during context switch.
20020117 dholland Stop using -O2 with -g for mips.
20020117 dholland More mips calling conventions fixes.
20020117 dholland Correct the inline asm in spl.c.
20020117 dholland Remove machine/inlineasm.h; fold into spl.c.
20020117 dholland Avoid using default make-supplied CFLAGS.
20020117 dholland Fix use of libhostcompat in mksfs and dumpsfs.
20020117 dholland Fix cosmetic bug in configure script.
20020116 dholland Adjust various things for new toolchain.
20020110 dholland Install hostcompat includes properly.
20020110 dholland Various fixes for new gcc (3.0.3) and binutils.
20020104 dholland More man pages.
20020103 dholland Remove excess register saves from mips context switch.
20020103 dholland Move old getcwd to __getcwd; put POSIX getcwd in libc.
20020103 dholland Tinker with tt3 test.
20020102 dholland Change thread_fork so it can return errors.
20020102 dholland Preallocate various things to avoid dying in mi_switch.
20010925 dholland Add a bunch of consistency checks to sfs.
20010925 dholland Fix bug in new panic code.
20010925 dholland Add menu command to panic intentionally.
20010925 dholland Fix bug in emufs.
20010925 dholland memcpy by words instead of bytes when properly aligned.
20010925 dholland Use setjmp() and longjmp() for aborting copyin/copyout.
20010925 dholland Add code for setjmp() and longjmp().
20010921 dholland Add VOP_KILL (undoes VOP_INIT, which can now fail too.)
20010921 dholland Fix race conditions in vnode reclaim.
20010921 dholland Fix VFS behavior for things like "rmdir foo:".
20010921 dholland OS/161 1.02 released.
20010921 dholland Revise device config/attach code.
20010920 dholland Standards compliance fixes for strchr/strrchr.
20010920 dholland Fix bug in system().
20010919 dholland More man pages.
20010918 dholland Changed MAXNAMLEN to NAME_MAX.
20010918 dholland Fix bug in kernel menu pwd command.
20010918 dholland Panic handling improvements.
20010918 dholland Kernel bootup and shutdown cleanup.
20010918 dholland Fixes for testbin/badcall.
20010824 dholland Make config script probe for <err.h>.
20010821 dholland Changes to queue code for consistent naming.
20010808 dholland Add man pages.
20010808 dholland The shell can now use <err.h> again, so do so.
20010808 dholland Add explicit support for host-runnable programs.
20010807 dholland Clean up -nostdinc/-nostdlib handling.
20010807 dholland Fix bug in cp.
20010807 dholland New test in testbin/crash.
20010807 dholland Fixes for testbin/malloctest.
20010806 dholland Fix glitch in testbin/badcall.
20010806 dholland New test: randcall.
20010804 dholland Add missing strrchr proto to <string.h>.
20010803 dholland Clean up ls; among other things, fix ls -R.
20010803 dholland Fixes for testbin/badcall.
20010803 dholland Add memset() to libc.
20010803 dholland Split part of testbin/crash to new testbin/badcall.
20010802 dholland Add comments to testbin describing intended uses.
20010802 dholland Fix testbin/ctest to be large enough to be interesting.
20010802 dholland Fix testbin/sort to be quicksort instead of bubble.
20010802 dholland Various minor testbin fixes/cleanup.
20010802 dholland Add dummy <fcntl.h> to make porting easier.
20010802 dholland Add dummy <time.h> to make porting easier.
20010802 dholland Add dummy <sys/ioctl.h> to make porting easier.
20010802 dholland Add dummy <sys/reboot.h> to make porting easier.
20010802 dholland Add dummy <sys/wait.h> to make porting easier.
20010802 dholland Have kfree deadbeef out free blocks.
20010801 dholland Time execution of every kernel menu command.
20010801 dholland Add getinterval() function for subtracting times.
20010801 dholland Print commands as they execute from the command string.
20010801 dholland New test tt3; add atoi from libc to kernel build.
20010801 dholland Add memcpy from libc.
20010801 dholland Fix size_t and add memcpy() to libc.
20010801 dholland Reset mips TLB at boot time.
20010801 dholland Revise kernel menu layout.
20010801 dholland Add tests for arrays, bitmaps, queues, and semaphores.
20010801 dholland Add "reconfig" rule to kernel makefiles.
20010801 dholland Fix queue code.
20010731 dholland Move main.c from kern/thread to kern/main.
20010730 dholland Add kernel menu command to unmount things.
20010730 dholland Add vfs_unmountall() for shutdown time.
20010730 dholland Report mounts to the console as they happen.
20010730 dholland Abolish pointless kernel shutdown functions.
20010726 dholland Add random: device accessible through VFS.
20010726 dholland Add pseudorand device for when hardware is missing.
20010726 dholland Add config support for pseudo-devices.
20010724 dholland Yield randomly at thread start if OPT_ASST1PROBS set.
20010724 dholland Clarify comments in mips exception.S.
20010724 dholland Don't allow calling P() from an interrupt handler.
20010724 dholland Fixes for lser driver.
20010723 dholland More mips calling conventions fixes.
20010626 dholland Add pwd and sync to kernel menu.
20010626 dholland Massive changes to kernel menu UI.
20010619 dholland Change as_copy so it can return error codes.
20010619 dholland Merge bitmap_isset() from sol3.
20010619 dholland Various fixes for new dumbvm.
20010619 dholland Fix overly enthusiastic test in vnode_check().
20010619 dholland Provide a sketch of the skeleton for doing fork.
20010618 dholland Add asserts to synch code.
20010618 dholland Clean up/clarify syscall entry code.
20010618 dholland New dumbvm supporting multiple address spaces.
20010618 dholland Remove mips dependencies from loadelf.c.
20010618 dholland Add hacks to prevent looping "Unknown syscall -1".
20010615 dholland Merge the kmalloc and kfree from sol3.
20010614 dholland Move kernel menu stuff to its own file.
20010614 dholland Fixes for sfs and vfs layer.
20010612 dholland Add sfs_rwblock to encapsulate sfs_device->d_io().
20010612 dholland Add lbolt and clocksleep() functionality to kernel.
20010612 dholland Add -W to standard warning options.
20010611 dholland Abolish rcsids.
20010611 dholland Fix memory leak on error in thread_fork.
20010611 dholland Don't panic if kmalloc fails. Add checks.
20010611 dholland Add VOP_MAGIC to vnode ops tables, and lots of checks.
20010611 dholland Add array_setguy().
20010608 dholland Add random() and srandom() to libc.
20010608 dholland Add some framework for user-level malloc to libc.
20010608 dholland Correct prototypes for read() and write().
20010608 dholland kprintf synchronization cleanups.
20010523 dholland Allow DEL as well as BS for backspacing in shell.
20010523 dholland Add warning about the consequences of touching paddr 0.
20010523 dholland Fix open count handling on VOP_CLOSE error.
20010523 dholland New test: malloctest.
20010428 dholland Handle multiple leading slashes on pathnames.
20010423 dholland Fix deadlock in vfs layer.
20010423 dholland Fix bug in testbin/dirtest.
20010423 dholland Fix multiple bugs in ls.
20010422 dholland Fix bug in sfs.
20010419 dholland Fix bug in sfs (patch from Amos Blackman).
20010416 dholland Fix fstest code.
20010416 dholland Remove stray debug output from dumpsfs.
20010414 dholland Fix host mksfs/dumpsfs build on DU.
20010414 dholland Makefile fix: build mksfs and dumpsfs by default.
20010414 dholland Fix bug in sfs (found by Dafina Toncheva).
20010414 dholland Fix endianness bug in dumpsfs.
20010414 dholland Do a sync at shutdown time.
20010414 dholland Format depend.mk files consistently.
20010414 dholland Fix memory leak in sfs.
20010413 dholland Allow VOP_FSYNC on sfs directories.
20010412 dholland Detect infinite loop triggerable by uio misuse.
20010411 dholland Fix bug in bitmap code.
20010406 dholland Fix calling conventions in mips asm code.
20010323 dholland Fix multi-sector lhd I/Os (found by Jeff DeSoto).
20010322 dholland Fix bug in comment in pcb.c (found by Jeffrey Enos).
20010319 dholland Make matmult smaller.
20010318 moorthi Fix bug in array code.
20010314 dholland Fix bug in mv (found by Edward Lim).
20010314 dholland Fix bug in testbin/crash (found by Mike Vernal).
20010314 dholland Fix bug in bitmap code.
20010308 moorthi Fix bug in sfs.
20010226 dholland OS/161 1.01 released.
20010226 dholland Shell fixes.
20010226 dholland Add a lock to the console device.
20010226 dholland Fix another bug in copyin/copyout code.
20010226 dholland Add vfs_getdevname().
20010226 dholland Use device name for FSes that don't return a volname.
20010226 dholland Fix two bugs in pwd.
20010226 dholland Make /bin/pwd work in emufs.
20010225 dholland Fix bug in mips trap code.
20010225 dholland Fix bug in mips copyin/copyout code.
20010224 dholland Add appropriate volatile keywords in various places.
20010224 dholland Fix synchronization in placeholder kmalloc.
20010221 dholland Fix bug in CV code.
20010208 dholland OS/161 1.00 released.
20010208 dholland Add EBADF to error list.
20010208 dholland Fix specification of VOP_STAT.
20010208 blackman Fix naming of queue functions.
20010208 blackman Driver for lrandom device.
20010207 dholland Check all calls to thread_fork for failure.
20010206 dholland Fix comment in mips/specialreg.h.
20010205 dholland Prevent recursive scheduler calls. (Fixes crash.)
20010205 dholland Make syscall wrapper generation more robust.
20010205 dholland Fix bug in cp.
20010202 dholland OS/161 0.99 released.
20010202 dholland Add host-sh (host-runnable version) to sh makefile.
20010202 dholland Add licensing boilerplate.
20010201 dholland Switch from getfilesize() to fstat().
20010201 dholland Add system().
20010130 dholland Add strtok() and strtok_r().
20010129 dholland Add ELF code.
20010111 dholland Fix bug in ls.
20010103 dholland Initial checkin of development tree.

71
Makefile Normal file
View File

@ -0,0 +1,71 @@
#
# Toplevel makefile for OS/161.
#
#
# Main rules:
# all (default): depend and compile system; install into staging area
# rebuild: likewise, but start with a clean slate.
# fullrebuild: likewise, but start with a very clean slate.
#
# What all does, in order:
# tools: depend and compile the tools used in build.
# includes: install header files.
# build: depend and compile the system.
#
# Other targets:
# depend: just update make dependency information.
# tags: generate/regenerate "tags" files.
# install: install into $(OSTREE).
# clean: remove generated files.
# distclean: remove all generated files.
#
TOP=.
.include "$(TOP)/mk/os161.config.mk"
all:; # make this first
MKDIRS=$(OSTREE)
.include "$(TOP)/mk/os161.mkdirs.mk"
all: tools .WAIT includes .WAIT build
rebuild:
$(MAKE) clean
$(MAKE) all
fullrebuild:
$(MAKE) distclean
$(MAKE) all
# currently no tools required, hence no tools/ dir or work to do
tools:
@true
build:
(cd userland && $(MAKE) build)
(cd man && $(MAKE) install-staging)
includes tags depend:
(cd kern && $(MAKE) $@)
(cd userland && $(MAKE) $@)
clean:
(cd kern && $(MAKE) $@)
(cd userland && $(MAKE) $@)
rm -rf $(INSTALLTOP)
distclean: clean
rm -rf $(WORKDIR)
install: $(OSTREE)
(cd $(INSTALLTOP) && tar -cf - .) | (cd $(OSTREE) && tar -xvf -)
.PHONY: all rebuild fullrebuild tools build includes tags depend
.PHONY: clean distclean
# old BSD name, same as distclean
cleandir: distclean
.PHONY: cleandir

View File

@ -0,0 +1,7 @@
These are support functions needed by gcc to perform operations on
64-bit integer types on 32-bit machines. The names are meaningful to
the gcc back end. The term "millicode" is sometimes used to describe
such compiler support code.
This code was taken from NetBSD's src/common/lib/libc/quad, and
polished some for OS/161.

View File

@ -0,0 +1,56 @@
/*-
* Copyright (c) 1992, 1993
* The Regents of the University of California. All rights reserved.
*
* This software was developed by the Computer Systems Engineering group
* at Lawrence Berkeley Laboratory under DARPA contract BG 91-66 and
* contributed to Berkeley.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* From:
* @(#)adddi3.c 8.1 (Berkeley) 6/4/93
* NetBSD: adddi3.c,v 1.1 2005/12/20 19:28:51 christos Exp
*/
#include "longlong.h"
/*
* Add two long longs. This is trivial since a one-bit carry from a
* single unsigned int addition x+y occurs if and only if the sum x+y
* is less than either x or y (the choice to compare with x or y is
* arbitrary).
*/
long long
__adddi3(long long a, long long b)
{
union uu aa, bb, sum;
aa.ll = a;
bb.ll = b;
sum.ui[L] = aa.ui[L] + bb.ui[L];
sum.ui[H] = aa.ui[H] + bb.ui[H] + (sum.ui[L] < bb.ui[L]);
return (sum.ll);
}

View File

@ -0,0 +1,53 @@
/*-
* Copyright (c) 1992, 1993
* The Regents of the University of California. All rights reserved.
*
* This software was developed by the Computer Systems Engineering group
* at Lawrence Berkeley Laboratory under DARPA contract BG 91-66 and
* contributed to Berkeley.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* From:
* @(#)anddi3.c 8.1 (Berkeley) 6/4/93
* NetBSD: anddi3.c,v 1.1 2005/12/20 19:28:51 christos Exp
*/
#include "longlong.h"
/*
* Return a & b, in long long.
*/
long long
__anddi3(long long a, long long b)
{
union uu aa, bb;
aa.ll = a;
bb.ll = b;
aa.ui[0] &= bb.ui[0];
aa.ui[1] &= bb.ui[1];
return (aa.ll);
}

View File

@ -0,0 +1,61 @@
/*-
* Copyright (c) 1992, 1993
* The Regents of the University of California. All rights reserved.
*
* This software was developed by the Computer Systems Engineering group
* at Lawrence Berkeley Laboratory under DARPA contract BG 91-66 and
* contributed to Berkeley.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* From:
* @(#)ashldi3.c 8.1 (Berkeley) 6/4/93
* NetBSD: ashldi3.c,v 1.1 2005/12/20 19:28:51 christos Exp
*/
#include "longlong.h"
/*
* Shift a (signed) long long value left (arithmetic shift left).
* This is the same as logical shift left!
*/
long long
__ashldi3(long long a, unsigned int shift)
{
union uu aa;
if (shift == 0)
return(a);
aa.ll = a;
if (shift >= INT_BITS) {
aa.ui[H] = aa.ui[L] << (shift - INT_BITS);
aa.ui[L] = 0;
} else {
aa.ui[H] = (aa.ui[H] << shift) |
(aa.ui[L] >> (INT_BITS - shift));
aa.ui[L] <<= shift;
}
return (aa.ll);
}

View File

@ -0,0 +1,73 @@
/*-
* Copyright (c) 1992, 1993
* The Regents of the University of California. All rights reserved.
*
* This software was developed by the Computer Systems Engineering group
* at Lawrence Berkeley Laboratory under DARPA contract BG 91-66 and
* contributed to Berkeley.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* From:
* @(#)ashrdi3.c 8.1 (Berkeley) 6/4/93
* NetBSD: ashrdi3.c,v 1.1 2005/12/20 19:28:51 christos Exp
*/
#include "longlong.h"
/*
* Shift a (signed) long long value right (arithmetic shift right).
*/
long long
__ashrdi3(long long a, unsigned int shift)
{
union uu aa;
if (shift == 0)
return(a);
aa.ll = a;
if (shift >= INT_BITS) {
int s;
/*
* Smear bits rightward using the machine's right-shift
* method, whether that is sign extension or zero fill,
* to get the `sign word' s. Note that shifting by
* INT_BITS is undefined, so we shift (INT_BITS-1),
* then 1 more, to get our answer.
*/
/* LINTED inherits machine dependency */
s = (aa.si[H] >> (INT_BITS - 1)) >> 1;
/* LINTED inherits machine dependency*/
aa.ui[L] = aa.si[H] >> (shift - INT_BITS);
aa.ui[H] = s;
} else {
aa.ui[L] = (aa.ui[L] >> shift) |
(aa.ui[H] << (INT_BITS - shift));
/* LINTED inherits machine dependency */
aa.si[H] >>= shift;
}
return (aa.ll);
}

View File

@ -0,0 +1,54 @@
/*-
* Copyright (c) 1992, 1993
* The Regents of the University of California. All rights reserved.
*
* This software was developed by the Computer Systems Engineering group
* at Lawrence Berkeley Laboratory under DARPA contract BG 91-66 and
* contributed to Berkeley.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* From:
* @(#)cmpdi2.c 8.1 (Berkeley) 6/4/93
* NetBSD: cmpdi2.c,v 1.1 2005/12/20 19:28:51 christos Exp
*/
#include "longlong.h"
/*
* Return 0, 1, or 2 as a <, =, > b respectively.
* Both a and b are considered signed---which means only the high word is
* signed.
*/
int
__cmpdi2(long long a, long long b)
{
union uu aa, bb;
aa.ll = a;
bb.ll = b;
return (aa.si[H] < bb.si[H] ? 0 : aa.si[H] > bb.si[H] ? 2 :
aa.ui[L] < bb.ui[L] ? 0 : aa.ui[L] > bb.ui[L] ? 2 : 1);
}

View File

@ -0,0 +1,62 @@
/*-
* Copyright (c) 1992, 1993
* The Regents of the University of California. All rights reserved.
*
* This software was developed by the Computer Systems Engineering group
* at Lawrence Berkeley Laboratory under DARPA contract BG 91-66 and
* contributed to Berkeley.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* From:
* @(#)divdi3.c 8.1 (Berkeley) 6/4/93
* NetBSD: divdi3.c,v 1.1 2005/12/20 19:28:51 christos Exp
*/
#include "longlong.h"
/*
* Divide two signed long longs.
* ??? if -1/2 should produce -1 on this machine, this code is wrong
*/
long long
__divdi3(long long a, long long b)
{
unsigned long long ua, ub, uq;
int neg = 0;
ua = a;
ub = b;
if (a < 0)
ua = -ua, neg ^= 1;
if (b < 0)
ub = -ub, neg ^= 1;
uq = __qdivrem(ua, ub, NULL);
if (neg)
uq = - uq;
return uq;
}

View File

@ -0,0 +1,53 @@
/*-
* Copyright (c) 1992, 1993
* The Regents of the University of California. All rights reserved.
*
* This software was developed by the Computer Systems Engineering group
* at Lawrence Berkeley Laboratory under DARPA contract BG 91-66 and
* contributed to Berkeley.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* From:
* @(#)iordi3.c 8.1 (Berkeley) 6/4/93
* NetBSD: iordi3.c,v 1.1 2005/12/20 19:28:51 christos Exp
*/
#include "longlong.h"
/*
* Return a | b, in long long.
*/
long long
__iordi3(long long a, long long b)
{
union uu aa, bb;
aa.ll = a;
bb.ll = b;
aa.ui[0] |= bb.ui[0];
aa.ui[1] |= bb.ui[1];
return (aa.ll);
}

View File

@ -0,0 +1,144 @@
/*-
* Copyright (c) 1992, 1993
* The Regents of the University of California. All rights reserved.
*
* This software was developed by the Computer Systems Engineering group
* at Lawrence Berkeley Laboratory under DARPA contract BG 91-66 and
* contributed to Berkeley.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* From:
* @(#)quad.h 8.1 (Berkeley) 6/4/93
* NetBSD: quad.h,v 1.1 2005/12/20 20:29:40 christos Exp
*/
/*
* Long long arithmetic.
*
* This library makes the following assumptions:
*
* - The type long long exists.
*
* - A long long variable is exactly twice as long as `int'.
*
* - The machine's arithmetic is two's complement.
*
* This library can provide 128-bit arithmetic on a machine with
* 128-bit long longs and 64-bit ints, for instance, or 96-bit
* arithmetic on machines with 48-bit ints.
*
* The names are built into gcc.
*/
#if defined(_KERNEL)
#include <types.h>
#include <endian.h>
#else
#include <sys/types.h>
#include <sys/endian.h>
#endif
#include <limits.h>
/*
* Depending on the desired operation, we view a `long long' in
* one or more of the following formats.
*/
union uu {
long long ll; /* as a (signed) long long */
unsigned long long ull; /* as an unsigned long long */
int si[2]; /* as two (signed) ints */
unsigned int ui[2]; /* as two unsigned ints */
};
/*
* Define high and low parts of a long long.
*/
#if _BYTE_ORDER == _LITTLE_ENDIAN
#define H 1
#define L 0
#endif
#if _BYTE_ORDER == _BIG_ENDIAN
#define H 0
#define L 1
#endif
/*
* Total number of bits in a long long and in the pieces that make it up.
* These are used for shifting, and also below for halfword extraction
* and assembly.
*/
#define LONGLONG_BITS (sizeof(long long) * CHAR_BIT)
#define INT_BITS (sizeof(int) * CHAR_BIT)
#define HALF_BITS (sizeof(int) * CHAR_BIT / 2)
/*
* Extract high and low shortwords from longword, and move low shortword of
* longword to upper half of long, i.e., produce the upper longword of
* ((long long)(x) << (number_of_bits_in_int/2)).
* [`x' must actually be unsigned int.]
*
* These are used in the multiply code, to split a longword into upper
* and lower halves, and to reassemble a product as a long long, shifted
* left (sizeof(int)*CHAR_BIT/2).
*/
#define HHALF(x) ((unsigned int)(x) >> HALF_BITS)
#define LHALF(x) ((unsigned int)(x) & (((int)1 << HALF_BITS) - 1))
#define LHUP(x) ((unsigned int)(x) << HALF_BITS)
long long __adddi3 ( long long, long long);
long long __anddi3 ( long long, long long);
long long __ashldi3 ( long long, unsigned int);
long long __ashrdi3 ( long long, unsigned int);
int __cmpdi2 ( long long, long long);
long long __divdi3 ( long long, long long);
long long __iordi3 ( long long, long long);
long long __lshldi3 ( long long, unsigned int);
long long __lshrdi3 ( long long, unsigned int);
long long __moddi3 ( long long, long long);
long long __muldi3 ( long long, long long);
long long __negdi2 ( long long);
long long __one_cmpldi2 ( long long);
long long __subdi3 ( long long, long long);
int __ucmpdi2 (unsigned long long, unsigned long long);
unsigned long long __udivdi3 (unsigned long long, unsigned long long);
unsigned long long __umoddi3 (unsigned long long, unsigned long long);
long long __xordi3 ( long long, long long);
#ifndef _KERNEL
long long __fixdfdi (double);
long long __fixsfdi (float);
unsigned long long __fixunsdfdi (double);
unsigned long long __fixunssfdi (float);
double __floatdidf (long long);
float __floatdisf (long long);
double __floatunsdidf(unsigned long long);
#endif
unsigned long long __qdivrem (unsigned long long, unsigned long long,
unsigned long long *);

View File

@ -0,0 +1,61 @@
/*-
* Copyright (c) 1992, 1993
* The Regents of the University of California. All rights reserved.
*
* This software was developed by the Computer Systems Engineering group
* at Lawrence Berkeley Laboratory under DARPA contract BG 91-66 and
* contributed to Berkeley.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* From:
* @(#)lshldi3.c 8.1 (Berkeley) 6/4/93
* NetBSD: lshldi3.c,v 1.1 2005/12/20 19:28:51 christos Exp
*/
#include "longlong.h"
/*
* Shift an (unsigned) long long value left (logical shift left).
* This is the same as arithmetic shift left!
*/
long long
__lshldi3(long long a, unsigned int shift)
{
union uu aa;
if (shift == 0)
return(a);
aa.ll = a;
if (shift >= INT_BITS) {
aa.ui[H] = aa.ui[L] << (shift - INT_BITS);
aa.ui[L] = 0;
} else {
aa.ui[H] = (aa.ui[H] << shift) |
(aa.ui[L] >> (INT_BITS - shift));
aa.ui[L] <<= shift;
}
return (aa.ll);
}

View File

@ -0,0 +1,60 @@
/*-
* Copyright (c) 1992, 1993
* The Regents of the University of California. All rights reserved.
*
* This software was developed by the Computer Systems Engineering group
* at Lawrence Berkeley Laboratory under DARPA contract BG 91-66 and
* contributed to Berkeley.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* From:
* @(#)lshrdi3.c 8.1 (Berkeley) 6/4/93
* $NetBSD: lshrdi3.c,v 1.1 2005/12/20 19:28:51 christos Exp
*/
#include "longlong.h"
/*
* Shift an (unsigned) long long value right (logical shift right).
*/
long long
__lshrdi3(long long a, unsigned int shift)
{
union uu aa;
if (shift == 0)
return(a);
aa.ll = a;
if (shift >= INT_BITS) {
aa.ui[L] = aa.ui[H] >> (shift - INT_BITS);
aa.ui[H] = 0;
} else {
aa.ui[L] = (aa.ui[L] >> shift) |
(aa.ui[H] << (INT_BITS - shift));
aa.ui[H] >>= shift;
}
return (aa.ll);
}

View File

@ -0,0 +1,62 @@
/*-
* Copyright (c) 1992, 1993
* The Regents of the University of California. All rights reserved.
*
* This software was developed by the Computer Systems Engineering group
* at Lawrence Berkeley Laboratory under DARPA contract BG 91-66 and
* contributed to Berkeley.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* From:
* @(#)moddi3.c 8.1 (Berkeley) 6/4/93
* NetBSD: moddi3.c,v 1.1 2005/12/20 19:28:51 christos Exp
*/
#include "longlong.h"
/*
* Return remainder after dividing two signed long longs.
*
* XXX we assume a % b < 0 iff a < 0, but this is actually machine-dependent.
*/
long long
__moddi3(long long a, long long b)
{
unsigned long long ua, ub, ur;
int neg = 0;
ua = a;
ub = b;
if (a < 0)
ua = -ua, neg ^= 1;
if (b < 0)
ub = -ub;
(void)__qdivrem(ua, ub, &ur);
if (neg)
ur = -ur;
return (ur);
}

View File

@ -0,0 +1,241 @@
/*-
* Copyright (c) 1992, 1993
* The Regents of the University of California. All rights reserved.
*
* This software was developed by the Computer Systems Engineering group
* at Lawrence Berkeley Laboratory under DARPA contract BG 91-66 and
* contributed to Berkeley.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* From:
* @(#)muldi3.c 8.1 (Berkeley) 6/4/93
* NetBSD: muldi3.c,v 1.1 2005/12/20 19:28:51 christos Exp
*/
#include "longlong.h"
/*
* Multiply two long longs.
*
* Our algorithm is based on the following. Split incoming long long
* values u and v (where u,v >= 0) into
*
* u = 2^n u1 * u0 (n = number of bits in `unsigned int', usu. 32)
*
* and
*
* v = 2^n v1 * v0
*
* Then
*
* uv = 2^2n u1 v1 + 2^n u1 v0 + 2^n v1 u0 + u0 v0
* = 2^2n u1 v1 + 2^n (u1 v0 + v1 u0) + u0 v0
*
* Now add 2^n u1 v1 to the first term and subtract it from the middle,
* and add 2^n u0 v0 to the last term and subtract it from the middle.
* This gives:
*
* uv = (2^2n + 2^n) (u1 v1) +
* (2^n) (u1 v0 - u1 v1 + u0 v1 - u0 v0) +
* (2^n + 1) (u0 v0)
*
* Factoring the middle a bit gives us:
*
* uv = (2^2n + 2^n) (u1 v1) + [u1v1 = high]
* (2^n) (u1 - u0) (v0 - v1) + [(u1-u0)... = mid]
* (2^n + 1) (u0 v0) [u0v0 = low]
*
* The terms (u1 v1), (u1 - u0) (v0 - v1), and (u0 v0) can all be done
* in just half the precision of the original. (Note that either or both
* of (u1 - u0) or (v0 - v1) may be negative.)
*
* This algorithm is from Knuth vol. 2 (2nd ed), section 4.3.3, p. 278.
*
* Since C does not give us a `int * int = long long' operator, we split
* our input long longs into two ints, then split the two ints into two
* shorts. We can then calculate `short * short = int' in native
* arithmetic.
*
* Our product should, strictly speaking, be a `long long long', with
* 128 bits, but we are going to discard the upper 64. In other words,
* we are not interested in uv, but rather in (uv mod 2^2n). This
* makes some of the terms above vanish, and we get:
*
* (2^n)(high) + (2^n)(mid) + (2^n + 1)(low)
*
* or
*
* (2^n)(high + mid + low) + low
*
* Furthermore, `high' and `mid' can be computed mod 2^n, as any factor
* of 2^n in either one will also vanish. Only `low' need be computed
* mod 2^2n, and only because of the final term above.
*/
static long long __lmulq(unsigned int, unsigned int);
long long
__muldi3(long long a, long long b)
{
union uu u, v, low, prod;
unsigned int high, mid, udiff, vdiff;
int negall, negmid;
#define u1 u.ui[H]
#define u0 u.ui[L]
#define v1 v.ui[H]
#define v0 v.ui[L]
/*
* Get u and v such that u, v >= 0. When this is finished,
* u1, u0, v1, and v0 will be directly accessible through the
* int fields.
*/
if (a >= 0)
u.ll = a, negall = 0;
else
u.ll = -a, negall = 1;
if (b >= 0)
v.ll = b;
else
v.ll = -b, negall ^= 1;
if (u1 == 0 && v1 == 0) {
/*
* An (I hope) important optimization occurs when u1 and v1
* are both 0. This should be common since most numbers
* are small. Here the product is just u0*v0.
*/
prod.ll = __lmulq(u0, v0);
} else {
/*
* Compute the three intermediate products, remembering
* whether the middle term is negative. We can discard
* any upper bits in high and mid, so we can use native
* unsigned int * unsigned int => unsigned int arithmetic.
*/
low.ll = __lmulq(u0, v0);
if (u1 >= u0)
negmid = 0, udiff = u1 - u0;
else
negmid = 1, udiff = u0 - u1;
if (v0 >= v1)
vdiff = v0 - v1;
else
vdiff = v1 - v0, negmid ^= 1;
mid = udiff * vdiff;
high = u1 * v1;
/*
* Assemble the final product.
*/
prod.ui[H] = high + (negmid ? -mid : mid) + low.ui[L] +
low.ui[H];
prod.ui[L] = low.ui[L];
}
return (negall ? -prod.ll : prod.ll);
#undef u1
#undef u0
#undef v1
#undef v0
}
/*
* Multiply two 2N-bit ints to produce a 4N-bit long long, where N is
* half the number of bits in an int (whatever that is---the code
* below does not care as long as the header file does its part of the
* bargain---but typically N==16).
*
* We use the same algorithm from Knuth, but this time the modulo refinement
* does not apply. On the other hand, since N is half the size of an int,
* we can get away with native multiplication---none of our input terms
* exceeds (UINT_MAX >> 1).
*
* Note that, for unsigned int l, the quad-precision (long long) result
*
* l << N
*
* splits into high and low ints as HHALF(l) and LHUP(l) respectively.
*/
static long long
__lmulq(unsigned int u, unsigned int v)
{
unsigned int u1, u0, v1, v0, udiff, vdiff, high, mid, low;
unsigned int prodh, prodl, was;
union uu prod;
int neg;
u1 = HHALF(u);
u0 = LHALF(u);
v1 = HHALF(v);
v0 = LHALF(v);
low = u0 * v0;
/* This is the same small-number optimization as before. */
if (u1 == 0 && v1 == 0)
return (low);
if (u1 >= u0)
udiff = u1 - u0, neg = 0;
else
udiff = u0 - u1, neg = 1;
if (v0 >= v1)
vdiff = v0 - v1;
else
vdiff = v1 - v0, neg ^= 1;
mid = udiff * vdiff;
high = u1 * v1;
/* prod = (high << 2N) + (high << N); */
prodh = high + HHALF(high);
prodl = LHUP(high);
/* if (neg) prod -= mid << N; else prod += mid << N; */
if (neg) {
was = prodl;
prodl -= LHUP(mid);
prodh -= HHALF(mid) + (prodl > was);
} else {
was = prodl;
prodl += LHUP(mid);
prodh += HHALF(mid) + (prodl < was);
}
/* prod += low << N */
was = prodl;
prodl += LHUP(low);
prodh += HHALF(low) + (prodl < was);
/* ... + low; */
if ((prodl += low) < low)
prodh++;
/* return 4N-bit product */
prod.ui[H] = prodh;
prod.ui[L] = prodl;
return (prod.ll);
}

View File

@ -0,0 +1,52 @@
/*-
* Copyright (c) 1992, 1993
* The Regents of the University of California. All rights reserved.
*
* This software was developed by the Computer Systems Engineering group
* at Lawrence Berkeley Laboratory under DARPA contract BG 91-66 and
* contributed to Berkeley.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* From:
* @(#)negdi2.c 8.1 (Berkeley) 6/4/93
* NetBSD: negdi2.c,v 1.1 2005/12/20 19:28:51 christos Exp
*/
#include "longlong.h"
/*
* Return -a (or, equivalently, 0 - a), in long long. See subdi3.c.
*/
long long
__negdi2(long long a)
{
union uu aa, res;
aa.ll = a;
res.ui[L] = -aa.ui[L];
res.ui[H] = -aa.ui[H] - (res.ui[L] > 0);
return (res.ll);
}

View File

@ -0,0 +1,53 @@
/*-
* Copyright (c) 1992, 1993
* The Regents of the University of California. All rights reserved.
*
* This software was developed by the Computer Systems Engineering group
* at Lawrence Berkeley Laboratory under DARPA contract BG 91-66 and
* contributed to Berkeley.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* From:
* @(#)notdi2.c 8.1 (Berkeley) 6/4/93
* NetBSD: notdi2.c,v 1.1 2005/12/20 19:28:51 christos Exp
*/
#include "longlong.h"
/*
* Return ~a. For some reason gcc calls this `one's complement' rather
* than `not'.
*/
long long
__one_cmpldi2(long long a)
{
union uu aa;
aa.ll = a;
aa.ui[0] = ~aa.ui[0];
aa.ui[1] = ~aa.ui[1];
return (aa.ll);
}

View File

@ -0,0 +1,279 @@
/*-
* Copyright (c) 1992, 1993
* The Regents of the University of California. All rights reserved.
*
* This software was developed by the Computer Systems Engineering group
* at Lawrence Berkeley Laboratory under DARPA contract BG 91-66 and
* contributed to Berkeley.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* From:
* @(#)qdivrem.c 8.1 (Berkeley) 6/4/93
* NetBSD: qdivrem.c,v 1.1 2005/12/20 19:28:51 christos Exp
*/
/*
* Multiprecision divide. This algorithm is from Knuth vol. 2 (2nd ed),
* section 4.3.1, pp. 257--259.
*/
#include "longlong.h"
#define B ((int)1 << HALF_BITS) /* digit base */
/* Combine two `digits' to make a single two-digit number. */
#define COMBINE(a, b) (((unsigned int)(a) << HALF_BITS) | (b))
/* select a type for digits in base B: use unsigned short if they fit */
#if UINT_MAX == 0xffffffffU && USHRT_MAX >= 0xffff
typedef unsigned short digit;
#else
typedef unsigned int digit;
#endif
static void shl(digit *p, int len, int sh);
/*
* __qdivrem(u, v, rem) returns u/v and, optionally, sets *rem to u%v.
*
* We do this in base 2-sup-HALF_BITS, so that all intermediate
* products fit within unsigned int. As a consequence, the maximum
* length dividend and divisor are 4 `digits' in this base (they are
* shorter if they have leading zeros).
*/
unsigned long long
__qdivrem(unsigned long long ull, unsigned long long vll,
unsigned long long *arq)
{
union uu tmp;
digit *u, *v, *q;
digit v1, v2;
unsigned int qhat, rhat, t;
int m, n, d, j, i;
digit uspace[5], vspace[5], qspace[5];
/*
* Take care of special cases: divide by zero, and u < v.
*/
if (vll == 0) {
/* divide by zero. */
static volatile const unsigned int zero = 0;
tmp.ui[H] = tmp.ui[L] = 1 / zero;
if (arq)
*arq = ull;
return (tmp.ll);
}
if (ull < vll) {
if (arq)
*arq = ull;
return (0);
}
u = &uspace[0];
v = &vspace[0];
q = &qspace[0];
/*
* Break dividend and divisor into digits in base B, then
* count leading zeros to determine m and n. When done, we
* will have:
* u = (u[1]u[2]...u[m+n]) sub B
* v = (v[1]v[2]...v[n]) sub B
* v[1] != 0
* 1 < n <= 4 (if n = 1, we use a different division algorithm)
* m >= 0 (otherwise u < v, which we already checked)
* m + n = 4
* and thus
* m = 4 - n <= 2
*/
tmp.ull = ull;
u[0] = 0;
u[1] = (digit)HHALF(tmp.ui[H]);
u[2] = (digit)LHALF(tmp.ui[H]);
u[3] = (digit)HHALF(tmp.ui[L]);
u[4] = (digit)LHALF(tmp.ui[L]);
tmp.ull = vll;
v[1] = (digit)HHALF(tmp.ui[H]);
v[2] = (digit)LHALF(tmp.ui[H]);
v[3] = (digit)HHALF(tmp.ui[L]);
v[4] = (digit)LHALF(tmp.ui[L]);
for (n = 4; v[1] == 0; v++) {
if (--n == 1) {
unsigned int rbj; /* r*B+u[j] (not root boy jim) */
digit q1, q2, q3, q4;
/*
* Change of plan, per exercise 16.
* r = 0;
* for j = 1..4:
* q[j] = floor((r*B + u[j]) / v),
* r = (r*B + u[j]) % v;
* We unroll this completely here.
*/
t = v[2]; /* nonzero, by definition */
q1 = (digit)(u[1] / t);
rbj = COMBINE(u[1] % t, u[2]);
q2 = (digit)(rbj / t);
rbj = COMBINE(rbj % t, u[3]);
q3 = (digit)(rbj / t);
rbj = COMBINE(rbj % t, u[4]);
q4 = (digit)(rbj / t);
if (arq)
*arq = rbj % t;
tmp.ui[H] = COMBINE(q1, q2);
tmp.ui[L] = COMBINE(q3, q4);
return (tmp.ll);
}
}
/*
* By adjusting q once we determine m, we can guarantee that
* there is a complete four-digit quotient at &qspace[1] when
* we finally stop.
*/
for (m = 4 - n; u[1] == 0; u++)
m--;
for (i = 4 - m; --i >= 0;)
q[i] = 0;
q += 4 - m;
/*
* Here we run Program D, translated from MIX to C and acquiring
* a few minor changes.
*
* D1: choose multiplier 1 << d to ensure v[1] >= B/2.
*/
d = 0;
for (t = v[1]; t < B / 2; t <<= 1)
d++;
if (d > 0) {
shl(&u[0], m + n, d); /* u <<= d */
shl(&v[1], n - 1, d); /* v <<= d */
}
/*
* D2: j = 0.
*/
j = 0;
v1 = v[1]; /* for D3 -- note that v[1..n] are constant */
v2 = v[2]; /* for D3 */
do {
digit uj0, uj1, uj2;
/*
* D3: Calculate qhat (\^q, in TeX notation).
* Let qhat = min((u[j]*B + u[j+1])/v[1], B-1), and
* let rhat = (u[j]*B + u[j+1]) mod v[1].
* While rhat < B and v[2]*qhat > rhat*B+u[j+2],
* decrement qhat and increase rhat correspondingly.
* Note that if rhat >= B, v[2]*qhat < rhat*B.
*/
uj0 = u[j + 0]; /* for D3 only -- note that u[j+...] change */
uj1 = u[j + 1]; /* for D3 only */
uj2 = u[j + 2]; /* for D3 only */
if (uj0 == v1) {
qhat = B;
rhat = uj1;
goto qhat_too_big;
} else {
unsigned int nn = COMBINE(uj0, uj1);
qhat = nn / v1;
rhat = nn % v1;
}
while (v2 * qhat > COMBINE(rhat, uj2)) {
qhat_too_big:
qhat--;
if ((rhat += v1) >= B)
break;
}
/*
* D4: Multiply and subtract.
* The variable `t' holds any borrows across the loop.
* We split this up so that we do not require v[0] = 0,
* and to eliminate a final special case.
*/
for (t = 0, i = n; i > 0; i--) {
t = u[i + j] - v[i] * qhat - t;
u[i + j] = (digit)LHALF(t);
t = (B - HHALF(t)) & (B - 1);
}
t = u[j] - t;
u[j] = (digit)LHALF(t);
/*
* D5: test remainder.
* There is a borrow if and only if HHALF(t) is nonzero;
* in that (rare) case, qhat was too large (by exactly 1).
* Fix it by adding v[1..n] to u[j..j+n].
*/
if (HHALF(t)) {
qhat--;
for (t = 0, i = n; i > 0; i--) { /* D6: add back. */
t += u[i + j] + v[i];
u[i + j] = (digit)LHALF(t);
t = HHALF(t);
}
u[j] = (digit)LHALF(u[j] + t);
}
q[j] = (digit)qhat;
} while (++j <= m); /* D7: loop on j. */
/*
* If caller wants the remainder, we have to calculate it as
* u[m..m+n] >> d (this is at most n digits and thus fits in
* u[m+1..m+n], but we may need more source digits).
*/
if (arq) {
if (d) {
for (i = m + n; i > m; --i)
u[i] = (digit)(((unsigned int)u[i] >> d) |
LHALF((unsigned int)u[i - 1] <<
(HALF_BITS - d)));
u[i] = 0;
}
tmp.ui[H] = COMBINE(uspace[1], uspace[2]);
tmp.ui[L] = COMBINE(uspace[3], uspace[4]);
*arq = tmp.ll;
}
tmp.ui[H] = COMBINE(qspace[1], qspace[2]);
tmp.ui[L] = COMBINE(qspace[3], qspace[4]);
return (tmp.ll);
}
/*
* Shift p[0]..p[len] left `sh' bits, ignoring any bits that
* `fall out' the left (there never will be any such anyway).
* We may assume len >= 0. NOTE THAT THIS WRITES len+1 DIGITS.
*/
static void
shl(digit *p, int len, int sh)
{
int i;
for (i = 0; i < len; i++)
p[i] = (digit)(LHALF((unsigned int)p[i] << sh) |
((unsigned int)p[i + 1] >> (HALF_BITS - sh)));
p[i] = (digit)(LHALF((unsigned int)p[i] << sh));
}

View File

@ -0,0 +1,55 @@
/*-
* Copyright (c) 1992, 1993
* The Regents of the University of California. All rights reserved.
*
* This software was developed by the Computer Systems Engineering group
* at Lawrence Berkeley Laboratory under DARPA contract BG 91-66 and
* contributed to Berkeley.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* From:
* @(#)subdi3.c 8.1 (Berkeley) 6/4/93
* NetBSD: subdi3.c,v 1.1 2005/12/20 19:28:51 christos Exp
*/
#include "longlong.h"
/*
* Subtract two long long values. This is trivial since a one-bit
* carry from a single unsigned int difference x-y occurs if and only
* if (x-y) > x.
*/
long long
__subdi3(long long a, long long b)
{
union uu aa, bb, diff;
aa.ll = a;
bb.ll = b;
diff.ui[L] = aa.ui[L] - bb.ui[L];
diff.ui[H] = aa.ui[H] - bb.ui[H] - (diff.ui[L] > aa.ui[L]);
return (diff.ll);
}

View File

@ -0,0 +1,53 @@
/*-
* Copyright (c) 1992, 1993
* The Regents of the University of California. All rights reserved.
*
* This software was developed by the Computer Systems Engineering group
* at Lawrence Berkeley Laboratory under DARPA contract BG 91-66 and
* contributed to Berkeley.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* From:
* @(#)ucmpdi2.c 8.1 (Berkeley) 6/4/93
* NetBSD: ucmpdi2.c,v 1.1 2005/12/20 19:28:51 christos Exp
*/
#include "longlong.h"
/*
* Return 0, 1, or 2 as a <, =, > b respectively.
* Neither a nor b are considered signed.
*/
int
__ucmpdi2(unsigned long long a, unsigned long long b)
{
union uu aa, bb;
aa.ull = a;
bb.ull = b;
return (aa.ui[H] < bb.ui[H] ? 0 : aa.ui[H] > bb.ui[H] ? 2 :
aa.ui[L] < bb.ui[L] ? 0 : aa.ui[L] > bb.ui[L] ? 2 : 1);
}

View File

@ -0,0 +1,48 @@
/*-
* Copyright (c) 1992, 1993
* The Regents of the University of California. All rights reserved.
*
* This software was developed by the Computer Systems Engineering group
* at Lawrence Berkeley Laboratory under DARPA contract BG 91-66 and
* contributed to Berkeley.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* From:
* @(#)udivdi3.c 8.1 (Berkeley) 6/4/93
* NetBSD: udivdi3.c,v 1.1 2005/12/20 19:28:51 christos Exp
*/
#include "longlong.h"
/*
* Divide two unsigned long longs.
*/
unsigned long long
__udivdi3(unsigned long long a, unsigned long long b)
{
return __qdivrem(a, b, NULL);
}

View File

@ -0,0 +1,50 @@
/*-
* Copyright (c) 1992, 1993
* The Regents of the University of California. All rights reserved.
*
* This software was developed by the Computer Systems Engineering group
* at Lawrence Berkeley Laboratory under DARPA contract BG 91-66 and
* contributed to Berkeley.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* From:
* @(#)umoddi3.c 8.1 (Berkeley) 6/4/93
* NetBSD: umoddi3.c,v 1.1 2005/12/20 19:28:51 christos Exp
*/
#include "longlong.h"
/*
* Return remainder after dividing two unsigned long longs.
*/
unsigned long long
__umoddi3(unsigned long long a, unsigned long long b)
{
unsigned long long r;
(void)__qdivrem(a, b, &r);
return (r);
}

View File

@ -0,0 +1,53 @@
/*-
* Copyright (c) 1992, 1993
* The Regents of the University of California. All rights reserved.
*
* This software was developed by the Computer Systems Engineering group
* at Lawrence Berkeley Laboratory under DARPA contract BG 91-66 and
* contributed to Berkeley.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
* From:
* @(#)xordi3.c 8.1 (Berkeley) 6/4/93
* NetBSD: xordi3.c,v 1.1 2005/12/20 19:28:51 christos Exp
*/
#include "longlong.h"
/*
* Return a ^ b, in long long.
*/
long long
__xordi3(long long a, long long b)
{
union uu aa, bb;
aa.ll = a;
bb.ll = b;
aa.ui[0] ^= bb.ui[0];
aa.ui[1] ^= bb.ui[1];
return (aa.ll);
}

View File

@ -0,0 +1,104 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* setjmp and longjmp for MIPS.
*/
#include <kern/mips/regdefs.h>
.text
.set noreorder
/*
* int setjmp(jmp_buf jb);
*
* Save the current state so we can return again from the call later
* if/when longjmp is called. (If the function that called setjmp
* returns before longjmp is called, the results are undefined. We
* only need to save registers, not the whole contents of the stack.)
*/
.globl setjmp
.type setjmp,@function
.ent setjmp
setjmp:
/*
* jmp_buf is in a0. We need to save s0-s8, sp, and ra in it.
* Don't store more registers without adjusting machine/setjmp.h.
*/
sw sp, 0(a0) /* save registers */
sw ra, 4(a0)
sw s0, 8(a0)
sw s1, 12(a0)
sw s2, 16(a0)
sw s3, 20(a0)
sw s4, 24(a0)
sw s5, 28(a0)
sw s6, 32(a0)
sw s7, 36(a0)
sw s8, 40(a0)
j ra /* done */
li v0, 0 /* return 0 (in delay slot) */
.end setjmp
/*
* void longjmp(jmp_buf jb, int code);
*/
.globl longjmp
.type longjmp,@function
.ent longjmp
longjmp:
/*
* jmp_buf is in a0. Return code is in a1.
* We need to restore s0-s8, sp, and ra from the jmp_buf.
* The return code is forced to 1 if 0 is passed in.
*/
sltiu t0, a1, 1 /* set t0 to 1 if return code is 0... otherwise 0 */
addu a1, a1, t0 /* update the return code */
lw sp, 0(a0) /* restore registers */
lw ra, 4(a0)
lw s0, 8(a0)
lw s1, 12(a0)
lw s2, 16(a0)
lw s3, 20(a0)
lw s4, 24(a0)
lw s5, 28(a0)
lw s6, 32(a0)
lw s7, 36(a0)
lw s8, 40(a0)
j ra /* return, to where setjmp was called from */
move v0, a1 /* set return value */
.end longjmp

View File

@ -0,0 +1,592 @@
/*
* Copyright (c) 1997, 1998, 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* Guts of printf.
*
* This file is used in both libc and the kernel and needs to work in both
* contexts. This makes a few things a bit awkward.
*
* This is a slightly simplified version of the real-life printf
* originally used in the VINO kernel.
*/
#ifdef _KERNEL
#include <types.h>
#include <lib.h>
#define assert KASSERT
#else
#include <sys/types.h>
#include <assert.h>
#include <stdint.h>
#include <stdio.h>
#include <string.h>
#endif
#include <stdarg.h>
/*
* Do we want to support "long long" types with %lld?
*
* Using 64-bit types with gcc causes gcc to emit calls to functions
* like __moddi3 and __divdi3. These need to be provided at link time,
* which can be a hassle; this switch is provided to help avoid
* needing them.
*/
#define USE_LONGLONG
/*
* Define a type that holds the longest signed integer we intend to support.
*/
#ifdef USE_LONGLONG
#define INTTYPE long long
#else
#define INTTYPE long
#endif
/*
* Space for a long long in base 8, plus a NUL, plus one
* character extra for slop.
*
* CHAR_BIT is the number of bits in a char; thus sizeof(long long)*CHAR_BIT
* is the number of bits in a long long. Each octal digit prints 3 bits.
* Values printed in larger bases will be shorter strings.
*/
#define NUMBER_BUF_SIZE ((sizeof(INTTYPE) * CHAR_BIT) / 3 + 2)
/*
* Structure holding the state for printf.
*/
typedef struct {
/* Callback for sending printed string data */
void (*sendfunc)(void *clientdata, const char *str, size_t len);
void *clientdata;
/* The varargs argument pointer */
va_list ap;
/* Total count of characters printed */
int charcount;
/* Flag that's true if we are currently looking in a %-format */
int in_pct;
/* Size of the integer argument to retrieve */
enum {
INTSZ,
LONGSZ,
#ifdef USE_LONGLONG
LLONGSZ,
#endif
SIZETSZ,
} size;
/* The value of the integer argument retrieved */
unsigned INTTYPE num;
/* Sign of the integer argument (0 = positive; -1 = negative) */
int sign;
/* Field width (number of spaces) */
int spacing;
/* Flag: align to left in field instead of right */
int rightspc;
/* Character to pad to field size with (space or 0) */
int fillchar;
/* Number base to print the integer argument in (8, 10, 16) */
int base;
/* Flag: if set, print 0x before hex and 0 before octal numbers */
int baseprefix;
/* Flag: alternative output format selected with %#... */
int altformat;
} PF;
/*
* Send some text onward to the output.
*
* We count the total length we send out so we can return it from __vprintf,
* since that's what most printf-like functions want to return.
*/
static
void
__pf_print(PF *pf, const char *txt, size_t len)
{
pf->sendfunc(pf->clientdata, txt, len);
pf->charcount += len;
}
/*
* Reset the state for the next %-field.
*/
static
void
__pf_endfield(PF *pf)
{
pf->in_pct = 0;
pf->size = INTSZ;
pf->num = 0;
pf->sign = 0;
pf->spacing = 0;
pf->rightspc = 0;
pf->fillchar = ' ';
pf->base = 0;
pf->baseprefix = 0;
pf->altformat = 0;
}
/*
* Process modifier chars (between the % and the type specifier)
* # use "alternate display format"
* - left align in field instead of right align
* l value is long (ll = long long)
* z value is size_t
* 0-9 field width
* leading 0 pad with zeros instead of spaces
*/
static
void
__pf_modifier(PF *pf, int ch)
{
switch (ch) {
case '#':
pf->altformat = 1;
break;
case '-':
pf->rightspc = 1;
break;
case 'l':
if (pf->size==LONGSZ) {
#ifdef USE_LONGLONG
pf->size = LLONGSZ;
#endif
}
else {
pf->size = LONGSZ;
}
break;
case 'z':
pf->size = SIZETSZ;
break;
case '0':
if (pf->spacing>0) {
/*
* Already seen some digits; this is part of the
* field size.
*/
pf->spacing = pf->spacing*10;
}
else {
/*
* Leading zero; set the padding character to 0.
*/
pf->fillchar = '0';
}
break;
default:
/*
* Invalid characters should be filtered out by a
* higher-level function, so if this assert goes off
* it's our fault.
*/
assert(ch>'0' && ch<='9');
/*
* Got a digit; accumulate the field size.
*/
pf->spacing = pf->spacing*10 + (ch-'0');
break;
}
}
/*
* Retrieve a numeric argument from the argument list and store it
* in pf->num, according to the size recorded in pf->size and using
* the numeric type specified by ch.
*/
static
void
__pf_getnum(PF *pf, int ch)
{
if (ch=='p') {
/*
* Pointer.
*
* uintptr_t is a C99 standard type that's an unsigned
* integer the same size as a pointer.
*/
pf->num = (uintptr_t) va_arg(pf->ap, void *);
}
else if (ch=='d') {
/* signed integer */
INTTYPE signednum=0;
switch (pf->size) {
case INTSZ:
/* %d */
signednum = va_arg(pf->ap, int);
break;
case LONGSZ:
/* %ld */
signednum = va_arg(pf->ap, long);
break;
#ifdef USE_LONGLONG
case LLONGSZ:
/* %lld */
signednum = va_arg(pf->ap, long long);
break;
#endif
case SIZETSZ:
/* %zd */
signednum = va_arg(pf->ap, ssize_t);
break;
}
/*
* Check for negative numbers.
*/
if (signednum < 0) {
pf->sign = -1;
pf->num = -signednum;
}
else {
pf->num = signednum;
}
}
else {
/* unsigned integer */
switch (pf->size) {
case INTSZ:
/* %u (or %o, %x) */
pf->num = va_arg(pf->ap, unsigned int);
break;
case LONGSZ:
/* %lu (or %lo, %lx) */
pf->num = va_arg(pf->ap, unsigned long);
break;
#ifdef USE_LONGLONG
case LLONGSZ:
/* %llu, %llo, %llx */
pf->num = va_arg(pf->ap, unsigned long long);
break;
#endif
case SIZETSZ:
/* %zu, %zo, %zx */
pf->num = va_arg(pf->ap, size_t);
break;
}
}
}
/*
* Set the printing base based on the numeric type specified in ch.
* %o octal
* %d,%u decimal
* %x hex
* %p pointer (print as hex)
*
* If the "alternate format" was requested, or always for pointers,
* note to print the C prefix for the type.
*/
static
void
__pf_setbase(PF *pf, int ch)
{
switch (ch) {
case 'd':
case 'u':
pf->base = 10;
break;
case 'x':
case 'p':
pf->base = 16;
break;
case 'o':
pf->base = 8;
break;
}
if (pf->altformat || ch=='p') {
pf->baseprefix = 1;
}
}
/*
* Function to print "spc" instances of the fill character.
*/
static
void
__pf_fill(PF *pf, int spc)
{
char f = pf->fillchar;
int i;
for (i=0; i<spc; i++) {
__pf_print(pf, &f, 1);
}
}
/*
* General printing function. Prints the string "stuff".
* The two prefixes (in practice one is a type prefix, such as "0x",
* and the other is the sign) get printed *after* space padding but
* *before* zero padding, if padding is on the left.
*/
static
void
__pf_printstuff(PF *pf,
const char *prefix, const char *prefix2,
const char *stuff)
{
/* Total length to print. */
int len = strlen(prefix)+strlen(prefix2)+strlen(stuff);
/* Get field width and compute amount of padding in "spc". */
int spc = pf->spacing;
if (spc > len) {
spc -= len;
}
else {
spc = 0;
}
/* If padding on left and the fill char is not 0, pad first. */
if (spc > 0 && pf->rightspc==0 && pf->fillchar!='0') {
__pf_fill(pf, spc);
}
/* Print the prefixes. */
__pf_print(pf, prefix, strlen(prefix));
__pf_print(pf, prefix2, strlen(prefix2));
/* If padding on left and the fill char *is* 0, pad here. */
if (spc > 0 && pf->rightspc==0 && pf->fillchar=='0') {
__pf_fill(pf, spc);
}
/* Print the actual string. */
__pf_print(pf, stuff, strlen(stuff));
/* If padding on the right, pad afterwards. */
if (spc > 0 && pf->rightspc!=0) {
__pf_fill(pf, spc);
}
}
/*
* Function to convert a number to ascii and then print it.
*
* Works from right to left in a buffer of NUMBER_BUF_SIZE bytes.
* NUMBER_BUF_SIZE is set so that the longest number string we can
* generate (a long long printed in octal) will fit. See above.
*/
static
void
__pf_printnum(PF *pf)
{
/* Digits to print with. */
const char *const digits = "0123456789abcdef";
char buf[NUMBER_BUF_SIZE]; /* Accumulation buffer for string. */
char *x; /* Current pointer into buf. */
unsigned INTTYPE xnum; /* Current value to print. */
const char *bprefix; /* Base prefix (0, 0x, or nothing) */
const char *sprefix; /* Sign prefix (- or nothing) */
/* Start in the last slot of the buffer. */
x = buf+sizeof(buf)-1;
/* Insert null terminator. */
*x-- = 0;
/* Initialize value. */
xnum = pf->num;
/*
* Convert a single digit.
* Do this loop at least once - that way 0 prints as 0 and not "".
*/
do {
/*
* Get the digit character for the least significant
* part of xnum.
*/
*x = digits[xnum % pf->base];
/*
* Back up the pointer to point to the next space to the left.
*/
x--;
/*
* Drop the value of the digit we just printed from xnum.
*/
xnum = xnum / pf->base;
/*
* If xnum hits 0 there's no more number left.
*/
} while (xnum > 0);
/*
* x points to the *next* slot in the buffer to use.
* However, we're done printing the number. So it's pointing
* one slot *before* the start of the actual number text.
* So advance it by one so it actually points at the number.
*/
x++;
/*
* If a base prefix was requested, select it.
*/
if (pf->baseprefix && pf->base==16) {
bprefix = "0x";
}
else if (pf->baseprefix && pf->base==8) {
bprefix = "0";
}
else {
bprefix = "";
}
/*
* Choose the sign prefix.
*/
sprefix = pf->sign ? "-" : "";
/*
* Now actually print the string we just generated.
*/
__pf_printstuff(pf, sprefix, bprefix, x);
}
/*
* Process a single character out of the format string.
*/
static
void
__pf_send(PF *pf, int ch)
{
/* Cannot get NULs here. */
assert(ch!=0);
if (pf->in_pct==0 && ch!='%') {
/*
* Not currently in a format, and not a %. Just send
* the character on through.
*/
char c = ch;
__pf_print(pf, &c, 1);
}
else if (pf->in_pct==0) {
/*
* Not in a format, but got a %. Start a format.
*/
pf->in_pct = 1;
}
else if (strchr("#-lz0123456789", ch)) {
/*
* These are the modifier characters we recognize.
* (These are the characters between the % and the type.)
*/
__pf_modifier(pf, ch);
}
else if (strchr("doupx", ch)) {
/*
* Integer types.
* Fetch the number, set the base, print it, then
* reset for the next format.
*/
__pf_getnum(pf, ch);
__pf_setbase(pf, ch);
__pf_printnum(pf);
__pf_endfield(pf);
}
else if (ch=='s') {
/*
* Print a string.
*/
const char *str = va_arg(pf->ap, const char *);
if (str==NULL) {
str = "(null)";
}
__pf_printstuff(pf, "", "", str);
__pf_endfield(pf);
}
else {
/*
* %%, %c, or illegal character.
* Illegal characters are printed like %%.
* for example, %5k prints " k".
*/
char x[2];
if (ch=='c') {
x[0] = va_arg(pf->ap, int);
}
else {
x[0] = ch;
}
x[1] = 0;
__pf_printstuff(pf, "", "", x);
__pf_endfield(pf);
}
}
/*
* Do a whole printf session.
* Create and initialize a printf state object,
* then send it each character from the format string.
*/
int
__vprintf(void (*func)(void *clientdata, const char *str, size_t len),
void *clientdata, const char *format, va_list ap)
{
PF pf;
int i;
pf.sendfunc = func;
pf.clientdata = clientdata;
#ifdef va_copy
va_copy(pf.ap, ap);
#else
pf.ap = ap;
#endif
pf.charcount = 0;
__pf_endfield(&pf);
for (i=0; format[i]; i++) {
__pf_send(&pf, format[i]);
}
return pf.charcount;
}

View File

@ -0,0 +1,157 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* This file is shared between libc and the kernel, so don't put anything
* in here that won't work in both contexts.
*/
#ifdef _KERNEL
#include <types.h>
#include <lib.h>
#else
#include <stdio.h>
#endif /* _KERNEL */
#include <stdarg.h>
/*
* Standard C string/IO function: printf into a character buffer.
*/
/*
* Context structure for snprintf: buffer to print into, maximum
* length, and index of the next character to write.
*
* Note that while the length argument to snprintf includes space for
* a null terminator, SNP.buflen does not. This is to make something
* vaguely reasonable happen if a length of 0 is passed to snprintf.
*/
typedef struct {
char *buf;
size_t buflen;
size_t bufpos;
} SNP;
/*
* Send function for snprintf. This is the function handed to the
* printf guts. It gets called with mydata pointing to the context,
* and some string data of length LEN in DATA. DATA is not necessarily
* null-terminated.
*/
static
void
__snprintf_send(void *mydata, const char *data, size_t len)
{
SNP *snp = mydata;
unsigned i;
/* For each character we're sent... */
for (i=0; i<len; i++) {
/* If we aren't past the length, */
if (snp->bufpos < snp->buflen) {
/* store the character */
snp->buf[snp->bufpos] = data[i];
/* and increment the position. */
snp->bufpos++;
}
}
}
/*
* The va_list version of snprintf.
*/
int
vsnprintf(char *buf, size_t len, const char *fmt, va_list ap)
{
int chars;
SNP snp;
/*
* Fill in the context structure.
* We set snp.buflen to the number of characters that can be
* written (excluding the null terminator) so as not to have
* to special-case the possibility that we got passed a length
* of zero elsewhere.
*/
snp.buf = buf;
if (len==0) {
snp.buflen = 0;
}
else {
snp.buflen = len-1;
}
snp.bufpos = 0;
/* Call __vprintf to do the actual work. */
chars = __vprintf(__snprintf_send, &snp, fmt, ap);
/*
* Add a null terminator. If the length *we were passed* is greater
* than zero, we reserved a space in the buffer for the terminator,
* so this won't overflow. If the length we were passed is zero,
* nothing will have been or should be written anyway, and buf
* might even be NULL. (C99 explicitly endorses this possibility.)
*/
if (len > 0) {
buf[snp.bufpos] = 0;
}
/*
* Return the number of characters __vprintf processed.
* According to C99, snprintf should return this number, not
* the number of characters actually stored, and should not
* return -1 on overflow but only on other errors. (All none
* of them since we don't do multibyte characters...)
*/
return chars;
}
/*
* snprintf - hand off to vsnprintf.
*/
int
snprintf(char *buf, size_t len, const char *fmt, ...)
{
int chars;
va_list ap;
va_start(ap, fmt);
chars = vsnprintf(buf, len, fmt, ap);
va_end(ap);
return chars;
}

101
common/libc/stdlib/atoi.c Normal file
View File

@ -0,0 +1,101 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* This file is shared between libc and the kernel, so don't put anything
* in here that won't work in both contexts.
*/
#ifdef _KERNEL
#include <types.h>
#include <lib.h>
#else
#include <stdlib.h>
#include <string.h>
#endif
/*
* Standard C function: parse a string that represents a decimal integer.
* Leading whitespace is allowed. Trailing gunk is allowed too. Doesn't
* really report syntax errors or overflow in any useful way.
*/
int
atoi(const char *s)
{
static const char digits[] = "0123456789"; /* legal digits in order */
unsigned val=0; /* value we're accumulating */
int neg=0; /* set to true if we see a minus sign */
/* skip whitespace */
while (*s==' ' || *s=='\t') {
s++;
}
/* check for sign */
if (*s=='-') {
neg=1;
s++;
}
else if (*s=='+') {
s++;
}
/* process each digit */
while (*s) {
const char *where;
unsigned digit;
/* look for the digit in the list of digits */
where = strchr(digits, *s);
if (where==NULL) {
/* not found; not a digit, so stop */
break;
}
/* get the index into the digit list, which is the value */
digit = (where - digits);
/* could (should?) check for overflow here */
/* shift the number over and add in the new digit */
val = val*10 + digit;
/* look at the next character */
s++;
}
/* handle negative numbers */
if (neg) {
return -val;
}
/* done */
return val;
}

View File

@ -0,0 +1,76 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* This file is shared between libc and the kernel, so don't put anything
* in here that won't work in both contexts.
*/
#ifdef _KERNEL
#include <types.h>
#include <lib.h>
#else
#include <stdint.h>
#include <string.h>
#endif
/*
* Standard (well, semi-standard) C string function - zero a block of
* memory.
*/
void
bzero(void *vblock, size_t len)
{
char *block = vblock;
size_t i;
/*
* For performance, optimize the common case where the pointer
* and the length are word-aligned, and write word-at-a-time
* instead of byte-at-a-time. Otherwise, write bytes.
*
* The alignment logic here should be portable. We rely on the
* compiler to be reasonably intelligent about optimizing the
* divides and moduli out. Fortunately, it is.
*/
if ((uintptr_t)block % sizeof(long) == 0 &&
len % sizeof(long) == 0) {
long *lb = (long *)block;
for (i=0; i<len/sizeof(long); i++) {
lb[i] = 0;
}
}
else {
for (i=0; i<len; i++) {
block[i] = 0;
}
}
}

View File

@ -0,0 +1,86 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* This file is shared between libc and the kernel, so don't put anything
* in here that won't work in both contexts.
*/
#ifdef _KERNEL
#include <types.h>
#include <lib.h>
#else
#include <stdint.h>
#include <string.h>
#endif
/*
* C standard function - copy a block of memory.
*/
void *
memcpy(void *dst, const void *src, size_t len)
{
size_t i;
/*
* memcpy does not support overlapping buffers, so always do it
* forwards. (Don't change this without adjusting memmove.)
*
* For speedy copying, optimize the common case where both pointers
* and the length are word-aligned, and copy word-at-a-time instead
* of byte-at-a-time. Otherwise, copy by bytes.
*
* The alignment logic below should be portable. We rely on
* the compiler to be reasonably intelligent about optimizing
* the divides and modulos out. Fortunately, it is.
*/
if ((uintptr_t)dst % sizeof(long) == 0 &&
(uintptr_t)src % sizeof(long) == 0 &&
len % sizeof(long) == 0) {
long *d = dst;
const long *s = src;
for (i=0; i<len/sizeof(long); i++) {
d[i] = s[i];
}
}
else {
char *d = dst;
const char *s = src;
for (i=0; i<len; i++) {
d[i] = s[i];
}
}
return dst;
}

View File

@ -0,0 +1,117 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* This file is shared between libc and the kernel, so don't put anything
* in here that won't work in both contexts.
*/
#ifdef _KERNEL
#include <types.h>
#include <lib.h>
#else
#include <stdint.h>
#include <string.h>
#endif
/*
* C standard function - copy a block of memory, handling overlapping
* regions correctly.
*/
void *
memmove(void *dst, const void *src, size_t len)
{
size_t i;
/*
* If the buffers don't overlap, it doesn't matter what direction
* we copy in. If they do, it does, so just assume they always do.
* We don't concern ourselves with the possibility that the region
* to copy might roll over across the top of memory, because it's
* not going to happen.
*
* If the destination is above the source, we have to copy
* back to front to avoid overwriting the data we want to
* copy.
*
* dest: dddddddd
* src: ssssssss ^
* | ^ |___|
* |___|
*
* If the destination is below the source, we have to copy
* front to back.
*
* dest: dddddddd
* src: ^ ssssssss
* |___| ^ |
* |___|
*/
if ((uintptr_t)dst < (uintptr_t)src) {
/*
* As author/maintainer of libc, take advantage of the
* fact that we know memcpy copies forwards.
*/
return memcpy(dst, src, len);
}
/*
* Copy by words in the common case. Look in memcpy.c for more
* information.
*/
if ((uintptr_t)dst % sizeof(long) == 0 &&
(uintptr_t)src % sizeof(long) == 0 &&
len % sizeof(long) == 0) {
long *d = dst;
const long *s = src;
/*
* The reason we copy index i-1 and test i>0 is that
* i is unsigned -- so testing i>=0 doesn't work.
*/
for (i=len/sizeof(long); i>0; i--) {
d[i-1] = s[i-1];
}
}
else {
char *d = dst;
const char *s = src;
for (i=len; i>0; i--) {
d[i-1] = s[i-1];
}
}
return dst;
}

View File

@ -0,0 +1,52 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifdef _KERNEL
#include <types.h>
#include <lib.h>
#else
#include <string.h>
#endif
/*
* C standard function - initialize a block of memory
*/
void *
memset(void *ptr, int ch, size_t len)
{
char *p = ptr;
size_t i;
for (i=0; i<len; i++) {
p[i] = ch;
}
return ptr;
}

View File

@ -0,0 +1,54 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* This file is shared between libc and the kernel, so don't put anything
* in here that won't work in both contexts.
*/
#ifdef _KERNEL
#include <types.h>
#include <lib.h>
#else
#include <string.h>
#endif
/*
* Standard C string function: append one string to another.
*/
char *
strcat(char *dest, const char *src)
{
size_t offset;
offset = strlen(dest);
strcpy(dest+offset, src);
return dest;
}

View File

@ -0,0 +1,68 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* This file is shared between libc and the kernel, so don't put anything
* in here that won't work in both contexts.
*/
#ifdef _KERNEL
#include <types.h>
#include <lib.h>
#else
#include <string.h>
#endif
/*
* C standard string function: find leftmost instance of a character
* in a string.
*/
char *
strchr(const char *s, int ch_arg)
{
/* avoid sign-extension problems */
const char ch = ch_arg;
/* scan from left to right */
while (*s) {
/* if we hit it, return it */
if (*s == ch) {
return (char *)s;
}
s++;
}
/* if we were looking for the 0, return that */
if (*s == ch) {
return (char *)s;
}
/* didn't find it */
return NULL;
}

View File

@ -0,0 +1,90 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* This file is shared between libc and the kernel, so don't put anything
* in here that won't work in both contexts.
*/
#ifdef _KERNEL
#include <types.h>
#include <lib.h>
#else
#include <string.h>
#endif
/*
* Standard C string function: compare two strings and return their
* sort order.
*/
int
strcmp(const char *a, const char *b)
{
size_t i;
/*
* Walk down both strings until either they're different
* or we hit the end of A.
*
* If A and B strings are not the same length, when the
* shorter one ends, the two will be different, and we'll
* stop before running off the end of either.
*
* If they *are* the same length, it's sufficient to check
* that we haven't run off the end of A, because that's the
* same as checking to make sure we haven't run off the end of
* B.
*/
for (i=0; a[i]!=0 && a[i]==b[i]; i++) {
/* nothing */
}
/*
* If A is greater than B, return 1. If A is less than B,
* return -1. If they're the same, return 0. Since we have
* stopped at the first character of difference (or the end of
* both strings) checking the character under I accomplishes
* this.
*
* Note that strcmp does not handle accented characters,
* internationalization, or locale sort order; strcoll() does
* that.
*
* The rules say we compare order in terms of *unsigned* char.
*/
if ((unsigned char)a[i] > (unsigned char)b[i]) {
return 1;
}
else if (a[i] == b[i]) {
return 0;
}
return -1;
}

View File

@ -0,0 +1,63 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* This file is shared between libc and the kernel, so don't put anything
* in here that won't work in both contexts.
*/
#ifdef _KERNEL
#include <types.h>
#include <lib.h>
#else
#include <string.h>
#endif
/*
* Standard C string function: copy one string to another.
*/
char *
strcpy(char *dest, const char *src)
{
size_t i;
/*
* Copy characters until we hit the null terminator.
*/
for (i=0; src[i]; i++) {
dest[i] = src[i];
}
/*
* Add null terminator to result.
*/
dest[i] = 0;
return dest;
}

View File

@ -0,0 +1,55 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* This file is shared between libc and the kernel, so don't put anything
* in here that won't work in both contexts.
*/
#ifdef _KERNEL
#include <types.h>
#include <lib.h>
#else
#include <string.h>
#endif
/*
* C standard string function: get length of a string
*/
size_t
strlen(const char *str)
{
size_t ret = 0;
while (str[ret]) {
ret++;
}
return ret;
}

View File

@ -0,0 +1,69 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* This file is shared between libc and the kernel, so don't put anything
* in here that won't work in both contexts.
*/
#ifdef _KERNEL
#include <types.h>
#include <lib.h>
#else
#include <string.h>
#endif
/*
* C standard string function: find rightmost instance of a character
* in a string.
*/
char *
strrchr(const char *s, int ch_arg)
{
/* avoid sign-extension problems */
const char ch = ch_arg;
/* start one past the last character INCLUDING NULL TERMINATOR */
size_t i = strlen(s)+1;
/* go from right to left; stop at 0 */
while (i > 0) {
/* decrement first */
i--;
/* now check the character we're over */
if (s[i] == ch) {
return (char *)(s+i);
}
}
/* didn't find it */
return NULL;
}

View File

@ -0,0 +1,96 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* This file is shared between libc and the kernel, so don't put anything
* in here that won't work in both contexts.
*/
#ifdef _KERNEL
#include <types.h>
#include <lib.h>
#else
#include <string.h>
#endif
/*
* Standard C string function: tokenize a string splitting based on a
* list of separator characters. Reentrant version.
*
* The "context" argument should point to a "char *" that is preserved
* between calls to strtok_r that wish to operate on same string.
*/
char *
strtok_r(char *string, const char *seps, char **context)
{
char *head; /* start of word */
char *tail; /* end of word */
/* If we're starting up, initialize context */
if (string) {
*context = string;
}
/* Get potential start of this next word */
head = *context;
if (head == NULL) {
return NULL;
}
/* Skip any leading separators */
while (*head && strchr(seps, *head)) {
head++;
}
/* Did we hit the end? */
if (*head == 0) {
/* Nothing left */
*context = NULL;
return NULL;
}
/* skip over word */
tail = head;
while (*tail && !strchr(seps, *tail)) {
tail++;
}
/* Save head for next time in context */
if (*tail == 0) {
*context = NULL;
}
else {
*tail = 0;
tail++;
*context = tail;
}
/* Return current word */
return head;
}

171
configure vendored Executable file
View File

@ -0,0 +1,171 @@
#!/bin/sh
#
# Configure script for OS/161 tree.
# This generates the file "defs.mk" at the top level of the tree.
#
# Usage: ./configure [options]
# where you can get a list of the options by doing ./configure --help.
#
# Must be run with the top of the OS/161 tree as its current directory.
#
# Note: while this superficially acts like a GNU Autoconf configure
# script, it was not generated by autoconf. Scripts generated by
# autoconf are much harder to read. :-)
#
# If this script bombs out, you can create defs.mk by hand based on
# the comments in mk/os161.config.mk.
#
# Target hardware platform and machine type.
PLATFORM='sys161'
MACHINE='mips'
# Default optimize/debug flag: optimize.
DEBUG='-O2'
# Default location of the root of the installed system.
# Note that we quote it such that the reference to the home directory
# is a make variable, not a shell variable. This means it gets expanded
# when make runs rather than when this script runs.
OSTREE='$(HOME)/os161/root'
# Assume this
HOST_CC=gcc
##################################################
#
# Check to make sure we're in the right place.
if [ ! -d kern/main ]; then
echo 'Please run configure from the top of the OS/161 tree.'
exit 1
fi
#
# Process the command-line options.
while [ "x$1" != x ]; do
case "$1" in
--debug) DEBUG='-g';;
--ostree=*) OSTREE=`echo $1 | sed 's,^[^=]*=,,'`;;
--help|*)
more <<EOF
Usage: ./configure [options]
where the options are:
--help Print this message.
--debug Compile the user-level programs with debug info.
This is disabled by default because there's no
support for userlevel source debugging in OS/161.
(Note: debug info in the kernel is controlled by
the kernel config file.)
--ostree=PATH Install the compiled system in a directory tree
rooted at PATH. Default is \$HOME/os161/root.
EOF
exit
;;
esac
shift
done
# Check if the host system supports 4.4BSD <err.h>.
printf "Checking for <err.h>... "
cat > __conftest.c <<EOF
#include <err.h>
int
main()
{
err(0, "works");
return 1;
}
EOF
OK=0
if $HOST_CC __conftest.c -o __conftest >/dev/null 2>&1; then
if ./__conftest >/dev/null 2>&1; then
OK=1
fi
fi
rm -f __conf*
if [ $OK = 1 ]; then
echo 'yes'
else
echo 'no'
COMPAT_CFLAGS="${COMPATCFLAGS} -DNEED_ERR"
COMPAT_TARGETS="${HOSTTARGETS} install-errh"
fi
# Check if the host system has ntohll() and htonll().
printf "Checking for ntohll()..."
cat > __conftest.c <<EOF
#include <arpa/inet.h>
int
main()
{
int ok = ntohll(0xbeefbeefbeefbeefULL) != 0;
return !ok; /* exit(0) for success */
}
EOF
OK=0
if $HOST_CC __conftest.c -o __conftest >/dev/null 2>&1; then
if ./__conftest >/dev/null 2>&1; then
OK=1
fi
fi
rm -f __conf*
if [ $OK = 1 ]; then
echo 'yes'
else
echo 'no'
COMPAT_CFLAGS="${COMPATCFLAGS} -DNEED_NTOHLL"
HOST_CFLAGS="${HOST_CFLAGS} -DDECLARE_NTOHLL"
fi
####################
# Now generate defs.mk.
echo 'Generating defs.mk.'
(
# First, put an explanatory comment at the top.
cat <<EOF
# This file was generated by configure. Edits will disappear if you rerun
# configure. If you find that you need to edit this file to make things
# work, let the course staff know and we'll try to fix the configure script.
#
# The purpose of this file is to hold all the makefile definitions
# needed to adjust the OS/161 build process to any particular
# environment. If I've done it right, all you need to do is rerun the
# configure script and make clean if you start working on a different
# host OS. If I've done it mostly right, you may need to edit this
# file but you still hopefully won't need to edit any of the
# makefiles.
#
# The things that can be set here are documented in mk/os161.config.mk.
#
EOF
echo "OSTREE=${OSTREE}"
echo "PLATFORM=${PLATFORM}"
echo "MACHINE=${MACHINE}"
echo "COMPAT_CFLAGS=${COMPAT_CFLAGS}"
echo "COMPAT_TARGETS=${COMPAT_TARGETS}"
if [ "x$HOST_CFLAGS" != x ]; then
echo "HOST_CFLAGS+=$HOST_CFLAGS"
fi
) > defs.mk

120
design/assignments.txt Normal file
View File

@ -0,0 +1,120 @@
The (potential) OS/161 assignments
----------------------------------
OS/161 is used by a wide variety of courses at a wide variety of
schools, no two of which have the exact same set of assignments and
assignment requirements. The code base has been (to the extent
reasonably possible) structured to allow this and not assume any
particular structure or (particularly) numbering of assignments.
That said, in various places comments and documentation must (to be
helpful, at least) refer to particular assignments and things that are
(typically) done in particular assignments. These are written in
fairly general terms. This file is provided as an index for those
terms.
*** Always refer to the course materials provided by your ***
*** instructors when trying to figure out what functionality ***
*** you are and are not required to implement. ***
Note that the OS/161 code base you are given may include solutions for
some parts of the assignments described below, or even some whole
assignments.
Also note that the text below refers to assorted technical terms and
OS concepts without much or any explanation; you may not be familiar
with most of them at first and that's perfectly ok.
OS/161 is intended to support six basic assignments, most of which can
be divided into smaller pieces. These six assignments are:
- synchronization;
- basic system calls;
- virtual memory;
- basic file system functionality;
- file system recovery via journaling;
- some additional piece of OS functionality.
Synchronization.
This assignment has (potentially) three parts:
- Implement (sleep) locks and condition variables.
- Implement reader-writer locks.
- Solve some synchronization problems of the dining-philosophers
variety.
Basic system calls. (And processes.)
This assignment has (potentially) up to six parts:
- Implement file tables and open-file objects.
- Implement the basic system calls for files, normally:
- open()
- dup2()
- read()
- write()
- lseek()
- close()
- chdir()
- __getcwd()
- Implement processes, process IDs, and the basic process system
calls, normally:
- getpid()
- fork()
- _exit()
- waitpid()
- Implement the execv() system call.
- Implement a scheduler.
Virtual memory.
This assignment entails replacing a provided very simple virtual
memory system with a real one. This possibly includes providing the
sbrk() system call. It does not split into parts readily.
Basic file system functionality.
This assignment has (potentially) up to five parts:
- Add more system calls for file system operations, typically taken
from these:
- sync()
- mkdir()
- rmdir()
- remove()
- link()
- rename()
- getdirentry()
- fstat()
- fsync()
- ftruncate()
- flock()
although others may be chosen.
- Implement a buffer cache.
- Replace a biglock with fine-grained locking in the VFS layer
and/or the SFS file system.
- Add support for subdirectories to SFS.
- Implement cross-directory rename in SFS.
- Implement larger files in SFS.
File system recovery via journaling.
This assignment has (potentially) five parts:
- Implement an on-disk container for a file system journal.
- Instrument the buffer cache to support write-ahead journaling.
- Design a system of journal records suitable for recovering the
file system after a crash.
- Add code to SFS to issue these journal records.
- Implement code to read the on-disk journal and recover from a
crash.
Additional projects.
There is a wide variety of things that can be done to build on the
above assignments. None are listed here, because this file is not
the place for it.

55
design/shell.txt Normal file
View File

@ -0,0 +1,55 @@
SHELL DESIGN NOTES
------------------
The shell has few bells and whistles. It allows up to 128
backgrounded jobs (after this point you have to wait for some to exit,
because the table it uses to track these cannot be resized.)
The background jobs are tracked in an array of MAXBG pid_t's. If an
open slot is found, a background job's pid can be stashed there.
Background jobs can be collected using the "wait" built-in command,
which removes any pids whose exit status it collects from the
background jobs table.
The wait built-in command takes an optional argument, the process
id to wait for. The shell will attempt to wait for any process, not
just the ones it actually started as its own background jobs. However,
since no facility exists for looking up the pids of running processes,
this ability is not necessarily useful. If no argument is provided,
wait waits for all outstanding background jobs.
The shell uses WNOHANG if WNOHANG is defined, in which case
background jobs are polled after every command, like in Unix shells.
If WNOHANG is not defined, background jobs are polled only by user
request. In OS/161 2.0, WNOHANG is always defined in the kernel header
files, but the implementation is only suggested, not required. To make
the shell stop trying to use WNOHANG, patch it, or remove WNOHANG from
kern/wait.h.
There are two other built-in commands: chdir, which uses the chdir
system call to change directory, and can also be accessed as just cd,
and exit, which causes the shell to exit with a specified exit status
(0 if not supplied).
Note that all these built-in commands must be built into the shell
in order to work usefully.
The shell processes commands by reading lines and then splitting
them up into words using whitespace characters (space, tab, carriage
return, and newline) as separators. No punctuation characters are
interpreted, except for `&'. No variable substitution or argument
wildcard expansion ("globbing") is performed.
The `&' character, if present as the last word on a command line,
is treated as the "background" operator: the command is run as a
background job, that is, after starting it the shell immediately
prints another prompt and accepts more commands. Note that the `&'
must be preceded by whitespace to be recognized. The process id of the
background job is printed as it starts. Note that shell builtins
cannot be backgrounded; furthermore, because the OS/161 console does
not support job control, starting background jobs that perform
terminal input (or, to a lesser extent, terminal output) may produce
confusing and/or unwanted results.
The shell also supports the "sh -c COMMAND" syntax in the hopes
that it will be useful.

24
design/usermalloc.txt Normal file
View File

@ -0,0 +1,24 @@
User-level malloc
-----------------
The user-level malloc implementation is defined to be simple, not
fast or efficient. It uses a very basic first-fit block algorithm.
There's an 8-byte header which holds the offsets to the previous
and next blocks, a used/free bit, and some magic numbers (for
consistency checking) in the remaining available header bits. It also
allocates in units of 8 bytes to guarantee proper alignment of
doubles. (It also assumes its own headers are aligned on 8-byte
boundaries.)
On malloc(), it searches the entire heap starting at the beginning
for the first block big enough to hold the allocation. If it doesn't
find one, it calls sbrk() to get more memory. If it does find one, it
marks the block in use. It splits the remaining portion of the block
off as a new free block only if said portion is large enough to hold
both a header and some data.
On free(), it marks the block free and then tries to merge it with
the adjacent blocks (both above and below) if they're free.
That's about all there is to it.

17
kern/Makefile Normal file
View File

@ -0,0 +1,17 @@
#
# Toplevel makefile for the OS/161 kernel tree.
#
# Note: actual kernels are not compiled here; they are compiled in
# compile/FOO where FOO is a kernel configuration name.
#
# We don't actually do anything from here except install includes.
#
TOP=..
.include "$(TOP)/mk/os161.config.mk"
INCLUDES=\
include/kern include/kern \
arch/$(MACHINE)/include/kern include/kern/$(MACHINE)
.include "$(TOP)/mk/os161.includes.mk"

View File

@ -0,0 +1,79 @@
#
# The machine dependent sources for MIPS.
#
# Standard C functions
machine mips file ../common/libc/arch/mips/setjmp.S
# 64-bit integer ops support for gcc
machine mips file ../common/gcc-millicode/adddi3.c
machine mips file ../common/gcc-millicode/anddi3.c
machine mips file ../common/gcc-millicode/ashldi3.c
machine mips file ../common/gcc-millicode/ashrdi3.c
machine mips file ../common/gcc-millicode/cmpdi2.c
machine mips file ../common/gcc-millicode/divdi3.c
machine mips file ../common/gcc-millicode/iordi3.c
machine mips file ../common/gcc-millicode/lshldi3.c
machine mips file ../common/gcc-millicode/lshrdi3.c
machine mips file ../common/gcc-millicode/moddi3.c
machine mips file ../common/gcc-millicode/muldi3.c
machine mips file ../common/gcc-millicode/negdi2.c
machine mips file ../common/gcc-millicode/notdi2.c
machine mips file ../common/gcc-millicode/qdivrem.c
machine mips file ../common/gcc-millicode/subdi3.c
machine mips file ../common/gcc-millicode/ucmpdi2.c
machine mips file ../common/gcc-millicode/udivdi3.c
machine mips file ../common/gcc-millicode/umoddi3.c
machine mips file ../common/gcc-millicode/xordi3.c
#
# Low-level stuff ("locore")
# The platform should select cache handling and exception handling from
# among these:
#
# cache-mips1.S
# cache-mips161.S
# cache-mips32.S
#
# exception-mips1.S
# exception-mips32.S
#
machine mips file arch/mips/locore/trap.c # Common trap handler.
#
# Thread subsystem
#
machine mips file arch/mips/thread/cpu.c # CPU control.
machine mips file arch/mips/thread/switch.S # Thread context switch
machine mips file arch/mips/thread/switchframe.c # New thread prep
machine mips file arch/mips/thread/thread_machdep.c # MD thread code
machine mips file arch/mips/thread/threadstart.S # New thread startup
#
# VM system
# The platform should select TLB handling from among these:
#
# tlb-mips1.S
# tlb-mips161.S
# tlb-mips32.S
#
machine mips file arch/mips/vm/ram.c # Physical memory accounting
# This is included here rather than in conf.kern because
# it may not be suitable for all architectures.
machine mips file vm/copyinout.c # copyin/out et al.
# For the early assignments, we supply a very stupid MIPS-only skeleton
# of a VM system. It is just barely capable of running a single userlevel
# program as long as that program's not very large.
defoption dumbvm
machine mips optfile dumbvm arch/mips/vm/dumbvm.c
#
# System call layer
#
machine mips file arch/mips/syscall/syscall.c # System call handler

View File

@ -0,0 +1,98 @@
/*
* This is a pile of crap that tells the linker how to link the kernel,
* because it's too stupid to be able to work it out on its own.
*/
ENTRY(__start)
_DYNAMIC_LINK = 0;
SECTIONS
{
/*
* Base address for the kernel.
*/
. = 0x80000200;
/*
* Read-only loaded sections.
*/
/* code */
.text : { *(.text) }
/* linker-provided symbol for end of code */
_etext = .;
/* read-only data */
.rodata : { *(.rodata) *(.rodata.*) }
/* MIPS register-usage blather */
.reginfo : { *(.reginfo) }
/*
* Move to a fresh page. This method puts read-only and
* read-write material on separate pages without having to
* waste space on page-alignment in the on-disk file; the
* on-disk page that contains both text and data is mapped
* twice.
*
* For mips kernels we can't write-protect the text anyhow so
* there's no point doing it.
*/
/* . = . + 0x1000; */
/*
* Read-write loaded sections.
*/
/* initialized data */
.data : {
*(.data)
CONSTRUCTORS
}
/* Value for GP register */
_gp = ALIGN(16) + 0x7ff0;
/* Small data accessed via GP register */
.lit8 : { *(.lit8) }
.lit4 : { *(.lit4) }
.sdata : { *(.sdata) }
/* cleared-to-zero data */
.sbss : { *(.sbss *.scommon) }
.bss : { *(.bss) *(COMMON) }
/* linker-provided symbol for end of program */
_end = .;
/*
* Debug info
*/
/* stabs debug sections */
.stab 0: { *(.stab) }
.stabstr 0: { *(.stabstr) }
/* DWARF debug sections */
.debug 0: { *(.debug) }
.line 0: { *(.line) }
.debug_srcinfo 0: { *(.debug_srcinfo) }
.debug_sfnames 0: { *(.debug_sfnames) }
.debug_aranges 0: { *(.debug_aranges) }
.debug_pubnames 0: { *(.debug_pubnames) }
.debug_info 0: { *(.debug_info .gnu.linkonce.wi.*) }
.debug_abbrev 0: { *(.debug_abbrev) }
.debug_line 0: { *(.debug_line) }
.debug_frame 0: { *(.debug_frame) }
.debug_str 0: { *(.debug_str) }
.debug_loc 0: { *(.debug_loc) }
.debug_macinfo 0: { *(.debug_macinfo) }
.debug_weaknames 0: { *(.debug_weaknames) }
.debug_funcnames 0: { *(.debug_funcnames) }
.debug_typenames 0: { *(.debug_typenames) }
.debug_varnames 0: { *(.debug_varnames) }
/* These must appear regardless of . */
.gptab.sdata : { *(.gptab.data) *(.gptab.sdata) }
.gptab.sbss : { *(.gptab.bss) *(.gptab.sbss) }
}

View File

@ -0,0 +1,73 @@
/*
* Copyright (c) 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifndef _MIPS_CURRENT_H_
#define _MIPS_CURRENT_H_
/*
* Macro for current thread, or current cpu.
*
* This file should only be included via <current.h> (q.v.)
*
* On mips we track the current thread. There's an architectural
* issue that informs this choice: there's no easy way to find the
* current cpu, the current thread, or even the kernel stack of the
* current thread when entering the kernel at trap time. (On most CPUs
* there's a canonical way to find at least the stack.)
*
* Therefore we do the following:
*
* - We misuse a kernel-settable field of a nonessential MMU register
* to hold the CPU number.
*
* - On trap entry we use this number to index an array that gets us
* both the kernel stack and curthread.
*
* - We tell the compiler not to use the s7 register and keep
* curthread there.
*
* Note that if you want to change this scheme to use a different
* register, or change to a different scheme, you need to touch three
* places: here, the mips-specific kernel CFLAGS in the makefiles, and
* the trap entry and return code.
*/
#ifdef __GNUC__
register struct thread *curthread __asm("$23"); /* s7 register */
#else
#error "Don't know how to declare curthread in this compiler"
#endif
#undef __NEED_CURTHREAD
#define __NEED_CURCPU
/* For how we've defined it, curthread gets set first, then curcpu. */
#define INIT_CURCPU(cpu, thread) (curthread = (thread), curcpu = (cpu))
#endif /* _MIPS_CURRENT_H_ */

View File

@ -0,0 +1,58 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifndef _MIPS_ELF_H_
#define _MIPS_ELF_H_
/*
* MIPS machine-dependent definitions for the ELF binary format.
*/
/* The ELF executable type. */
#define EM_MACHINE EM_MIPS
/* Linker relocation codes. SIZE DESCRIPTION */
#define R_MIPS_NONE 0 /* --- nop */
#define R_MIPS_16 1 /* u16 value */
#define R_MIPS_32 2 /* u32 value */
#define R_MIPS_REL32 3 /* u32 value relative to patched address */
#define R_MIPS_26 4 /* u26 j/jal instruction address field */
#define R_MIPS_HI16 5 /* u16 %hi(sym) as below */
#define R_MIPS_LO16 6 /* s16 %lo(sym) as below */
#define R_MIPS_GPREL16 7 /* s16 offset from GP register */
#define R_MIPS_LITERAL 8 /* s16 GPREL16 for file-local symbols (?) */
#define R_MIPS_GOT16 9 /* u16 offset into global offset table */
#define R_MIPS_PC16 10 /* s16 PC-relative reference */
#define R_MIPS_CALL16 11 /* u16 call through global offset table */
#define R_MIPS_GPREL32 12 /* s32 offset from GP register */
/* %hi/%lo are defined so %hi(sym) << 16 + %lo(sym) = sym */
#endif /* _MIPS_ELF_H_ */

View File

@ -0,0 +1,44 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifndef _KERN_MIPS_ENDIAN_H_
#define _KERN_MIPS_ENDIAN_H_
/*
* Endianness. While the MIPS can be either big-endian (mipseb) or
* little-endian (mipsel), at least for now we only do mipseb.
*
* This file should only be included via <kern/endian.h> which in turn
* should be gotten via <endian.h> in the kernel or <arpa/inet.h> in
* userland.
*/
#define _BYTE_ORDER _BIG_ENDIAN
#endif /* _KERN_MIPS_ENDIAN_H_ */

View File

@ -0,0 +1,74 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* Macros for general-purpose register numbers for MIPS.
*
* Exported to userlevel because it's ~standard for that architecture.
*/
#ifndef _KERN_MIPS_REGDEFS_H_
#define _KERN_MIPS_REGDEFS_H_
#define z0 $0 /* always zero register */
#define AT $1 /* assembler temp register */
#define v0 $2 /* value 0 */
#define v1 $3 /* value 1 */
#define a0 $4 /* argument 0 */
#define a1 $5 /* argument 1 */
#define a2 $6 /* argument 2 */
#define a3 $7 /* argument 3 */
#define t0 $8 /* temporary (caller-save) 0 */
#define t1 $9 /* temporary (caller-save) 1 */
#define t2 $10 /* temporary (caller-save) 2 */
#define t3 $11 /* temporary (caller-save) 3 */
#define t4 $12 /* temporary (caller-save) 4 */
#define t5 $13 /* temporary (caller-save) 5 */
#define t6 $14 /* temporary (caller-save) 6 */
#define t7 $15 /* temporary (caller-save) 7 */
#define s0 $16 /* saved (callee-save) 0 */
#define s1 $17 /* saved (callee-save) 1 */
#define s2 $18 /* saved (callee-save) 2 */
#define s3 $19 /* saved (callee-save) 3 */
#define s4 $20 /* saved (callee-save) 4 */
#define s5 $21 /* saved (callee-save) 5 */
#define s6 $22 /* saved (callee-save) 6 */
#define s7 $23 /* saved (callee-save) 7 */
#define t8 $24 /* temporary (caller-save) 8 */
#define t9 $25 /* temporary (caller-save) 9 */
#define k0 $26 /* kernel temporary 0 */
#define k1 $27 /* kernel temporary 1 */
#define gp $28 /* global pointer */
#define sp $29 /* stack pointer */
#define s8 $30 /* saved (callee-save) 8 = frame pointer */
#define ra $31 /* return address */
#endif /* _KERN_MIPS_REGDEFS_H_ */

View File

@ -0,0 +1,47 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifndef _MIPS_SETJMP_H_
#define _MIPS_SETJMP_H_
/*
* MIPS jmp_buf definition.
*/
/*
* Must save: s0-s8, sp, ra (11 registers)
* Don't change __JB_REGS without adjusting mips_setjmp.S accordingly.
*/
#define __JB_REGS 11
/* A jmp_buf is an array of __JB_REGS registers */
typedef uint32_t jmp_buf[__JB_REGS];
#endif /* _MIPS_SETJMP_H_ */

View File

@ -0,0 +1,45 @@
/*
* Copyright (c) 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifndef _KERN_MIPS_SIGNAL_H_
#define _KERN_MIPS_SIGNAL_H_
/*
* Structure used to hold the register values for returning from a
* userland signal handler - basically the saved register values from
* whatever userlevel execution context the signal interrupted. Fill
* this in as needed, if you ever implement signal handlers. (Which you
* probably won't.)
*/
struct sigcontext {
/* Dummy. */
};
#endif /* _KERN_MIPS_SIGNAL_H_ */

View File

@ -0,0 +1,78 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifndef _KERN_MIPS_TYPES_H_
#define _KERN_MIPS_TYPES_H_
/*
* Machine-dependent types visible to userland.
* (Kernel-only types should go in mips/types.h.)
* 32-bit MIPS version.
*
* See kern/types.h for an explanation of the underscores.
*/
/* Sized integer types, with convenient short names */
typedef char __i8; /* 8-bit signed integer */
typedef short __i16; /* 16-bit signed integer */
typedef int __i32; /* 32-bit signed integer */
typedef long long __i64; /* 64-bit signed integer */
typedef unsigned char __u8; /* 8-bit unsigned integer */
typedef unsigned short __u16; /* 16-bit unsigned integer */
typedef unsigned int __u32; /* 32-bit unsigned integer */
typedef unsigned long long __u64; /* 64-bit unsigned integer */
/* Further standard C types */
typedef long __intptr_t; /* Signed pointer-sized integer */
typedef unsigned long __uintptr_t; /* Unsigned pointer-sized integer */
/*
* Since we're a 32-bit platform, size_t, ssize_t, and ptrdiff_t can
* correctly be either (unsigned) int or (unsigned) long. However, if we
* don't define it to the same one gcc is using, gcc will get
* upset. If you switch compilers and see otherwise unexplicable type
* errors involving size_t, try changing this.
*/
#if 1
typedef unsigned __size_t; /* Size of a memory region */
typedef int __ssize_t; /* Signed type of same size */
typedef int __ptrdiff_t; /* Difference of two pointers */
#else
typedef unsigned long __size_t; /* Size of a memory region */
typedef long __ssize_t; /* Signed type of same size */
typedef long __ptrdiff_t; /* Difference of two pointers */
#endif
/* Number of bits per byte. */
#define __CHAR_BIT 8
#endif /* _KERN_MIPS_TYPES_H_ */

View File

@ -0,0 +1,63 @@
/*
* Copyright (c) 2013
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifndef _MIPS_MEMBAR_H_
#define _MIPS_MEMBAR_H_
/*
* On the mips there's only one memory barrier instruction, so these
* are all the same. This is not true on many other CPUs (x86, arm,
* sparc, powerpc, etc.) We also mark the instruction as a compiler-
* level barrier by telling gcc that it destroys memory; this prevents
* gcc from reordering loads and stores around it.
*
* See include/membar.h for further information.
*/
MEMBAR_INLINE
void
membar_any_any(void)
{
__asm volatile(
".set push;" /* save assembler mode */
".set mips32;" /* allow MIPS32 instructions */
"sync;" /* do it */
".set pop" /* restore assembler mode */
: /* no outputs */
: /* no inputs */
: "memory"); /* "changes" memory */
}
MEMBAR_INLINE void membar_load_load(void) { membar_any_any(); }
MEMBAR_INLINE void membar_store_store(void) { membar_any_any(); }
MEMBAR_INLINE void membar_store_any(void) { membar_any_any(); }
MEMBAR_INLINE void membar_any_store(void) { membar_any_any(); }
#endif /* _MIPS_MEMBAR_H_ */

View File

@ -0,0 +1,117 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifndef _MIPS_SPECIALREG_H_
#define _MIPS_SPECIALREG_H_
/*
* Coprocessor 0 (system processor) register numbers
*/
#define c0_index $0 /* TLB entry index register */
#define c0_random $1 /* TLB random slot register */
#define c0_entrylo $2 /* TLB entry contents (low-order half) */
/* c0_entrylo0 $2 */ /* MIPS-II and up only */
/* c0_entrylo1 $3 */ /* MIPS-II and up only */
#define c0_context $4 /* some precomputed pagetable stuff */
/* c0_pagemask $5 */ /* MIPS-II and up only */
/* c0_wired $6 */ /* MIPS-II and up only */
#define c0_vaddr $8 /* virtual addr of failing memory access */
#define c0_count $9 /* cycle counter (MIPS-II and up) */
#define c0_entryhi $10 /* TLB entry contents (high-order half) */
#define c0_compare $11 /* on-chip timer control (MIPS-II and up) */
#define c0_status $12 /* processor status register */
#define c0_cause $13 /* exception cause register */
#define c0_epc $14 /* exception PC register */
#define c0_prid $15 /* processor ID register */
/* c0_config $16 */ /* MIPS-II and up only */
/* c0_lladdr $17 */ /* MIPS-II and up only */
/* c0_watchlo $18 */ /* MIPS-II and up only */
/* c0_watchhi $19 */ /* MIPS-II and up only */
/*
* Mode bits in c0_status
*/
#define CST_IEc 0x00000001 /* current: interrupt enable */
#define CST_KUc 0x00000002 /* current: user mode */
#define CST_IEp 0x00000004 /* previous: interrupt enable */
#define CST_KUp 0x00000008 /* previous: user mode */
#define CST_IEo 0x00000010 /* old: interrupt enable */
#define CST_KUo 0x00000020 /* old: user mode */
#define CST_MODEMASK 0x0000003f /* mask for the above */
#define CST_IRQMASK 0x0000ff00 /* mask for the individual irq enable bits */
#define CST_BEV 0x00400000 /* bootstrap exception vectors flag */
/*
* Fields of the c0_cause register
*/
#define CCA_UTLB 0x00000001 /* true if UTLB exception (set by our asm) */
#define CCA_CODE 0x0000003c /* EX_foo in trapframe.h */
#define CCA_IRQS 0x0000ff00 /* Currently pending interrupts */
#define CCA_COPN 0x30000000 /* Coprocessor number for EX_CPU */
#define CCA_JD 0x80000000 /* True if exception happened in jump delay */
#define CCA_CODESHIFT 2 /* shift for CCA_CODE field */
/*
* Fields of the c0_index register
*/
#define CIN_P 0x80000000 /* nonzero -> TLB probe found nothing */
#define CIN_INDEX 0x00003f00 /* 6-bit index into TLB */
#define CIN_INDEXSHIFT 8 /* shift for CIN_INDEX field */
/*
* Fields of the c0_context register
*
* The intent of c0_context is that you can manage virtually-mapped
* page tables in kseg2; then you load the base address of the current
* page table into c0_context. On a TLB miss the failing address is
* masked and shifted and appears in the VSHIFT field, and c0_context
* thereby contains the address of the page table entry you need to
* load into the TLB. This can be used to make TLB refill very fast.
*
* However, in OS/161 we use CTX_PTBASE to hold the current CPU
* number. This (or something like it) is fairly important to have and
* there's no other good place in the chip to put it. See discussions
* elsewhere.
*/
#define CTX_VSHIFT 0x001ffffc /* shifted/masked copy of c0_vaddr */
#define CTX_PTBASE 0xffe00000 /* page table base address */
#define CTX_PTBASESHIFT 21 /* shift for CTX_PBASE field */
/*
* Hardwired exception handler addresses.
*/
#define EXADDR_UTLB 0x80000000
#define EXADDR_GENERAL 0x80000080
#endif /* _MIPS_SPECIALREG_H_ */

View File

@ -0,0 +1,122 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifndef _MIPS_SPINLOCK_H_
#define _MIPS_SPINLOCK_H_
#include <cdefs.h>
/* Type of value needed to actually spin on */
typedef unsigned spinlock_data_t;
/* Initializer for use by SPINLOCK_INITIALIZER */
#define SPINLOCK_DATA_INITIALIZER 0
/* Atomic operations on spinlock_data_t */
SPINLOCK_INLINE
void spinlock_data_set(volatile spinlock_data_t *sd, unsigned val);
SPINLOCK_INLINE
spinlock_data_t spinlock_data_get(volatile spinlock_data_t *sd);
SPINLOCK_INLINE
spinlock_data_t spinlock_data_testandset(volatile spinlock_data_t *sd);
////////////////////////////////////////////////////////////
/*
* Assign a spinlock_data_t. On mips assigment of a plain 32-bit value
* is one instruction, and instructions are atomic with respect to
* memory.
*/
SPINLOCK_INLINE
void
spinlock_data_set(volatile spinlock_data_t *sd, unsigned val)
{
*sd = val;
}
/*
* Read a spinlock_data_t. On mips reading a plain 32-bit value is one
* instruction, and instructions are atomic with respect to memory.
*/
SPINLOCK_INLINE
spinlock_data_t
spinlock_data_get(volatile spinlock_data_t *sd)
{
return *sd;
}
/*
* Test-and-set a spinlock_data_t. Use the LL/SC instructions to
* make it atomic.
*
* LL (load linked) loads a machine word from memory, and marks the
* address. SC (store conditional) stores a machine word to memory,
* but succeeds only if the address is marked from a previous LL on
* the same processor. Stores from other processors clear that mark,
* as do traps on the current processor. Note that there may be no
* other memory accesses (besides instruction fetches) between the LL
* and the SC or the behavior is *undefined*. You can only use LL/SC
* to atomically update one machine word.
*/
SPINLOCK_INLINE
spinlock_data_t
spinlock_data_testandset(volatile spinlock_data_t *sd)
{
spinlock_data_t x;
spinlock_data_t y;
/*
* Test-and-set using LL/SC.
*
* Load the existing value into X, and use Y to store 1.
* After the SC, Y contains 1 if the store succeeded,
* 0 if it failed.
*
* On failure, return 1 to pretend that the spinlock
* was already held.
*/
y = 1;
__asm volatile(
".set push;" /* save assembler mode */
".set mips32;" /* allow MIPS32 instructions */
".set volatile;" /* avoid unwanted optimization */
"ll %0, 0(%2);" /* x = *sd */
"sc %1, 0(%2);" /* *sd = y; y = success? */
".set pop" /* restore assembler mode */
: "=&r" (x), "+r" (y) : "r" (sd));
if (y == 0) {
return 1;
}
return x;
}
#endif /* _MIPS_SPINLOCK_H_ */

View File

@ -0,0 +1,48 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifndef _MIPS_THREAD_H_
#define _MIPS_THREAD_H_
/*
* Machine-dependent thread bits.
*/
#include <setjmp.h>
typedef void (*badfaultfunc_t)(void);
struct thread_machdep {
badfaultfunc_t tm_badfaultfunc; /* fault hook used by copyin/out */
jmp_buf tm_copyjmp; /* longjmp area used by copyin/out */
};
#endif /* _MIPS_THREAD_H_ */

View File

@ -0,0 +1,105 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifndef _MIPS_TLB_H_
#define _MIPS_TLB_H_
/*
* MIPS-specific TLB access functions.
*
* tlb_random: write the TLB entry specified by ENTRYHI and ENTRYLO
* into a "random" TLB slot chosen by the processor.
*
* IMPORTANT NOTE: never write more than one TLB entry with the
* same virtual page field.
*
* tlb_write: same as tlb_random, but you choose the slot.
*
* tlb_read: read a TLB entry out of the TLB into ENTRYHI and ENTRYLO.
* INDEX specifies which one to get.
*
* tlb_probe: look for an entry matching the virtual page in ENTRYHI.
* Returns the index, or a negative number if no matching entry
* was found. ENTRYLO is not actually used, but must be set; 0
* should be passed.
*
* IMPORTANT NOTE: An entry may be matching even if the valid bit
* is not set. To completely invalidate the TLB, load it with
* translations for addresses in one of the unmapped address
* ranges - these will never be matched.
*/
void tlb_random(uint32_t entryhi, uint32_t entrylo);
void tlb_write(uint32_t entryhi, uint32_t entrylo, uint32_t index);
void tlb_read(uint32_t *entryhi, uint32_t *entrylo, uint32_t index);
int tlb_probe(uint32_t entryhi, uint32_t entrylo);
/*
* TLB entry fields.
*
* Note that the MIPS has support for a 6-bit address space ID. In the
* interests of simplicity, we don't use it. The fields related to it
* (TLBLO_GLOBAL and TLBHI_PID) can be left always zero, as can the
* bits that aren't assigned a meaning.
*
* The TLBLO_DIRTY bit is actually a write privilege bit - it is not
* ever set by the processor. If you set it, writes are permitted. If
* you don't set it, you'll get a "TLB Modify" exception when a write
* is attempted.
*
* There is probably no reason in the course of CS161 to use TLBLO_NOCACHE.
*/
/* Fields in the high-order word */
#define TLBHI_VPAGE 0xfffff000
/* TLBHI_PID 0x00000fc0 */
/* Fields in the low-order word */
#define TLBLO_PPAGE 0xfffff000
#define TLBLO_NOCACHE 0x00000800
#define TLBLO_DIRTY 0x00000400
#define TLBLO_VALID 0x00000200
/* TLBLO_GLOBAL 0x00000100 */
/*
* Values for completely invalid TLB entries. The TLB entry index should
* be passed to TLBHI_INVALID; this prevents loading the same invalid
* entry into multiple TLB slots.
*/
#define TLBHI_INVALID(entryno) ((0x80000+(entryno))<<12)
#define TLBLO_INVALID() (0)
/*
* Number of TLB entries in the processor.
*/
#define NUM_TLB 64
#endif /* _MIPS_TLB_H_ */

View File

@ -0,0 +1,110 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifndef _MIPS_TRAPFRAME_H_
#define _MIPS_TRAPFRAME_H_
/*
* Structure describing what is saved on the stack during entry to
* the exception handler.
*
* This must agree with the code in exception-*.S.
*/
struct trapframe {
uint32_t tf_vaddr; /* coprocessor 0 vaddr register */
uint32_t tf_status; /* coprocessor 0 status register */
uint32_t tf_cause; /* coprocessor 0 cause register */
uint32_t tf_lo;
uint32_t tf_hi;
uint32_t tf_ra; /* Saved register 31 */
uint32_t tf_at; /* Saved register 1 (AT) */
uint32_t tf_v0; /* Saved register 2 (v0) */
uint32_t tf_v1; /* etc. */
uint32_t tf_a0;
uint32_t tf_a1;
uint32_t tf_a2;
uint32_t tf_a3;
uint32_t tf_t0;
uint32_t tf_t1;
uint32_t tf_t2;
uint32_t tf_t3;
uint32_t tf_t4;
uint32_t tf_t5;
uint32_t tf_t6;
uint32_t tf_t7;
uint32_t tf_s0;
uint32_t tf_s1;
uint32_t tf_s2;
uint32_t tf_s3;
uint32_t tf_s4;
uint32_t tf_s5;
uint32_t tf_s6;
uint32_t tf_s7;
uint32_t tf_t8;
uint32_t tf_t9;
uint32_t tf_k0; /* dummy (see exception-mips1.S comments) */
uint32_t tf_k1; /* dummy */
uint32_t tf_gp;
uint32_t tf_sp;
uint32_t tf_s8;
uint32_t tf_epc; /* coprocessor 0 epc register */
};
/*
* MIPS exception codes.
*/
#define EX_IRQ 0 /* Interrupt */
#define EX_MOD 1 /* TLB Modify (write to read-only page) */
#define EX_TLBL 2 /* TLB miss on load */
#define EX_TLBS 3 /* TLB miss on store */
#define EX_ADEL 4 /* Address error on load */
#define EX_ADES 5 /* Address error on store */
#define EX_IBE 6 /* Bus error on instruction fetch */
#define EX_DBE 7 /* Bus error on data load *or* store */
#define EX_SYS 8 /* Syscall */
#define EX_BP 9 /* Breakpoint */
#define EX_RI 10 /* Reserved (illegal) instruction */
#define EX_CPU 11 /* Coprocessor unusable */
#define EX_OVF 12 /* Arithmetic overflow */
/*
* Function to enter user mode. Does not return. The trapframe must
* be on the thread's own stack or bad things will happen.
*/
__DEAD void mips_usermode(struct trapframe *tf);
/*
* Arrays used to load the kernel stack and curthread on trap entry.
*/
extern vaddr_t cpustacks[];
extern vaddr_t cputhreads[];
#endif /* _MIPS_TRAPFRAME_H_ */

View File

@ -0,0 +1,46 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifndef _MIPS_TYPES_H_
#define _MIPS_TYPES_H_
/*
* Machine-dependent types that are *not* made visible to userland.
* Those that are made visible are found in kern/machine/types.h.
* 32-bit MIPS version.
*
* (Use the underscore versions of the base type names because this
* file is included by types.h before the non-underscore versions are
* defined.)
*/
typedef __u32 paddr_t;
typedef __u32 vaddr_t;
#endif /* _MIPS_TYPES_H_ */

129
kern/arch/mips/include/vm.h Normal file
View File

@ -0,0 +1,129 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifndef _MIPS_VM_H_
#define _MIPS_VM_H_
/*
* Machine-dependent VM system definitions.
*/
#define PAGE_SIZE 4096 /* size of VM page */
#define PAGE_FRAME 0xfffff000 /* mask for getting page number from addr */
/*
* MIPS-I hardwired memory layout:
* 0xc0000000 - 0xffffffff kseg2 (kernel, tlb-mapped)
* 0xa0000000 - 0xbfffffff kseg1 (kernel, unmapped, uncached)
* 0x80000000 - 0x9fffffff kseg0 (kernel, unmapped, cached)
* 0x00000000 - 0x7fffffff kuseg (user, tlb-mapped)
*
* (mips32 is a little different)
*/
#define MIPS_KUSEG 0x00000000
#define MIPS_KSEG0 0x80000000
#define MIPS_KSEG1 0xa0000000
#define MIPS_KSEG2 0xc0000000
/*
* The first 512 megs of physical space can be addressed in both kseg0 and
* kseg1. We use kseg0 for the kernel. This macro returns the kernel virtual
* address of a given physical address within that range. (We assume we're
* not using systems with more physical space than that anyway.)
*
* N.B. If you, say, call a function that returns a paddr or 0 on error,
* check the paddr for being 0 *before* you use this macro. While paddr 0
* is not legal for memory allocation or memory management (it holds
* exception handler code) when converted to a vaddr it's *not* NULL, *is*
* a valid address, and will make a *huge* mess if you scribble on it.
*/
#define PADDR_TO_KVADDR(paddr) ((paddr)+MIPS_KSEG0)
/*
* The top of user space. (Actually, the address immediately above the
* last valid user address.)
*/
#define USERSPACETOP MIPS_KSEG0
/*
* The starting value for the stack pointer at user level. Because
* the stack is subtract-then-store, this can start as the next
* address after the stack area.
*
* We put the stack at the very top of user virtual memory because it
* grows downwards.
*/
#define USERSTACK USERSPACETOP
/*
* Interface to the low-level module that looks after the amount of
* physical memory we have.
*
* ram_getsize returns one past the highest valid physical
* address. (This value is page-aligned.) The extant RAM ranges from
* physical address 0 up to but not including this address.
*
* ram_getfirstfree returns the lowest valid physical address. (It is
* also page-aligned.) Memory at this address and above is available
* for use during operation, and excludes the space the kernel is
* loaded into and memory that is grabbed in the very early stages of
* bootup. Memory below this address is already in use and should be
* reserved or otherwise not managed by the VM system. It should be
* called exactly once when the VM system initializes to take over
* management of physical memory.
*
* ram_stealmem can be used before ram_getsize is called to allocate
* memory that cannot be freed later. This is intended for use early
* in bootup before VM initialization is complete.
*/
void ram_bootstrap(void);
paddr_t ram_stealmem(unsigned long npages);
paddr_t ram_getsize(void);
paddr_t ram_getfirstfree(void);
/*
* TLB shootdown bits.
*
* We'll take up to 16 invalidations before just flushing the whole TLB.
*/
struct tlbshootdown {
/*
* Change this to what you need for your VM design.
*/
int ts_placeholder;
};
#define TLBSHOOTDOWN_MAX 16
#endif /* _MIPS_VM_H_ */

View File

@ -0,0 +1,49 @@
/*
* Copyright (c) 2001, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#include <kern/mips/regdefs.h>
/*
* Cache flushing code for the System/161 MIPS variant, which
* (for now at least) has magically coherent caches. Almost all
* real MIPS processors require explicit cache control of one
* form or another; it can be quite a nuisance. (It is particularly
* nasty on the MIPS-1, that is, r2000/r3000.)
*/
.text
.set noreorder
.globl mips_flushicache
.type mips_flushicache,@function
.ent mips_flushicache
mips_flushicache:
j ra
nop
.end mips_flushicache

View File

@ -0,0 +1,355 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#include <kern/mips/regdefs.h>
#include <mips/specialreg.h>
/*
* Entry points for exceptions.
*
* MIPS-1 (r2000/r3000) style exception handling, with the "rfe"
* instruction rather than "eret", and the three sets of status bits.
*/
/*
* Do not allow the assembler to use $1 (at), because we need to be
* able to save it.
*/
.set noat
.set noreorder
/*
* UTLB exception handler.
*
* This code is copied to address 0x80000000, where the MIPS processor
* automatically invokes it.
*
* To avoid colliding with the other exception code, it must not
* exceed 128 bytes (32 instructions).
*
* This is the special entry point for the fast-path TLB refill for
* faults in the user address space. We don't implement fast-path TLB
* refill by default. Note that if you do, you either need to make
* sure the refill code doesn't fault or write extra code in
* common_exception to tidy up after such faults.
*/
.text
.globl mips_utlb_handler
.type mips_utlb_handler,@function
.ent mips_utlb_handler
mips_utlb_handler:
j common_exception /* Don't need to do anything special */
nop /* Delay slot */
.globl mips_utlb_end
mips_utlb_end:
.end mips_utlb_handler
/*
* General exception handler.
*
* This code is copied to address 0x80000080, where
* the MIPS processor automatically invokes it.
*/
.text
.globl mips_general_handler
.type mips_general_handler,@function
.ent mips_general_handler
mips_general_handler:
j common_exception /* Don't need to do anything special */
nop /* Delay slot */
.globl mips_general_end
mips_general_end:
.end mips_general_handler
/* This keeps gdb from conflating common_exception and mips_general_end */
nop /* padding */
/*
* Shared exception code for both handlers.
*/
.text
.type common_exception,@function
.ent common_exception
common_exception:
mfc0 k0, c0_status /* Get status register */
andi k0, k0, CST_KUp /* Check the we-were-in-user-mode bit */
beq k0, $0, 1f /* If clear, from kernel, already have stack */
nop /* delay slot */
/* Coming from user mode - find kernel stack */
mfc0 k1, c0_context /* we keep the CPU number here */
srl k1, k1, CTX_PTBASESHIFT /* shift it to get just the CPU number */
sll k1, k1, 2 /* shift it back to make an array index */
lui k0, %hi(cpustacks) /* get base address of cpustacks[] */
addu k0, k0, k1 /* index it */
move k1, sp /* Save previous stack pointer in k1 */
b 2f /* Skip to common code */
lw sp, %lo(cpustacks)(k0) /* Load kernel stack pointer (in delay slot) */
1:
/* Coming from kernel mode - just save previous stuff */
move k1, sp /* Save previous stack in k1 (delay slot) */
2:
/*
* At this point:
* Interrupts are off. (The processor did this for us.)
* k0 contains the value for curthread, to go into s7.
* k1 contains the old stack pointer.
* sp points into the kernel stack.
* All other registers are untouched.
*/
/*
* Allocate stack space for 37 words to hold the trap frame,
* plus four more words for a minimal argument block, plus
* one more for proper (64-bit) stack alignment.
*/
addi sp, sp, -168
/*
* Save general registers.
* We exclude k0/k1, which the kernel is free to clobber (and which
* we already have clobbered), and $0, whose value is fixed.
*
* The order here must match mips/include/trapframe.h.
*
* gdb disassembles this code to try to figure out what registers
* are where, and it isn't very bright. So in order to make gdb be
* able to trace the stack back through here, we play some silly
* games.
*
* In particular:
* (1) We store the return address register into the epc slot,
* which makes gdb think it's the return address slot. Then
* we store the real epc value over that.
* (2) We store the current sp into the sp slot, which makes gdb
* think it's the stack pointer slot. Then we store the real
* value.
* (3) gdb also assumes that saved registers in a function are
* saved in order. This is why we put epc where it is, and
* handle the real value of ra afterwards.
* (4) Because gdb will think we're saving k0 and k1, we need to
* leave slots for them in the trap frame, even though the
* stuff we save there is useless.
*
* This logic has not been tested against a recent gdb and has
* probably bitrotted. Someone(TM) should figure out what gdb
* currently expects -- or maybe even patch gdb to understand a
* better form of this that doesn't waste so many cycles.
*/
sw ra, 160(sp) /* dummy for gdb */
sw s8, 156(sp) /* save s8 */
sw sp, 152(sp) /* dummy for gdb */
sw gp, 148(sp) /* save gp */
sw k1, 144(sp) /* dummy for gdb */
sw k0, 140(sp) /* dummy for gdb */
sw k1, 152(sp) /* real saved sp */
nop /* delay slot for store */
mfc0 k1, c0_epc /* Copr.0 reg 13 == PC for exception */
sw k1, 160(sp) /* real saved PC */
sw t9, 136(sp)
sw t8, 132(sp)
sw s7, 128(sp)
sw s6, 124(sp)
sw s5, 120(sp)
sw s4, 116(sp)
sw s3, 112(sp)
sw s2, 108(sp)
sw s1, 104(sp)
sw s0, 100(sp)
sw t7, 96(sp)
sw t6, 92(sp)
sw t5, 88(sp)
sw t4, 84(sp)
sw t3, 80(sp)
sw t2, 76(sp)
sw t1, 72(sp)
sw t0, 68(sp)
sw a3, 64(sp)
sw a2, 60(sp)
sw a1, 56(sp)
sw a0, 52(sp)
sw v1, 48(sp)
sw v0, 44(sp)
sw AT, 40(sp)
sw ra, 36(sp)
/*
* Save special registers.
*/
mfhi t0
mflo t1
sw t0, 32(sp)
sw t1, 28(sp)
/*
* Save remaining exception context information.
*/
mfc0 t2, c0_status /* Copr.0 reg 11 == status */
sw t2, 20(sp)
mfc0 t3, c0_vaddr /* Copr.0 reg 8 == faulting vaddr */
sw t3, 16(sp)
mfc0 t4, c0_cause
sw t4, 24(sp) /* Copr.0 reg 13 == exception cause */
/*
* Pretend to save $0 for gdb's benefit.
*/
sw $0, 12(sp)
/*
* Load the curthread register if coming from user mode.
*/
andi k0, t2, CST_KUp /* Check the we-were-in-user-mode bit */
beq k0, $0, 3f /* If clear, were in kernel, skip ahead */
nop /* delay slot */
mfc0 k1, c0_context /* we keep the CPU number here */
srl k1, k1, CTX_PTBASESHIFT /* shift it to get just the CPU number */
sll k1, k1, 2 /* shift it back to make an array index */
lui k0, %hi(cputhreads) /* get base address of cputhreads[] */
addu k0, k0, k1 /* index it */
lw s7, %lo(cputhreads)(k0) /* Load curthread value */
3:
/*
* Load the kernel GP value.
*/
la gp, _gp
/*
* Prepare to call mips_trap(struct trapframe *)
*/
addiu a0, sp, 16 /* set argument - pointer to the trapframe */
jal mips_trap /* call it */
nop /* delay slot */
/* Something must be here or gdb doesn't find the stack frame. */
nop
/*
* Now restore stuff and return from the exception.
* Interrupts should be off.
*/
exception_return:
/* 16(sp) no need to restore tf_vaddr */
lw t0, 20(sp) /* load status register value into t0 */
nop /* load delay slot */
mtc0 t0, c0_status /* store it back to coprocessor 0 */
/* 24(sp) no need to restore tf_cause */
/* restore special registers */
lw t1, 28(sp)
lw t0, 32(sp)
mtlo t1
mthi t0
/* load the general registers */
lw ra, 36(sp)
lw AT, 40(sp)
lw v0, 44(sp)
lw v1, 48(sp)
lw a0, 52(sp)
lw a1, 56(sp)
lw a2, 60(sp)
lw a3, 64(sp)
lw t0, 68(sp)
lw t1, 72(sp)
lw t2, 76(sp)
lw t3, 80(sp)
lw t4, 84(sp)
lw t5, 88(sp)
lw t6, 92(sp)
lw t7, 96(sp)
lw s0, 100(sp)
lw s1, 104(sp)
lw s2, 108(sp)
lw s3, 112(sp)
lw s4, 116(sp)
lw s5, 120(sp)
lw s6, 124(sp)
lw s7, 128(sp)
lw t8, 132(sp)
lw t9, 136(sp)
/* 140(sp) "saved" k0 was dummy garbage anyway */
/* 144(sp) "saved" k1 was dummy garbage anyway */
lw gp, 148(sp) /* restore gp */
/* 152(sp) stack pointer - below */
lw s8, 156(sp) /* restore s8 */
lw k0, 160(sp) /* fetch exception return PC into k0 */
lw sp, 152(sp) /* fetch saved sp (must be last) */
/* done */
jr k0 /* jump back */
rfe /* in delay slot */
.end common_exception
/*
* Code to enter user mode for the first time.
* Does not return.
*
* This is called from mips_usermode().
* Interrupts on this processor should be off.
*/
.text
.globl asm_usermode
.type asm_usermode,@function
.ent asm_usermode
asm_usermode:
/*
* a0 is the address of a trapframe to use for exception "return".
* It's allocated on our stack.
*
* Move it to the stack pointer - we don't need the actual stack
* position any more. (When we come back from usermode, cpustacks[]
* will be used to reinitialize our stack pointer, and that was
* set by mips_usermode.)
*
* Then just jump to the exception return code above.
*/
j exception_return
addiu sp, a0, -16 /* in delay slot */
.end asm_usermode

View File

@ -0,0 +1,438 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#include <types.h>
#include <signal.h>
#include <lib.h>
#include <mips/specialreg.h>
#include <mips/trapframe.h>
#include <cpu.h>
#include <spl.h>
#include <thread.h>
#include <current.h>
#include <vm.h>
#include <mainbus.h>
#include <syscall.h>
/* in exception-*.S */
extern __DEAD void asm_usermode(struct trapframe *tf);
/* called only from assembler, so not declared in a header */
void mips_trap(struct trapframe *tf);
/* Names for trap codes */
#define NTRAPCODES 13
static const char *const trapcodenames[NTRAPCODES] = {
"Interrupt",
"TLB modify trap",
"TLB miss on load",
"TLB miss on store",
"Address error on load",
"Address error on store",
"Bus error on code",
"Bus error on data",
"System call",
"Break instruction",
"Illegal instruction",
"Coprocessor unusable",
"Arithmetic overflow",
};
/*
* Function called when user-level code hits a fatal fault.
*/
static
void
kill_curthread(vaddr_t epc, unsigned code, vaddr_t vaddr)
{
int sig = 0;
KASSERT(code < NTRAPCODES);
switch (code) {
case EX_IRQ:
case EX_IBE:
case EX_DBE:
case EX_SYS:
/* should not be seen */
KASSERT(0);
sig = SIGABRT;
break;
case EX_MOD:
case EX_TLBL:
case EX_TLBS:
sig = SIGSEGV;
break;
case EX_ADEL:
case EX_ADES:
sig = SIGBUS;
break;
case EX_BP:
sig = SIGTRAP;
break;
case EX_RI:
sig = SIGILL;
break;
case EX_CPU:
sig = SIGSEGV;
break;
case EX_OVF:
sig = SIGFPE;
break;
}
/*
* You will probably want to change this.
*/
kprintf("Fatal user mode trap %u sig %d (%s, epc 0x%x, vaddr 0x%x)\n",
code, sig, trapcodenames[code], epc, vaddr);
panic("I don't know how to handle this\n");
}
/*
* General trap (exception) handling function for mips.
* This is called by the assembly-language exception handler once
* the trapframe has been set up.
*/
void
mips_trap(struct trapframe *tf)
{
uint32_t code;
/*bool isutlb; -- not used */
bool iskern;
int spl;
/* The trap frame is supposed to be 37 registers long. */
KASSERT(sizeof(struct trapframe)==(37*4));
/*
* Extract the exception code info from the register fields.
*/
code = (tf->tf_cause & CCA_CODE) >> CCA_CODESHIFT;
/*isutlb = (tf->tf_cause & CCA_UTLB) != 0;*/
iskern = (tf->tf_status & CST_KUp) == 0;
KASSERT(code < NTRAPCODES);
/* Make sure we haven't run off our stack */
if (curthread != NULL && curthread->t_stack != NULL) {
KASSERT((vaddr_t)tf > (vaddr_t)curthread->t_stack);
KASSERT((vaddr_t)tf < (vaddr_t)(curthread->t_stack
+ STACK_SIZE));
}
/* Interrupt? Call the interrupt handler and return. */
if (code == EX_IRQ) {
int old_in;
bool doadjust;
old_in = curthread->t_in_interrupt;
curthread->t_in_interrupt = 1;
/*
* The processor has turned interrupts off; if the
* currently recorded interrupt state is interrupts on
* (spl of 0), adjust the recorded state to match, and
* restore after processing the interrupt.
*
* How can we get an interrupt if the recorded state
* is interrupts off? Well, as things currently stand
* when the CPU finishes idling it flips interrupts on
* and off to allow things to happen, but leaves
* curspl high while doing so.
*
* While we're here, assert that the interrupt
* handling code hasn't leaked a spinlock or an
* splhigh().
*/
if (curthread->t_curspl == 0) {
KASSERT(curthread->t_curspl == 0);
KASSERT(curthread->t_iplhigh_count == 0);
curthread->t_curspl = IPL_HIGH;
curthread->t_iplhigh_count++;
doadjust = true;
}
else {
doadjust = false;
}
mainbus_interrupt(tf);
if (doadjust) {
KASSERT(curthread->t_curspl == IPL_HIGH);
KASSERT(curthread->t_iplhigh_count == 1);
curthread->t_iplhigh_count--;
curthread->t_curspl = 0;
}
curthread->t_in_interrupt = old_in;
goto done2;
}
/*
* The processor turned interrupts off when it took the trap.
*
* While we're in the kernel, and not actually handling an
* interrupt, restore the interrupt state to where it was in
* the previous context, which may be low (interrupts on).
*
* Do this by forcing splhigh(), which may do a redundant
* cpu_irqoff() but forces the stored MI interrupt state into
* sync, then restoring the previous state.
*/
spl = splhigh();
splx(spl);
/* Syscall? Call the syscall handler and return. */
if (code == EX_SYS) {
/* Interrupts should have been on while in user mode. */
KASSERT(curthread->t_curspl == 0);
KASSERT(curthread->t_iplhigh_count == 0);
DEBUG(DB_SYSCALL, "syscall: #%d, args %x %x %x %x\n",
tf->tf_v0, tf->tf_a0, tf->tf_a1, tf->tf_a2, tf->tf_a3);
syscall(tf);
goto done;
}
/*
* Ok, it wasn't any of the really easy cases.
* Call vm_fault on the TLB exceptions.
* Panic on the bus error exceptions.
*/
switch (code) {
case EX_MOD:
if (vm_fault(VM_FAULT_READONLY, tf->tf_vaddr)==0) {
goto done;
}
break;
case EX_TLBL:
if (vm_fault(VM_FAULT_READ, tf->tf_vaddr)==0) {
goto done;
}
break;
case EX_TLBS:
if (vm_fault(VM_FAULT_WRITE, tf->tf_vaddr)==0) {
goto done;
}
break;
case EX_IBE:
case EX_DBE:
/*
* This means you loaded invalid TLB entries, or
* touched invalid parts of the direct-mapped
* segments. These are serious kernel errors, so
* panic.
*
* The MIPS won't even tell you what invalid address
* caused the bus error.
*/
panic("Bus error exception, PC=0x%x\n", tf->tf_epc);
break;
}
/*
* If we get to this point, it's a fatal fault - either it's
* one of the other exceptions, like illegal instruction, or
* it was a page fault we couldn't handle.
*/
if (!iskern) {
/*
* Fatal fault in user mode.
* Kill the current user process.
*/
kill_curthread(tf->tf_epc, code, tf->tf_vaddr);
goto done;
}
/*
* Fatal fault in kernel mode.
*
* If pcb_badfaultfunc is set, we do not panic; badfaultfunc is
* set by copyin/copyout and related functions to signify that
* the addresses they're accessing are userlevel-supplied and
* not trustable. What we actually want to do is resume
* execution at the function pointed to by badfaultfunc. That's
* going to be "copyfail" (see copyinout.c), which longjmps
* back to copyin/copyout or wherever and returns EFAULT.
*
* Note that we do not just *call* this function, because that
* won't necessarily do anything. We want the control flow
* that is currently executing in copyin (or whichever), and
* is stopped while we process the exception, to *teleport* to
* copyfail.
*
* This is accomplished by changing tf->tf_epc and returning
* from the exception handler.
*/
if (curthread != NULL &&
curthread->t_machdep.tm_badfaultfunc != NULL) {
tf->tf_epc = (vaddr_t) curthread->t_machdep.tm_badfaultfunc;
goto done;
}
/*
* Really fatal kernel-mode fault.
*/
kprintf("panic: Fatal exception %u (%s) in kernel mode\n", code,
trapcodenames[code]);
kprintf("panic: EPC 0x%x, exception vaddr 0x%x\n",
tf->tf_epc, tf->tf_vaddr);
panic("I can't handle this... I think I'll just die now...\n");
done:
/*
* Turn interrupts off on the processor, without affecting the
* stored interrupt state.
*/
cpu_irqoff();
done2:
/*
* The boot thread can get here (e.g. on interrupt return) but
* since it doesn't go to userlevel, it can't be returning to
* userlevel, so there's no need to set cputhreads[] and
* cpustacks[]. Just return.
*/
if (curthread->t_stack == NULL) {
return;
}
cputhreads[curcpu->c_number] = (vaddr_t)curthread;
cpustacks[curcpu->c_number] = (vaddr_t)curthread->t_stack + STACK_SIZE;
/*
* This assertion will fail if either
* (1) curthread->t_stack is corrupted, or
* (2) the trap frame is somehow on the wrong kernel stack.
*
* If cpustacks[] is corrupted, the next trap back to the
* kernel will (most likely) hang the system, so it's better
* to find out now.
*/
KASSERT(SAME_STACK(cpustacks[curcpu->c_number]-1, (vaddr_t)tf));
}
/*
* Function for entering user mode.
*
* This should not be used by threads returning from traps - they
* should just return from mips_trap(). It should be used by threads
* entering user mode for the first time - whether the child thread in
* a fork(), or into a brand-new address space after exec(), or when
* starting the first userlevel program.
*
* It works by jumping into the exception return code.
*
* mips_usermode is common code for this. It cannot usefully be called
* outside the mips port, but should be called from one of the
* following places:
* - enter_new_process, for use by exec and equivalent.
* - enter_forked_process, in syscall.c, for use by fork.
*/
void
mips_usermode(struct trapframe *tf)
{
/*
* Interrupts should be off within the kernel while entering
* user mode. However, while in user mode, interrupts should
* be on. To interact properly with the spl-handling logic
* above, we explicitly call spl0() and then call cpu_irqoff().
*/
spl0();
cpu_irqoff();
cputhreads[curcpu->c_number] = (vaddr_t)curthread;
cpustacks[curcpu->c_number] = (vaddr_t)curthread->t_stack + STACK_SIZE;
/*
* This assertion will fail if either
* (1) cpustacks[] is corrupted, or
* (2) the trap frame is not on our own kernel stack, or
* (3) the boot thread tries to enter user mode.
*
* If cpustacks[] is corrupted, the next trap back to the
* kernel will (most likely) hang the system, so it's better
* to find out now.
*
* It's necessary for the trap frame used here to be on the
* current thread's own stack. It cannot correctly be on
* either another thread's stack or in the kernel heap.
* (Exercise: why?)
*/
KASSERT(SAME_STACK(cpustacks[curcpu->c_number]-1, (vaddr_t)tf));
/*
* This actually does it. See exception-*.S.
*/
asm_usermode(tf);
}
/*
* enter_new_process: go to user mode after loading an executable.
*
* Performs the necessary initialization so that the user program will
* get the arguments supplied in argc/argv (note that argv must be a
* user-level address) and the environment pointer env (ditto), and
* begin executing at the specified entry point. The stack pointer is
* initialized from the stackptr argument. Note that passing argc/argv
* may use additional stack space on some other platforms (but not on
* mips).
*
* Unless you implement execve() that passes environments around, just
* pass NULL for the environment.
*
* Works by creating an ersatz trapframe.
*/
void
enter_new_process(int argc, userptr_t argv, userptr_t env,
vaddr_t stack, vaddr_t entry)
{
struct trapframe tf;
bzero(&tf, sizeof(tf));
tf.tf_status = CST_IRQMASK | CST_IEp | CST_KUp;
tf.tf_epc = entry;
tf.tf_a0 = argc;
tf.tf_a1 = (vaddr_t)argv;
tf.tf_a2 = (vaddr_t)env;
tf.tf_sp = stack;
mips_usermode(&tf);
}

View File

@ -0,0 +1,161 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#include <types.h>
#include <kern/errno.h>
#include <kern/syscall.h>
#include <lib.h>
#include <mips/trapframe.h>
#include <thread.h>
#include <current.h>
#include <syscall.h>
/*
* System call dispatcher.
*
* A pointer to the trapframe created during exception entry (in
* exception-*.S) is passed in.
*
* The calling conventions for syscalls are as follows: Like ordinary
* function calls, the first 4 32-bit arguments are passed in the 4
* argument registers a0-a3. 64-bit arguments are passed in *aligned*
* pairs of registers, that is, either a0/a1 or a2/a3. This means that
* if the first argument is 32-bit and the second is 64-bit, a1 is
* unused.
*
* This much is the same as the calling conventions for ordinary
* function calls. In addition, the system call number is passed in
* the v0 register.
*
* On successful return, the return value is passed back in the v0
* register, or v0 and v1 if 64-bit. This is also like an ordinary
* function call, and additionally the a3 register is also set to 0 to
* indicate success.
*
* On an error return, the error code is passed back in the v0
* register, and the a3 register is set to 1 to indicate failure.
* (Userlevel code takes care of storing the error code in errno and
* returning the value -1 from the actual userlevel syscall function.
* See src/user/lib/libc/arch/mips/syscalls-mips.S and related files.)
*
* Upon syscall return the program counter stored in the trapframe
* must be incremented by one instruction; otherwise the exception
* return code will restart the "syscall" instruction and the system
* call will repeat forever.
*
* If you run out of registers (which happens quickly with 64-bit
* values) further arguments must be fetched from the user-level
* stack, starting at sp+16 to skip over the slots for the
* registerized values, with copyin().
*/
void
syscall(struct trapframe *tf)
{
int callno;
int32_t retval;
int err;
KASSERT(curthread != NULL);
KASSERT(curthread->t_curspl == 0);
KASSERT(curthread->t_iplhigh_count == 0);
callno = tf->tf_v0;
/*
* Initialize retval to 0. Many of the system calls don't
* really return a value, just 0 for success and -1 on
* error. Since retval is the value returned on success,
* initialize it to 0 by default; thus it's not necessary to
* deal with it except for calls that return other values,
* like write.
*/
retval = 0;
switch (callno) {
case SYS_reboot:
err = sys_reboot(tf->tf_a0);
break;
case SYS___time:
err = sys___time((userptr_t)tf->tf_a0,
(userptr_t)tf->tf_a1);
break;
/* Add stuff here */
default:
kprintf("Unknown syscall %d\n", callno);
err = ENOSYS;
break;
}
if (err) {
/*
* Return the error code. This gets converted at
* userlevel to a return value of -1 and the error
* code in errno.
*/
tf->tf_v0 = err;
tf->tf_a3 = 1; /* signal an error */
}
else {
/* Success. */
tf->tf_v0 = retval;
tf->tf_a3 = 0; /* signal no error */
}
/*
* Now, advance the program counter, to avoid restarting
* the syscall over and over again.
*/
tf->tf_epc += 4;
/* Make sure the syscall code didn't forget to lower spl */
KASSERT(curthread->t_curspl == 0);
/* ...or leak any spinlocks */
KASSERT(curthread->t_iplhigh_count == 0);
}
/*
* Enter user mode for a newly forked process.
*
* This function is provided as a reminder. You need to write
* both it and the code that calls it.
*
* Thus, you can trash it and do things another way if you prefer.
*/
void
enter_forked_process(struct trapframe *tf)
{
(void)tf;
}

301
kern/arch/mips/thread/cpu.c Normal file
View File

@ -0,0 +1,301 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* CPU control functions.
*/
#include <types.h>
#include <lib.h>
#include <mips/specialreg.h>
#include <mips/trapframe.h>
#include <platform/maxcpus.h>
#include <cpu.h>
#include <thread.h>
////////////////////////////////////////////////////////////
/*
* Startup and exception-time stack hook.
*
* The MIPS lacks a good way to find the current CPU, current thread,
* or current thread stack upon trap entry from user mode. To deal
* with this, we store the CPU number (our number, not the hardware
* number) in a nonessential field in the MMU, which is about the only
* place possible, and then use that to index cpustacks[]. This gets
* us the value to load as the stack pointer. We can then also load
* curthread from cputhreads[] by parallel indexing.
*
* These arrays are also used to start up new CPUs, for roughly the
* same reasons.
*/
vaddr_t cpustacks[MAXCPUS];
vaddr_t cputhreads[MAXCPUS];
/*
* Do machine-dependent initialization of the cpu structure or things
* associated with a new cpu. Note that we're not running on the new
* cpu when this is called.
*/
void
cpu_machdep_init(struct cpu *c)
{
vaddr_t stackpointer;
KASSERT(c->c_number < MAXCPUS);
if (c->c_curthread->t_stack == NULL) {
/* boot cpu; don't need to do anything here */
}
else {
/*
* Stick the stack in cpustacks[], and thread pointer
* in cputhreads[].
*/
/* stack base address */
stackpointer = (vaddr_t) c->c_curthread->t_stack;
/* since stacks grow down, get the top */
stackpointer += STACK_SIZE;
cpustacks[c->c_number] = stackpointer;
cputhreads[c->c_number] = (vaddr_t)c->c_curthread;
}
}
////////////////////////////////////////////////////////////
/*
* Return the type name of the currently running CPU.
*
* For now, assume we're running on System/161 so we can use the
* System/161 processor-ID values.
*/
#define SYS161_PRID_ORIG 0x000003ff
#define SYS161_PRID_2X 0x000000a1
static inline
uint32_t
cpu_getprid(void)
{
uint32_t prid;
__asm volatile("mfc0 %0,$15" : "=r" (prid));
return prid;
}
static inline
uint32_t
cpu_getfeatures(void)
{
uint32_t features;
__asm volatile(".set push;" /* save assembler mode */
".set mips32;" /* allow mips32 instructions */
"mfc0 %0,$15,1;" /* get cop0 reg 15 sel 1 */
".set pop" /* restore assembler mode */
: "=r" (features));
return features;
}
static inline
uint32_t
cpu_getifeatures(void)
{
uint32_t features;
__asm volatile(".set push;" /* save assembler mode */
".set mips32;" /* allow mips32 instructions */
"mfc0 %0,$15,2;" /* get cop0 reg 15 sel 2 */
".set pop" /* restore assembler mode */
: "=r" (features));
return features;
}
void
cpu_identify(char *buf, size_t max)
{
uint32_t prid;
uint32_t features;
prid = cpu_getprid();
switch (prid) {
case SYS161_PRID_ORIG:
snprintf(buf, max, "MIPS/161 (System/161 1.x and pre-2.x)");
break;
case SYS161_PRID_2X:
features = cpu_getfeatures();
snprintf(buf, max, "MIPS/161 (System/161 2.x) features 0x%x",
features);
features = cpu_getifeatures();
if (features != 0) {
kprintf("WARNING: unknown CPU incompatible features "
"0x%x\n", features);
}
break;
default:
snprintf(buf, max, "32-bit MIPS (unknown type, CPU ID 0x%x)",
prid);
break;
}
}
////////////////////////////////////////////////////////////
/*
* Interrupt control.
*
* While the mips actually has on-chip interrupt priority masking, in
* the interests of simplicity, we don't use it. Instead we use
* coprocessor 0 register 12 (the system coprocessor "status"
* register) bit 0, IEc, which is the global interrupt enable flag.
* (IEc stands for interrupt-enable-current.)
*/
/*
* gcc inline assembly to get at the status register.
*
* Pipeline hazards:
* - there must be at least one cycle between GET_STATUS
* and SET_STATUS;
* - it may take up to three cycles after SET_STATUS for the
* interrupt state to really change.
*
* These considerations do not (currently) apply to System/161,
* however.
*/
#define GET_STATUS(x) __asm volatile("mfc0 %0,$12" : "=r" (x))
#define SET_STATUS(x) __asm volatile("mtc0 %0,$12" :: "r" (x))
/*
* Interrupts on.
*/
void
cpu_irqon(void)
{
uint32_t x;
GET_STATUS(x);
x |= CST_IEc;
SET_STATUS(x);
}
/*
* Interrupts off.
*/
void
cpu_irqoff(void)
{
uint32_t x;
GET_STATUS(x);
x &= ~(uint32_t)CST_IEc;
SET_STATUS(x);
}
/*
* Used below.
*/
static
void
cpu_irqonoff(void)
{
uint32_t x, xon, xoff;
GET_STATUS(x);
xon = x | CST_IEc;
xoff = x & ~(uint32_t)CST_IEc;
SET_STATUS(xon);
__asm volatile("nop; nop; nop; nop");
SET_STATUS(xoff);
}
////////////////////////////////////////////////////////////
/*
* Idling.
*/
/*
* gcc inline assembly for the WAIT instruction.
*
* mips r2k/r3k has no idle instruction at all.
*
* However, to avoid completely overloading the computing cluster, we
* appropriate the mips32 WAIT instruction.
*/
static
inline
void
wait(void)
{
/*
* The WAIT instruction goes into powersave mode until an
* interrupt is trying to occur.
*
* Then switch interrupts on and off again, so we actually
* take the interrupt.
*
* Note that the precise behavior of this instruction in the
* System/161 simulator is partly guesswork. This code may not
* work on a real mips.
*/
__asm volatile(
".set push;" /* save assembler mode */
".set mips32;" /* allow MIPS32 instructions */
".set volatile;" /* avoid unwanted optimization */
"wait;" /* suspend until interrupted */
".set pop" /* restore assembler mode */
);
}
/*
* Idle the processor until something happens.
*/
void
cpu_idle(void)
{
wait();
cpu_irqonoff();
}
/*
* Halt the CPU permanently.
*/
void
cpu_halt(void)
{
cpu_irqoff();
while (1) {
wait();
}
}

View File

@ -0,0 +1,99 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* Assembly language context switch code.
*/
#include <kern/mips/regdefs.h>
.text
.set noreorder
.globl switchframe_switch
.type switchframe_switch,@function
.ent switchframe_switch
switchframe_switch:
/*
* a0 contains the address of the switchframe pointer in the old thread.
* a1 contains the address of the switchframe pointer in the new thread.
*
* The switchframe pointer is really the stack pointer. The other
* registers get saved on the stack, namely:
*
* s0-s6, s8
* gp, ra
*
* The order must match <mips/switchframe.h>.
*
* Note that while we'd ordinarily need to save s7 too, because we
* use it to hold curthread saving it would interfere with the way
* curthread is managed by thread.c. So we'll just let thread.c
* manage it.
*/
/* Allocate stack space for saving 10 registers. 10*4 = 40 */
addi sp, sp, -40
/* Save the registers */
sw ra, 36(sp)
sw gp, 32(sp)
sw s8, 28(sp)
sw s6, 24(sp)
sw s5, 20(sp)
sw s4, 16(sp)
sw s3, 12(sp)
sw s2, 8(sp)
sw s1, 4(sp)
sw s0, 0(sp)
/* Store the old stack pointer in the old thread */
sw sp, 0(a0)
/* Get the new stack pointer from the new thread */
lw sp, 0(a1)
nop /* delay slot for load */
/* Now, restore the registers */
lw s0, 0(sp)
lw s1, 4(sp)
lw s2, 8(sp)
lw s3, 12(sp)
lw s4, 16(sp)
lw s5, 20(sp)
lw s6, 24(sp)
lw s8, 28(sp)
lw gp, 32(sp)
lw ra, 36(sp)
nop /* delay slot for load */
/* and return. */
j ra
addi sp, sp, 40 /* in delay slot */
.end switchframe_switch

View File

@ -0,0 +1,98 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#include <types.h>
#include <lib.h>
#include <thread.h>
#include <threadprivate.h>
#include "switchframe.h"
/* in threadstart.S */
extern void mips_threadstart(/* arguments are in unusual registers */);
/*
* Function to initialize the switchframe of a new thread, which is
* *not* the one that is currently running.
*
* The new thread should, when it is run the first time, end up calling
* thread_startup(entrypoint, data1, data2).
*
* We arrange for this by creating a phony switchframe for
* switchframe_switch() to switch to. The only trouble is that the
* switchframe doesn't include the argument registers a0-a3. So we
* store the arguments in the s* registers, and use a bit of asm
* (mips_threadstart) to move them and then jump to thread_startup.
*/
void
switchframe_init(struct thread *thread,
void (*entrypoint)(void *data1, unsigned long data2),
void *data1, unsigned long data2)
{
vaddr_t stacktop;
struct switchframe *sf;
/*
* MIPS stacks grow down. t_stack is just a hunk of memory, so
* get the other end of it. Then set up a switchframe on the
* top of the stack.
*/
stacktop = ((vaddr_t)thread->t_stack) + STACK_SIZE;
sf = ((struct switchframe *) stacktop) - 1;
/* Zero out the switchframe. */
bzero(sf, sizeof(*sf));
/*
* Now set the important parts: pass through the three arguments,
* and set the return address register to the place we want
* execution to begin.
*
* Thus, when switchframe_switch does its "j ra", it will
* actually jump to mips_threadstart, which will move the
* arguments into the right register and jump to
* thread_startup().
*
* Note that this means that when we call switchframe_switch()
* in thread_switch(), we may not come back out the same way
* in the next thread. (Though we will come back out the same
* way when we later come back to the same thread again.)
*
* This has implications for code at the bottom of
* thread_switch, described in thread.c.
*/
sf->sf_s0 = (uint32_t)entrypoint;
sf->sf_s1 = (uint32_t)data1;
sf->sf_s2 = (uint32_t)data2;
sf->sf_ra = (uint32_t)mips_threadstart;
/* Set ->t_context, and we're done. */
thread->t_context = sf;
}

View File

@ -0,0 +1,52 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifndef _MIPS_SWITCHFRAME_H_
#define _MIPS_SWITCHFRAME_H_
/*
* Structure describing what is saved on the stack during a context switch.
*
* This must agree with the code in switch.S.
*/
struct switchframe {
uint32_t sf_s0;
uint32_t sf_s1;
uint32_t sf_s2;
uint32_t sf_s3;
uint32_t sf_s4;
uint32_t sf_s5;
uint32_t sf_s6;
uint32_t sf_s8;
uint32_t sf_gp;
uint32_t sf_ra;
};
#endif /* _MIPS_SWITCHFRAME_H_ */

View File

@ -0,0 +1,49 @@
/*
* Copyright (c) 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* Functions for handling struct thread_machdep.
*/
#include <types.h>
#include <lib.h>
#include <thread.h>
#include <threadprivate.h>
void
thread_machdep_init(struct thread_machdep *tm)
{
tm->tm_badfaultfunc = NULL;
}
void
thread_machdep_cleanup(struct thread_machdep *tm)
{
KASSERT(tm->tm_badfaultfunc == NULL);
}

View File

@ -0,0 +1,68 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* Assembler-level thread startup trampoline.
*/
#include <kern/mips/regdefs.h>
.text
.set noreorder
.globl mips_threadstart
.type mips_threadstart,@function
.ent mips_threadstart
mips_threadstart:
/*
* This code doesn't take normal arguments. It's reached when
* switchframe_switch switches to a new thread. switchframe_switch
* does "j ra"; ra gets preloaded in switchframe_init to come here.
*
* Our arguments are in callee-save registers, as follows:
*
* s0 entrypoint
* s1 data1
* s2 data2
*
* We need to rearrange these so as to call the normal C function
* thread_startup(void (*entrypoint)(), void *data1, unsigned long data2).
*/
addiu sp, sp, -16 /* make our stack frame */
move ra, $0 /* clear return addr so we're top of the call stack */
move a0, s0 /* load arguments and call */
move a1, s1
j thread_startup
move a2, s2 /* (in delay slot) */
.end mips_threadstart

433
kern/arch/mips/vm/dumbvm.c Normal file
View File

@ -0,0 +1,433 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#include <types.h>
#include <kern/errno.h>
#include <lib.h>
#include <spl.h>
#include <cpu.h>
#include <spinlock.h>
#include <proc.h>
#include <current.h>
#include <mips/tlb.h>
#include <addrspace.h>
#include <vm.h>
/*
* Dumb MIPS-only "VM system" that is intended to only be just barely
* enough to struggle off the ground. You should replace all of this
* code while doing the VM assignment. In fact, starting in that
* assignment, this file is not included in your kernel!
*
* NOTE: it's been found over the years that students often begin on
* the VM assignment by copying dumbvm.c and trying to improve it.
* This is not recommended. dumbvm is (more or less intentionally) not
* a good design reference. The first recommendation would be: do not
* look at dumbvm at all. The second recommendation would be: if you
* do, be sure to review it from the perspective of comparing it to
* what a VM system is supposed to do, and understanding what corners
* it's cutting (there are many) and why, and more importantly, how.
*/
/* under dumbvm, always have 72k of user stack */
/* (this must be > 64K so argument blocks of size ARG_MAX will fit) */
#define DUMBVM_STACKPAGES 18
/*
* Wrap ram_stealmem in a spinlock.
*/
static struct spinlock stealmem_lock = SPINLOCK_INITIALIZER;
void
vm_bootstrap(void)
{
/* Do nothing. */
}
/*
* Check if we're in a context that can sleep. While most of the
* operations in dumbvm don't in fact sleep, in a real VM system many
* of them would. In those, assert that sleeping is ok. This helps
* avoid the situation where syscall-layer code that works ok with
* dumbvm starts blowing up during the VM assignment.
*/
static
void
dumbvm_can_sleep(void)
{
if (CURCPU_EXISTS()) {
/* must not hold spinlocks */
KASSERT(curcpu->c_spinlocks == 0);
/* must not be in an interrupt handler */
KASSERT(curthread->t_in_interrupt == 0);
}
}
static
paddr_t
getppages(unsigned long npages)
{
paddr_t addr;
spinlock_acquire(&stealmem_lock);
addr = ram_stealmem(npages);
spinlock_release(&stealmem_lock);
return addr;
}
/* Allocate/free some kernel-space virtual pages */
vaddr_t
alloc_kpages(unsigned npages)
{
paddr_t pa;
dumbvm_can_sleep();
pa = getppages(npages);
if (pa==0) {
return 0;
}
return PADDR_TO_KVADDR(pa);
}
void
free_kpages(vaddr_t addr)
{
/* nothing - leak the memory. */
(void)addr;
}
void
vm_tlbshootdown_all(void)
{
panic("dumbvm tried to do tlb shootdown?!\n");
}
void
vm_tlbshootdown(const struct tlbshootdown *ts)
{
(void)ts;
panic("dumbvm tried to do tlb shootdown?!\n");
}
int
vm_fault(int faulttype, vaddr_t faultaddress)
{
vaddr_t vbase1, vtop1, vbase2, vtop2, stackbase, stacktop;
paddr_t paddr;
int i;
uint32_t ehi, elo;
struct addrspace *as;
int spl;
faultaddress &= PAGE_FRAME;
DEBUG(DB_VM, "dumbvm: fault: 0x%x\n", faultaddress);
switch (faulttype) {
case VM_FAULT_READONLY:
/* We always create pages read-write, so we can't get this */
panic("dumbvm: got VM_FAULT_READONLY\n");
case VM_FAULT_READ:
case VM_FAULT_WRITE:
break;
default:
return EINVAL;
}
if (curproc == NULL) {
/*
* No process. This is probably a kernel fault early
* in boot. Return EFAULT so as to panic instead of
* getting into an infinite faulting loop.
*/
return EFAULT;
}
as = proc_getas();
if (as == NULL) {
/*
* No address space set up. This is probably also a
* kernel fault early in boot.
*/
return EFAULT;
}
/* Assert that the address space has been set up properly. */
KASSERT(as->as_vbase1 != 0);
KASSERT(as->as_pbase1 != 0);
KASSERT(as->as_npages1 != 0);
KASSERT(as->as_vbase2 != 0);
KASSERT(as->as_pbase2 != 0);
KASSERT(as->as_npages2 != 0);
KASSERT(as->as_stackpbase != 0);
KASSERT((as->as_vbase1 & PAGE_FRAME) == as->as_vbase1);
KASSERT((as->as_pbase1 & PAGE_FRAME) == as->as_pbase1);
KASSERT((as->as_vbase2 & PAGE_FRAME) == as->as_vbase2);
KASSERT((as->as_pbase2 & PAGE_FRAME) == as->as_pbase2);
KASSERT((as->as_stackpbase & PAGE_FRAME) == as->as_stackpbase);
vbase1 = as->as_vbase1;
vtop1 = vbase1 + as->as_npages1 * PAGE_SIZE;
vbase2 = as->as_vbase2;
vtop2 = vbase2 + as->as_npages2 * PAGE_SIZE;
stackbase = USERSTACK - DUMBVM_STACKPAGES * PAGE_SIZE;
stacktop = USERSTACK;
if (faultaddress >= vbase1 && faultaddress < vtop1) {
paddr = (faultaddress - vbase1) + as->as_pbase1;
}
else if (faultaddress >= vbase2 && faultaddress < vtop2) {
paddr = (faultaddress - vbase2) + as->as_pbase2;
}
else if (faultaddress >= stackbase && faultaddress < stacktop) {
paddr = (faultaddress - stackbase) + as->as_stackpbase;
}
else {
return EFAULT;
}
/* make sure it's page-aligned */
KASSERT((paddr & PAGE_FRAME) == paddr);
/* Disable interrupts on this CPU while frobbing the TLB. */
spl = splhigh();
for (i=0; i<NUM_TLB; i++) {
tlb_read(&ehi, &elo, i);
if (elo & TLBLO_VALID) {
continue;
}
ehi = faultaddress;
elo = paddr | TLBLO_DIRTY | TLBLO_VALID;
DEBUG(DB_VM, "dumbvm: 0x%x -> 0x%x\n", faultaddress, paddr);
tlb_write(ehi, elo, i);
splx(spl);
return 0;
}
kprintf("dumbvm: Ran out of TLB entries - cannot handle page fault\n");
splx(spl);
return EFAULT;
}
struct addrspace *
as_create(void)
{
struct addrspace *as = kmalloc(sizeof(struct addrspace));
if (as==NULL) {
return NULL;
}
as->as_vbase1 = 0;
as->as_pbase1 = 0;
as->as_npages1 = 0;
as->as_vbase2 = 0;
as->as_pbase2 = 0;
as->as_npages2 = 0;
as->as_stackpbase = 0;
return as;
}
void
as_destroy(struct addrspace *as)
{
dumbvm_can_sleep();
kfree(as);
}
void
as_activate(void)
{
int i, spl;
struct addrspace *as;
as = proc_getas();
if (as == NULL) {
return;
}
/* Disable interrupts on this CPU while frobbing the TLB. */
spl = splhigh();
for (i=0; i<NUM_TLB; i++) {
tlb_write(TLBHI_INVALID(i), TLBLO_INVALID(), i);
}
splx(spl);
}
void
as_deactivate(void)
{
/* nothing */
}
int
as_define_region(struct addrspace *as, vaddr_t vaddr, size_t sz,
int readable, int writeable, int executable)
{
size_t npages;
dumbvm_can_sleep();
/* Align the region. First, the base... */
sz += vaddr & ~(vaddr_t)PAGE_FRAME;
vaddr &= PAGE_FRAME;
/* ...and now the length. */
sz = (sz + PAGE_SIZE - 1) & PAGE_FRAME;
npages = sz / PAGE_SIZE;
/* We don't use these - all pages are read-write */
(void)readable;
(void)writeable;
(void)executable;
if (as->as_vbase1 == 0) {
as->as_vbase1 = vaddr;
as->as_npages1 = npages;
return 0;
}
if (as->as_vbase2 == 0) {
as->as_vbase2 = vaddr;
as->as_npages2 = npages;
return 0;
}
/*
* Support for more than two regions is not available.
*/
kprintf("dumbvm: Warning: too many regions\n");
return ENOSYS;
}
static
void
as_zero_region(paddr_t paddr, unsigned npages)
{
bzero((void *)PADDR_TO_KVADDR(paddr), npages * PAGE_SIZE);
}
int
as_prepare_load(struct addrspace *as)
{
KASSERT(as->as_pbase1 == 0);
KASSERT(as->as_pbase2 == 0);
KASSERT(as->as_stackpbase == 0);
dumbvm_can_sleep();
as->as_pbase1 = getppages(as->as_npages1);
if (as->as_pbase1 == 0) {
return ENOMEM;
}
as->as_pbase2 = getppages(as->as_npages2);
if (as->as_pbase2 == 0) {
return ENOMEM;
}
as->as_stackpbase = getppages(DUMBVM_STACKPAGES);
if (as->as_stackpbase == 0) {
return ENOMEM;
}
as_zero_region(as->as_pbase1, as->as_npages1);
as_zero_region(as->as_pbase2, as->as_npages2);
as_zero_region(as->as_stackpbase, DUMBVM_STACKPAGES);
return 0;
}
int
as_complete_load(struct addrspace *as)
{
dumbvm_can_sleep();
(void)as;
return 0;
}
int
as_define_stack(struct addrspace *as, vaddr_t *stackptr)
{
KASSERT(as->as_stackpbase != 0);
*stackptr = USERSTACK;
return 0;
}
int
as_copy(struct addrspace *old, struct addrspace **ret)
{
struct addrspace *new;
dumbvm_can_sleep();
new = as_create();
if (new==NULL) {
return ENOMEM;
}
new->as_vbase1 = old->as_vbase1;
new->as_npages1 = old->as_npages1;
new->as_vbase2 = old->as_vbase2;
new->as_npages2 = old->as_npages2;
/* (Mis)use as_prepare_load to allocate some physical memory. */
if (as_prepare_load(new)) {
as_destroy(new);
return ENOMEM;
}
KASSERT(new->as_pbase1 != 0);
KASSERT(new->as_pbase2 != 0);
KASSERT(new->as_stackpbase != 0);
memmove((void *)PADDR_TO_KVADDR(new->as_pbase1),
(const void *)PADDR_TO_KVADDR(old->as_pbase1),
old->as_npages1*PAGE_SIZE);
memmove((void *)PADDR_TO_KVADDR(new->as_pbase2),
(const void *)PADDR_TO_KVADDR(old->as_pbase2),
old->as_npages2*PAGE_SIZE);
memmove((void *)PADDR_TO_KVADDR(new->as_stackpbase),
(const void *)PADDR_TO_KVADDR(old->as_stackpbase),
DUMBVM_STACKPAGES*PAGE_SIZE);
*ret = new;
return 0;
}

153
kern/arch/mips/vm/ram.c Normal file
View File

@ -0,0 +1,153 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#include <types.h>
#include <lib.h>
#include <vm.h>
#include <mainbus.h>
vaddr_t firstfree; /* first free virtual address; set by start.S */
static paddr_t firstpaddr; /* address of first free physical page */
static paddr_t lastpaddr; /* one past end of last free physical page */
/*
* Called very early in system boot to figure out how much physical
* RAM is available.
*/
void
ram_bootstrap(void)
{
size_t ramsize;
/* Get size of RAM. */
ramsize = mainbus_ramsize();
/*
* This is the same as the last physical address, as long as
* we have less than 512 megabytes of memory. If we had more,
* we wouldn't be able to access it all through kseg0 and
* everything would get a lot more complicated. This is not a
* case we are going to worry about.
*/
if (ramsize > 512*1024*1024) {
ramsize = 512*1024*1024;
}
lastpaddr = ramsize;
/*
* Get first free virtual address from where start.S saved it.
* Convert to physical address.
*/
firstpaddr = firstfree - MIPS_KSEG0;
kprintf("%uk physical memory available\n",
(lastpaddr-firstpaddr)/1024);
}
/*
* This function is for allocating physical memory prior to VM
* initialization.
*
* The pages it hands back will not be reported to the VM system when
* the VM system calls ram_getsize(). If it's desired to free up these
* pages later on after bootup is complete, some mechanism for adding
* them to the VM system's page management must be implemented.
* Alternatively, one can do enough VM initialization early so that
* this function is never needed.
*
* Note: while the error return value of 0 is a legal physical address,
* it's not a legal *allocatable* physical address, because it's the
* page with the exception handlers on it.
*
* This function should not be called once the VM system is initialized,
* so it is not synchronized.
*/
paddr_t
ram_stealmem(unsigned long npages)
{
size_t size;
paddr_t paddr;
size = npages * PAGE_SIZE;
if (firstpaddr + size > lastpaddr) {
return 0;
}
paddr = firstpaddr;
firstpaddr += size;
return paddr;
}
/*
* This function is intended to be called by the VM system when it
* initializes in order to find out what memory it has available to
* manage. Physical memory begins at physical address 0 and ends with
* the address returned by this function. We assume that physical
* memory is contiguous. This is not universally true, but is true on
* the MIPS platforms we intend to run on.
*
* lastpaddr is constant once set by ram_bootstrap(), so this function
* need not be synchronized.
*
* It is recommended, however, that this function be used only to
* initialize the VM system, after which the VM system should take
* charge of knowing what memory exists.
*/
paddr_t
ram_getsize(void)
{
return lastpaddr;
}
/*
* This function is intended to be called by the VM system when it
* initializes in order to find out what memory it has available to
* manage.
*
* It can only be called once, and once called ram_stealmem() will
* no longer work, as that would invalidate the result it returned
* and lead to multiple things using the same memory.
*
* This function should not be called once the VM system is initialized,
* so it is not synchronized.
*/
paddr_t
ram_getfirstfree(void)
{
paddr_t ret;
ret = firstpaddr;
firstpaddr = lastpaddr = 0;
return ret;
}

View File

@ -0,0 +1,204 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#include <kern/mips/regdefs.h>
#include <mips/specialreg.h>
/*
* TLB handling for the MIPS-161.
*
* The MIPS-161 uses the simpler MIPS-1 (r2000/r3000) TLB rather
* than the paired-page TLB of later MIPS models.
*
* However, we handle MIPS32 pipeline hazards. If you want to run on
* a real MIPS-1, change the ssnops to plain nops and check where and
* how many you need in the matching processor docs.
*
* (ssnop means "superscalar nop"; it exists because the pipeline
* hazards require a fixed number of cycles, and a superscalar CPU can
* potentially issue arbitrarily many nops in one cycle.)
*/
.text
.set noreorder
.set mips32 /* so we can use ssnop */
/*
* tlb_random: use the "tlbwr" instruction to write a TLB entry
* into a (very pseudo-) random slot in the TLB.
*
* Pipeline hazard: must wait between setting entryhi/lo and
* doing the tlbwr. Use two cycles; some processors may vary.
*/
.globl tlb_random
.type tlb_random,@function
.ent tlb_random
tlb_random:
mtc0 a0, c0_entryhi /* store the passed entry into the */
mtc0 a1, c0_entrylo /* tlb entry registers */
ssnop /* wait for pipeline hazard */
ssnop
tlbwr /* do it */
j ra
nop
.end tlb_random
/*
* tlb_write: use the "tlbwi" instruction to write a TLB entry
* into a selected slot in the TLB.
*
* Pipeline hazard: must wait between setting entryhi/lo and
* doing the tlbwi. Use two cycles; some processors may vary.
*/
.text
.globl tlb_write
.type tlb_write,@function
.ent tlb_write
tlb_write:
mtc0 a0, c0_entryhi /* store the passed entry into the */
mtc0 a1, c0_entrylo /* tlb entry registers */
sll t0, a2, CIN_INDEXSHIFT /* shift the passed index into place */
mtc0 t0, c0_index /* store the shifted index into the index register */
ssnop /* wait for pipeline hazard */
ssnop
tlbwi /* do it */
j ra
nop
.end tlb_write
/*
* tlb_read: use the "tlbr" instruction to read a TLB entry
* from a selected slot in the TLB.
*
* Pipeline hazard: must wait between setting c0_index and
* doing the tlbr. Use two cycles; some processors may vary.
* Similarly, three more cycles before reading c0_entryhi/lo.
*/
.text
.globl tlb_read
.type tlb_read,@function
.ent tlb_read
tlb_read:
sll t0, a2, CIN_INDEXSHIFT /* shift the passed index into place */
mtc0 t0, c0_index /* store the shifted index into the index register */
ssnop /* wait for pipeline hazard */
ssnop
tlbr /* do it */
ssnop /* wait for pipeline hazard */
ssnop
ssnop
mfc0 t0, c0_entryhi /* get the tlb entry out of the */
mfc0 t1, c0_entrylo /* tlb entry registers */
sw t0, 0(a0) /* store through the passed pointer */
j ra
sw t1, 0(a1) /* store (in delay slot) */
.end tlb_read
/*
* tlb_probe: use the "tlbp" instruction to find the index in the
* TLB of a TLB entry matching the relevant parts of the one supplied.
*
* Pipeline hazard: must wait between setting c0_entryhi/lo and
* doing the tlbp. Use two cycles; some processors may vary.
* Similarly, two more cycles before reading c0_index.
*/
.text
.globl tlb_probe
.type tlb_probe,@function
.ent tlb_probe
tlb_probe:
mtc0 a0, c0_entryhi /* store the passed entry into the */
mtc0 a1, c0_entrylo /* tlb entry registers */
ssnop /* wait for pipeline hazard */
ssnop
tlbp /* do it */
ssnop /* wait for pipeline hazard */
ssnop
mfc0 t0, c0_index /* fetch the index back in t0 */
/*
* If the high bit (CIN_P) of c0_index is set, the probe failed.
* The high bit is not set <--> c0_index (now in t0) >= 0.
*/
bgez t0, 1f /* did probe succeed? if so, skip forward */
nop /* delay slot */
addi v0, z0, -1 /* set return value to -1 to indicate failure */
j ra /* done */
nop /* delay slot */
1:
/* succeeded - get the index field from the index register value */
andi t1, t0, CIN_INDEX /* mask off the field */
j ra /* done */
sra v0, t1, CIN_INDEXSHIFT /* shift it (in delay slot) */
.end tlb_probe
/*
* tlb_reset
*
* Initialize the TLB. At processor startup, the TLB state is completely
* undefined. So be sure to avoid creating any duplicates. Also make sure
* that the initialization entries don't duplicate the INVALID entries
* defined in tlb.h. (This way you can write the invalid entries in
* without having to use tlbp to find out if they're going to cause dups.)
*
* This function is not defined in tlb.h because it's only called from
* start.S.
*
* Pipeline hazards are as above.
*/
.text
.globl tlb_reset
.type tlb_reset,@function
.ent tlb_reset
tlb_reset:
li t0, 0 /* t0 <- tlb index number (shifted) */
li t1, 0x81000000 /* t1 <- tlb reset vaddr */
1:
mtc0 $0, c0_entrylo /* set up proposed tlb entry for reset */
mtc0 t1, c0_entryhi
ssnop /* wait for pipeline hazard */
ssnop
tlbp /* check if it already exists */
ssnop /* wait for pipeline hazard */
ssnop
mfc0 t2, c0_index
bgez t2, 1b /* if it does, loop back */
addiu t1, t1, 0x1000 /* next vaddr (in delay slot) */
mtc0 t0, c0_index /* doesn't exist, set index to write to */
ssnop /* wait for pipeline hazard */
ssnop
addiu t0, t0, 0x100 /* next tlb index (shifted) */
bne t0, 0x4000, 1b /* if it's not the last tlb index, loop */
tlbwi /* write tlb entry (in delay slot) */
j ra /* done */
nop /* delay slot */
.end tlb_reset

View File

@ -0,0 +1,34 @@
#
# Platform-dependent sources for System/161.
#
#
# locore
#
# Cache handling for the kind of MIPS we have
platform sys161 file arch/mips/locore/cache-mips161.S
# Exception handling (assembler entry points) for the kind of MIPS we have
platform sys161 file arch/mips/locore/exception-mips1.S
#
# VM
#
# TLB handling for the kind of MIPS we have
platform sys161 file arch/mips/vm/tlb-mips161.S
#
# Devices. We have LAMEbus.
#
platform sys161 file arch/sys161/dev/lamebus_machdep.c
include dev/lamebus/conf.lamebus
#
# Startup and initialization.
#
platform sys161 file arch/sys161/main/start.S

View File

@ -0,0 +1,334 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#include <types.h>
#include <kern/unistd.h>
#include <lib.h>
#include <mips/specialreg.h>
#include <mips/trapframe.h>
#include <cpu.h>
#include <spl.h>
#include <clock.h>
#include <thread.h>
#include <current.h>
#include <membar.h>
#include <synch.h>
#include <mainbus.h>
#include <sys161/bus.h>
#include <lamebus/lamebus.h>
#include "autoconf.h"
/*
* CPU frequency used by the on-chip timer.
*
* Note that we really ought to measure the CPU frequency against the
* real-time clock instead of compiling it in like this.
*/
#define CPU_FREQUENCY 25000000 /* 25 MHz */
/*
* Access to the on-chip timer.
*
* The c0_count register increments on every cycle; when the value
* matches the c0_compare register, the timer interrupt line is
* asserted. Writing to c0_compare again clears the interrupt.
*/
static
void
mips_timer_set(uint32_t count)
{
/*
* $11 == c0_compare; we can't use the symbolic name inside
* the asm string.
*/
__asm volatile(
".set push;" /* save assembler mode */
".set mips32;" /* allow MIPS32 registers */
"mtc0 %0, $11;" /* do it */
".set pop" /* restore assembler mode */
:: "r" (count));
}
/*
* LAMEbus data for the system. (We have only one LAMEbus per system.)
* This does not need to be locked, because it's constant once
* initialized, and initialized before we start other threads or CPUs.
*/
static struct lamebus_softc *lamebus;
void
mainbus_bootstrap(void)
{
/* Interrupts should be off (and have been off since startup) */
KASSERT(curthread->t_curspl > 0);
/* Initialize the system LAMEbus data */
lamebus = lamebus_init();
/* Probe CPUs (should these be done as device attachments instead?) */
lamebus_find_cpus(lamebus);
/*
* Print the device name for the main bus.
*/
kprintf("lamebus0 (system main bus)\n");
/*
* Now we can take interrupts without croaking, so turn them on.
* Some device probes might require being able to get interrupts.
*/
spl0();
/*
* Now probe all the devices attached to the bus.
* (This amounts to all devices.)
*/
autoconf_lamebus(lamebus, 0);
/*
* Configure the MIPS on-chip timer to interrupt HZ times a second.
*/
mips_timer_set(CPU_FREQUENCY / HZ);
}
/*
* Start all secondary CPUs.
*/
void
mainbus_start_cpus(void)
{
lamebus_start_cpus(lamebus);
}
/*
* Function to generate the memory address (in the uncached segment)
* for the specified offset into the specified slot's region of the
* LAMEbus.
*/
void *
lamebus_map_area(struct lamebus_softc *bus, int slot, uint32_t offset)
{
uint32_t address;
(void)bus; // not needed
KASSERT(slot >= 0 && slot < LB_NSLOTS);
address = LB_BASEADDR + slot*LB_SLOT_SIZE + offset;
return (void *)address;
}
/*
* Read a 32-bit register from a LAMEbus device.
*/
uint32_t
lamebus_read_register(struct lamebus_softc *bus, int slot, uint32_t offset)
{
uint32_t *ptr;
ptr = lamebus_map_area(bus, slot, offset);
/*
* Make sure the load happens after anything the device has
* been doing.
*/
membar_load_load();
return *ptr;
}
/*
* Write a 32-bit register of a LAMEbus device.
*/
void
lamebus_write_register(struct lamebus_softc *bus, int slot,
uint32_t offset, uint32_t val)
{
uint32_t *ptr;
ptr = lamebus_map_area(bus, slot, offset);
*ptr = val;
/*
* Make sure the store happens before we do anything else to
* the device.
*/
membar_store_store();
}
/*
* Power off the system.
*/
void
mainbus_poweroff(void)
{
/*
*
* Note that lamebus_write_register() doesn't actually access
* the bus argument, so this will still work if we get here
* before the bus is initialized.
*/
lamebus_poweroff(lamebus);
}
/*
* Reboot the system.
*/
void
mainbus_reboot(void)
{
/*
* The MIPS doesn't appear to have any on-chip reset.
* LAMEbus doesn't have a reset control, so we just
* power off instead of rebooting. This would not be
* so great in a real system, but it's fine for what
* we're doing.
*/
kprintf("Cannot reboot - powering off instead, sorry.\n");
mainbus_poweroff();
}
/*
* Halt the system.
* On some systems, this would return to the boot monitor. But we don't
* have one.
*/
void
mainbus_halt(void)
{
cpu_halt();
}
/*
* Called to reset the system from panic().
*
* By the time we get here, the system may well be sufficiently hosed
* as to panic recursively if we do much of anything. So just power off.
* (We'd reboot, but System/161 doesn't do that.)
*/
void
mainbus_panic(void)
{
mainbus_poweroff();
}
/*
* Function to get the size of installed physical RAM from the LAMEbus
* controller.
*/
uint32_t
mainbus_ramsize(void)
{
uint32_t ramsize;
ramsize = lamebus_ramsize();
/*
* This is the same as the last physical address, as long as
* we have less than 508 megabytes of memory. The LAMEbus I/O
* area occupies the space between 508 megabytes and 512
* megabytes, so if we had more RAM than this it would have to
* be discontiguous. This is not a case we are going to worry
* about.
*/
if (ramsize > 508*1024*1024) {
ramsize = 508*1024*1024;
}
return ramsize;
}
/*
* Send IPI.
*/
void
mainbus_send_ipi(struct cpu *target)
{
lamebus_assert_ipi(lamebus, target);
}
/*
* Interrupt dispatcher.
*/
/* Wiring of LAMEbus interrupts to bits in the cause register */
#define LAMEBUS_IRQ_BIT 0x00000400 /* all system bus slots */
#define LAMEBUS_IPI_BIT 0x00000800 /* inter-processor interrupt */
#define MIPS_TIMER_BIT 0x00008000 /* on-chip timer */
void
mainbus_interrupt(struct trapframe *tf)
{
uint32_t cause;
bool seen = false;
/* interrupts should be off */
KASSERT(curthread->t_curspl > 0);
cause = tf->tf_cause;
if (cause & LAMEBUS_IRQ_BIT) {
lamebus_interrupt(lamebus);
seen = true;
}
if (cause & LAMEBUS_IPI_BIT) {
interprocessor_interrupt();
lamebus_clear_ipi(lamebus, curcpu);
seen = true;
}
if (cause & MIPS_TIMER_BIT) {
/* Reset the timer (this clears the interrupt) */
mips_timer_set(CPU_FREQUENCY / HZ);
/* and call hardclock */
hardclock();
seen = true;
}
if (!seen) {
if ((cause & CCA_IRQS) == 0) {
/*
* Don't panic here; this can happen if an
* interrupt line asserts (very) briefly and
* turns off again before we get as far as
* reading the cause register. This was
* actually seen... once.
*/
}
else {
/*
* But if we get an interrupt on an interrupt
* line that's not supposed to be wired up,
* complain.
*/
panic("Unknown interrupt; cause register is %08x\n",
cause);
}
}
}

View File

@ -0,0 +1,60 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifndef _SYS161_BUS_H_
#define _SYS161_BUS_H_
/*
* Generic bus interface file.
*
* The only bus on System/161 is LAMEbus.
* This would need to be a bit more complicated if that weren't the case.
*/
#include <machine/vm.h> /* for MIPS_KSEG1 */
#include <lamebus/lamebus.h> /* for LAMEbus definitions */
#define bus_write_register(bus, slot, offset, val) \
lamebus_write_register(bus, slot, offset, val)
#define bus_read_register(bus, slot, offset) \
lamebus_read_register(bus, slot, offset)
#define bus_map_area(bus, slot, offset) \
lamebus_map_area(bus, slot, offset)
/*
* Machine-dependent LAMEbus definitions
*/
/* Base address of the LAMEbus mapping area */
#define LB_BASEADDR (MIPS_KSEG1 + 0x1fe00000)
#endif /* _SYS161_BUS_H_ */

View File

@ -0,0 +1,44 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifndef _SYS161_MAXCPUS_H_
#define _SYS161_MAXCPUS_H_
/*
* For various reasons (see mips/cpu.c) it's desirable to have a
* fixed-size per-cpu array in the data segment. This is
* platform-dependent rather than processor-dependent because there's
* nothing about the processor that determines how many CPUs can
* exist; however, any real platform has *some* limit. For System/161,
* the limit is 32.
*/
#define MAXCPUS 32
#endif /* _SYS161_MAXCPUS_H_ */

View File

@ -0,0 +1,335 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#include <kern/mips/regdefs.h>
#include <mips/specialreg.h>
.set noreorder
.text
.globl __start
.type __start,@function
.ent __start
__start:
/*
* Stack frame. We save the return address register, even though
* it contains nothing useful. This is for gdb's benefit when it
* comes disassembling. We also need 16 bytes for making a call,
* and we have to align to an 8-byte (64-bit) boundary, so the
* total frame size is 24.
*
* Note that the frame here must match the frame we set up below
* when we switch off the bootup stack. Otherwise, gdb gets very
* confused.
*/
.frame sp, 24, $0 /* 24-byte sp-relative frame; return addr on stack */
.mask 0x80000000, -4 /* register 31 (ra) saved at (sp+24)-4 */
addiu sp, sp, -24
sw ra, 20(sp)
/*
* The System/161 loader sets up a boot stack for the first
* processor at the top of physical memory, and passes us a single
* string argument. The string lives on the very top of the stack.
* We get its address in a0.
*
* The kernel loads at virtual address 0x80000200, which is
* physical address 0x00000200. The space immediately below this
* is reserved for the exception vector code.
*
* The symbol _end is generated by the linker. It's the address of
* the end of the kernel. It's not a variable; the *value* of the
* _end symbol itself is this address. In C you'd use "&_end".
*
* We set up the memory map like this:
*
* top of memory
* free memory
* P + 0x1000
* first thread's stack (1 page)
* P
* wasted space (< 1 page)
* copy of the boot string
* _end
* kernel
* 0x80000200
* exception handlers
* 0x80000000
*
* where P is the next whole page after copying the argument string.
*/
la s0, _end /* stash _end in a saved register */
move a1, a0 /* move bootstring to the second argument */
move a0, s0 /* make _end the first argument */
jal strcpy /* call strcpy(_end, bootstring) */
nop /* delay slot */
move a0, s0 /* make _end the first argument again */
jal strlen /* call strlen(_end) */
nop
add t0, s0, v0 /* add in the length of the string */
addi t0, t0, 1 /* and the null terminator */
addi t0, t0, 4095 /* round up to next page boundary */
li t1, 0xfffff000
and t0, t0, t1
addi t0, t0, 4096 /* add one page to hold the stack */
move sp, t0 /* start the kernel stack for the first thread here */
sw t0, firstfree /* remember the first free page for later */
/*
* At this point, s0 contains the boot argument string, and no other
* registers contain anything interesting (except the stack pointer).
*/
/*
* Now set up a stack frame on the real kernel stack: a dummy saved
* return address and four argument slots for making function calls,
* plus a wasted slot for alignment.
*
* (This needs to match the stack frame set up at the top of the
* function, or the debugger gets confused.)
*/
addiu sp, sp, -24
sw $0, 20(sp)
/*
* Now, copy the exception handler code onto the first page of memory.
*/
li a0, EXADDR_UTLB
la a1, mips_utlb_handler
la a2, mips_utlb_end
sub a2, a2, a1
jal memmove
nop
li a0, EXADDR_GENERAL
la a1, mips_general_handler
la a2, mips_general_end
sub a2, a2, a1
jal memmove
nop
/*
* Flush the instruction cache to make sure the above changes show
* through to instruction fetch.
*/
jal mips_flushicache
nop
/*
* Initialize the TLB.
*/
jal tlb_reset
nop
/*
* Load NULL into the register we use for curthread.
*/
li s7, 0
/*
* Set up the status register.
*
* The MIPS has six hardware interrupt lines and two software interrupts.
* These are individually maskable in the status register. However, we
* don't use this feature (for simplicity) - we only use the master
* interrupt enable/disable flag in bit 0. So enable all of those bits
* now and forget about them.
*
* The BEV bit in the status register, if set, causes the processor to
* jump to a different set of hardwired exception handling addresses.
* This is so that the kernel's exception handling code can be loaded
* into RAM and that the boot ROM's exception handling code can be ROM.
* This flag is normally set at boot time, and we need to be sure to
* clear it.
*
* The KUo/IEo/KUp/IEp/KUc/IEc bits should all start at zero.
*
* We also want all the other random control bits (mostly for cache
* stuff) set to zero.
*
* Thus, the actual value we write is CST_IRQMASK.
*/
li t0, CST_IRQMASK /* get value */
mtc0 t0, c0_status /* set status register */
/*
* Load the CPU number into the PTBASE field of the CONTEXT
* register. This is necessary to read from cpustacks[] and
* cputhreads[] on trap entry from user mode. See further
* discussions elsewhere.
*
* Because the boot CPU is CPU 0, we can just send 0.
*/
mtc0 $0, c0_context
/*
* Load the GP register. This is a MIPS ABI feature; the GP
* register points to an address in the middle of the data segment,
* so data can be accessed relative to GP using one instruction
* instead of the two it takes to set up a full 32-bit address.
*/
la gp, _gp
/*
* We're all set up!
* Fetch the copy of the bootstring as the argument, and call main.
*/
jal kmain
move a0, s0 /* in delay slot */
/*
* kmain shouldn't return. panic.
* Loop back just in case panic returns too.
*/
1:
la a0, panicstr
jal panic
nop /* delay slot */
j 1b
nop /* delay slot */
.end __start
.rdata
panicstr:
.asciz "kmain returned\n"
/*
* CPUs started after the boot CPU come here.
*/
.text
.globl cpu_start_secondary
.type cpu_start_secondary,@function
.ent cpu_start_secondary
cpu_start_secondary:
/*
* When we get here our stack points to the CRAM area of the bus
* controller per-CPU space. This means we can, with a bit of
* caution, call C functions, but nothing very deeply nesting.
* However, we don't need to.
*
* The a0 register contains the value that was put in the second
* word of the CRAM area, which is the (software) cpu number for
* indexing cpustacks[]. None of the other registers contain
* anything useful.
*/
/*
* Stack frame. We save the return address register, even though
* it contains nothing useful. This is for gdb's benefit when it
* comes disassembling. We also need 16 bytes for making a call,
* and 4 bytes for alignment, so the total frame size is 24.
*
* Note that the frame here must match the frame we set up below
* when we switch stacks. Otherwise, gdb gets very confused.
*/
.frame sp, 24, $0 /* 24-byte sp-relative frame; return addr on stack */
.mask 0x80000000, -4 /* register 31 (ra) saved at (sp+24)-4 */
addiu sp, sp, -24
sw ra, 20(sp)
/*
* Fetch the stack out of cpustacks[].
*/
lui t0, %hi(cpustacks) /* load upper half of cpustacks base addr */
sll v0, a0, 2 /* get byte index for array (multiply by 4) */
addu t0, t0, v0 /* add it in */
lw sp, %lo(cpustacks)(t0) /* get the stack pointer */
/*
* Now fetch curthread out of cputhreads[].
*/
lui t0, %hi(cputhreads) /* load upper half of cpustacks base addr */
sll v0, a0, 2 /* get byte index for array (multiply by 4) */
addu t0, t0, v0 /* add it in */
lw s7, %lo(cputhreads)(t0) /* load curthread register */
/*
* Initialize the TLB.
*/
jal tlb_reset
nop
/*
* Set up the status register, as described above.
*/
li t0, CST_IRQMASK /* get value */
mtc0 t0, c0_status /* set status register */
/*
* Load the CPU number into the PTBASE field of the CONTEXT
* register, as described above.
*/
sll v0, a0, CTX_PTBASESHIFT
mtc0 v0, c0_context
/*
* Initialize the on-chip timer interrupt.
*
* This should be set to CPU_FREQUENCY/HZ, but we don't have either
* of those values here, so we'll arbitrarily set it to 100,000. It
* will get reset to the right thing after it first fires.
*/
li v0, 100000
mtc0 v0, c0_compare
/*
* Load the GP register.
*/
la gp, _gp
/*
* Set up a stack frame. Store zero into the return address slot so
* we show as the top of the stack.
*/
addiu sp, sp, -24
sw z0, 20(sp)
/*
* Off to MI code. Pass the cpu number as the argument; it's already
* in the a0 register.
*/
j cpu_hatch
nop /* delay slot for jump */
.end cpu_start_secondary

32
kern/conf/DUMBVM Normal file
View File

@ -0,0 +1,32 @@
# Kernel config file using dumbvm.
# This should be used until you have your own VM system.
include conf/conf.kern # get definitions of available options
debug # Compile with debug info.
#
# Device drivers for hardware.
#
device lamebus0 # System/161 main bus
device emu* at lamebus* # Emulator passthrough filesystem
device ltrace* at lamebus* # trace161 trace control device
device ltimer* at lamebus* # Timer device
device lrandom* at lamebus* # Random device
device lhd* at lamebus* # Disk device
device lser* at lamebus* # Serial port
#device lscreen* at lamebus* # Text screen (not supported yet)
#device lnet* at lamebus* # Network interface (not supported yet)
device beep0 at ltimer* # Abstract beep handler device
device con0 at lser* # Abstract console on serial port
#device con0 at lscreen* # Abstract console on screen (not supported)
device rtclock0 at ltimer* # Abstract realtime clock
device random0 at lrandom* # Abstract randomness device
#options net # Network stack (not supported)
options semfs # Semaphores for userland
options sfs # Always use the file system
#options netfs # You might write this as a project.
options dumbvm # Chewing gum and baling wire.

36
kern/conf/DUMBVM-OPT Normal file
View File

@ -0,0 +1,36 @@
# Kernel config file using dumbvm.
# This should be used until you have your own VM system.
#
# This config builds with optimization for performance testing.
#
include conf/conf.kern # get definitions of available options
#debug # Optimizing compile (no debug).
options noasserts # Disable assertions.
#
# Device drivers for hardware.
#
device lamebus0 # System/161 main bus
device emu* at lamebus* # Emulator passthrough filesystem
device ltrace* at lamebus* # trace161 trace control device
device ltimer* at lamebus* # Timer device
device lrandom* at lamebus* # Random device
device lhd* at lamebus* # Disk device
device lser* at lamebus* # Serial port
#device lscreen* at lamebus* # Text screen (not supported yet)
#device lnet* at lamebus* # Network interface (not supported yet)
device beep0 at ltimer* # Abstract beep handler device
device con0 at lser* # Abstract console on serial port
#device con0 at lscreen* # Abstract console on screen (not supported)
device rtclock0 at ltimer* # Abstract realtime clock
device random0 at lrandom* # Abstract randomness device
#options net # Network stack (not supported)
options semfs # Semaphores for userland
options sfs # Always use the file system
#options netfs # You might write this as a project.
options dumbvm # Chewing gum and baling wire.

33
kern/conf/GENERIC Normal file
View File

@ -0,0 +1,33 @@
# Kernel config file for an ordinary, generic kernel.
# This config file should be used once you start working on
# your own VM system.
include conf/conf.kern # get definitions of available options
debug # Compile with debug info.
#
# Device drivers for hardware.
#
device lamebus0 # System/161 main bus
device emu* at lamebus* # Emulator passthrough filesystem
device ltrace* at lamebus* # trace161 trace control device
device ltimer* at lamebus* # Timer device
device lrandom* at lamebus* # Random device
device lhd* at lamebus* # Disk device
device lser* at lamebus* # Serial port
#device lscreen* at lamebus* # Text screen (not supported yet)
#device lnet* at lamebus* # Network interface (not supported yet)
device beep0 at ltimer* # Abstract beep handler device
device con0 at lser* # Abstract console on serial port
#device con0 at lscreen* # Abstract console on screen (not supported)
device rtclock0 at ltimer* # Abstract realtime clock
device random0 at lrandom* # Abstract randomness device
#options net # Network stack (not supported)
options semfs # Semaphores for userland
options sfs # Always use the file system
#options netfs # You might write this as a project.
#options dumbvm # Use your own VM system now.

36
kern/conf/GENERIC-OPT Normal file
View File

@ -0,0 +1,36 @@
# Kernel config file for an ordinary, generic kernel.
# This config file should be used once you start working on
# your own VM system.
#
# This config builds with optimization for performance testing.
include conf/conf.kern # get definitions of available options
#debug # Optimizing compile (no debug).
options noasserts # Disable assertions.
#
# Device drivers for hardware.
#
device lamebus0 # System/161 main bus
device emu* at lamebus* # Emulator passthrough filesystem
device ltrace* at lamebus* # trace161 trace control device
device ltimer* at lamebus* # Timer device
device lrandom* at lamebus* # Random device
device lhd* at lamebus* # Disk device
device lser* at lamebus* # Serial port
#device lscreen* at lamebus* # Text screen (not supported yet)
#device lnet* at lamebus* # Network interface (not supported yet)
device beep0 at ltimer* # Abstract beep handler device
device con0 at lser* # Abstract console on serial port
#device con0 at lscreen* # Abstract console on screen (not supported)
device rtclock0 at ltimer* # Abstract realtime clock
device random0 at lrandom* # Abstract randomness device
#options net # Network stack (not supported)
options semfs # Semaphores for userland
options sfs # Always use the file system
#options netfs # You might write this as a project.
#options dumbvm # Use your own VM system now.

440
kern/conf/conf.kern Normal file
View File

@ -0,0 +1,440 @@
#
# Machine-independent kernel config definitions.
#
# The idea is that the files, options, and facilities in the system
# are declared by conf.kern and the various files it includes. Then a
# kernel config (such as ASST1, or GENERIC, or TEST, or whatever) is
# used to select options and facilities for a particular kernel build.
#
# To add new files to the system, you need to edit this file (or
# others like it) and rerun the config script.
#
# Note: when running the config script, be sure to be in the
# right directory (the same one this file is in) and run it as
# "./config", not just "config" - in the latter case you will
# probably get the host system's kernel config utility, which
# will likely make a mess and produce mysterious error messages.
#
# The documentation for the syntax of these files follows.
#
############################################################
#
# Kernel config file syntax:
#
# The syntax for including the system definition is:
#
# include conf.kern
#
# This should come first. This is because the system must be
# defined before you can do much else useful.
#
# You can also include other files using the same syntax.
#
#
# The syntax for turning on a kernel compile option is:
#
# options optname
#
# A previous "defoption" must have been seen first. See below
# for more information.
#
# The act of compiling with debug info is (has to be) handled
# specially, and is just "debug" without the "options".
#
#
# The syntax for turning on a device driver is:
#
# device foo%
# device foo% at bar%
#
# where the % is either a number or a star, which is treated as
# a wildcard. The first line enables a device foo that is not
# supposed to be "attached" to anything. The second line enables
# a device foo that is attached to a device bar. For more
# information about what this means, see below.
#
#
############################################################
#
# Kernel definition file syntax:
#
# Note: All source file names are relative to the top directory of the
# kernel source, that is, src/kern.
#
# The syntax for adding a regular source file is:
#
# [machine M | platform P] file sourcefile.c
#
# Such a file is always included automatically in every kernel
# built for machine M, or platform P, or all kernels.
#
#
# The syntax for defining optional source files is:
#
# defoption optname
# [machine M | platform P] optfile optname sourcefile.c
# [machine M | platform P] optofffile optname sourcefile.c
#
# "defoption" declares the name of a kernel option. These are
# then turned on by including "options optname" in a
# kernel config.
#
# Source files added with optfile are compiled in if the option
# specified is enabled. Source files added with optofffile are
# compiled in if the option specified is not enabled.
#
# Additionally, a file "opt-optname.h" is created in the compile
# directory, which defines a C preprocessor symbol OPT_OPTNAME.
# This symbol is #defined to either 0 or 1 in the logical way.
# Thus, you can have small bits of code that are enabled or
# disabled by particular options by writing constructs like
#
# #include "opt-foo.h"
# #if OPT_FOO
# code();
# #else
# other_code();
# #endif
#
# *** Be sure to use #if and not #ifdef - you want the value
# of the symbol.
# *** Be sure to remember to include the header file for the
# option - if you don't, cpp will silently assume it is 0,
# which can be quite frustrating.
#
# The defoption must be seen before any optional file
# declarations that use it.
#
#
# The syntax for defining device drivers is:
#
# defdevice devname sourcefile.c
# defattach devname% otherdevname% sourcefile.c
# pseudoattach devname%
#
# Declare a device driver and its "attachment(s)". (The device
# driver can then be selectively included or not included in any
# particular kernel by using the "device" statement in the
# kernel config file.)
#
# The specified source files are only compiled if the device
# is enabled.
#
# The % is either a specific number N, meaning "only the Nth
# such device can be attached this way", or a star (*), meaning
# "any such device can be attached this way".
#
# In OS/161, device drivers are conceptually organized into
# trees. This mimics the organization of real hardware, where
# several expansion cards are plugged into one bus and there
# might be several devices on each expansion card and so forth.
#
# There can be any number of these trees. However, devices at
# the root of each tree must be able to probe and "find"
# themselves completely on their own. This generally means that
# they are either all software with no hardware, or they are the
# system main bus which is located in a machine-dependent way.
#
# Software-only devices are known as "pseudo-devices". These
# are "attached" with the pseudoattach directive; functions
# of the form
#
# pseudoattach_devname
#
# are called from autoconf.c to create instances as requested.
# These calls are made from the function pseudoconfig(), which
# should be called from dev/init.c after hardware device
# initialization completes. The pseudoattach functions should
# perform all setup and initialization necessary. (No
# config_devname function will be called.)
#
# Devices with attachments are automatically probed and
# configured from code in autoconf.c. This file is generated
# by the config script. It contains functions called
# "autoconf_devname", for each device. These functions call
# other functions, which are supplied by device drivers,
# which have the following hardwired names:
#
# attach_devname1_to_devname2
#
# A "devname2" device has been found and configured;
# this function attempts to probe the devname2 for
# a "devname1" device. Returns NULL if nothing was
# found.
#
# config_devname
#
# A "devname" device has been found. This function
# can then perform initialization that's shared
# among all the possible things it can be attached
# to.
#
# The idea is that there can be multiple attachments for
# the same device to different underlying devices. In the
# real world this can be used to great effect when you have,
# for instance, the same ethernet chipset used on both PCI
# and ISA cards - the chipset behaves the same way in both
# cases, but the probe and attach logic is very different.
#
# The attach_foo_to_bar functions are put in the files
# specified with defattach; the config_foo function (and
# generally the rest of the driver for the foo device) is
# put in the file specified with defdevice.
#
# One selects particular attachments when including the device
# in the kernel. A top-level device with no attachments should
# be included with this syntax:
#
# device bar
#
# A pseudo-device should be included with this syntax:
#
# device bar0
#
# To make use of device foo, which can be found attached to
# device bar, one of the following syntaxes is used:
#
# device foo* at bar*
# device foo* at bar0
# device foo0 at bar*
# device foo0 at bar0
#
# depending on to what extent you want to configure only a
# specific device number.
#
# It sometimes matters what order things are handled in; probes
# occur more or less in the order things appear in the config,
# as constrained by the tree structure of the available devices.
#
# Note that OS/161 does not make extensive use of this
# functionality, and the device driver architecture outlined
# here is overkill for such a limited environment as System/161.
# However, it's similar to the way real systems are organized.
#
#
# The syntax for including other config/definition files is:
#
# include filename
#
# The filename is relative to the top of the kernel source tree.
#
# Thus,
# include conf/conf.foo includes src/kern/conf/conf.foo
#
#
############################################################
########################################
# #
# Generic machine-independent devices. #
# #
########################################
#
# These are abstract system services we expect the system hardware to
# provide: beeping, system console I/O, and time of day clock.
#
# These come before the archinclude so that the hardware device
# definitions, which are included from there, can define attachments
# for them.
#
defdevice beep dev/generic/beep.c
defdevice con dev/generic/console.c
defdevice rtclock dev/generic/rtclock.c
defdevice random dev/generic/random.c
########################################
# #
# Machine-dependent stuff #
# #
########################################
#
# Get the definitions for each machine and platform supported. The
# ones used will be selected by make at compile time based on the
# contents of the top-level defs.mk file.
#
# This will declare a bunch of machine-dependent source files and also
# declare all the hardware devices (since what sorts of hardware we
# expect to find is machine-dependent.)
#
include arch/mips/conf/conf.arch
include arch/sys161/conf/conf.arch
########################################
# #
# Support code #
# #
########################################
#
# Kernel utility code
#
file lib/array.c
file lib/bitmap.c
file lib/bswap.c
file lib/kgets.c
file lib/kprintf.c
file lib/misc.c
file lib/time.c
file lib/uio.c
defoption noasserts
#
# Standard C functions
#
# For most of these, we take the source files from our libc. Note
# that those files have to have been hacked a bit to support this.
#
file ../common/libc/printf/__printf.c
file ../common/libc/printf/snprintf.c
file ../common/libc/stdlib/atoi.c
file ../common/libc/string/bzero.c
file ../common/libc/string/memcpy.c
file ../common/libc/string/memmove.c
file ../common/libc/string/memset.c
file ../common/libc/string/strcat.c
file ../common/libc/string/strchr.c
file ../common/libc/string/strcmp.c
file ../common/libc/string/strcpy.c
file ../common/libc/string/strlen.c
file ../common/libc/string/strrchr.c
file ../common/libc/string/strtok_r.c
########################################
# #
# Core kernel source files #
# #
########################################
#
# Thread system
#
file thread/clock.c
file thread/spl.c
file thread/spinlock.c
file thread/synch.c
file thread/thread.c
file thread/threadlist.c
#
# Process system
#
file proc/proc.c
#
# Virtual memory system
# (you will probably want to add stuff here while doing the VM assignment)
#
file vm/kmalloc.c
optofffile dumbvm vm/addrspace.c
#
# Network
# (nothing here yet)
#
defoption net
#optfile net net/net.c
#
# VFS layer
#
file vfs/device.c
file vfs/vfscwd.c
file vfs/vfsfail.c
file vfs/vfslist.c
file vfs/vfslookup.c
file vfs/vfspath.c
file vfs/vnode.c
#
# VFS devices
#
file vfs/devnull.c
#
# System call layer
# (You will probably want to add stuff here while doing the basic system
# calls assignment.)
#
file syscall/loadelf.c
file syscall/runprogram.c
file syscall/time_syscalls.c
#
# Startup and initialization
#
file main/main.c
file main/menu.c
########################################
# #
# Filesystems #
# #
########################################
#
# semfs (fake filesystem providing userlevel semaphores)
#
defoption semfs
optfile semfs fs/semfs/semfs_fsops.c
optfile semfs fs/semfs/semfs_obj.c
optfile semfs fs/semfs/semfs_vnops.c
#
# sfs (the small/simple filesystem)
#
defoption sfs
optfile sfs fs/sfs/sfs_balloc.c
optfile sfs fs/sfs/sfs_bmap.c
optfile sfs fs/sfs/sfs_dir.c
optfile sfs fs/sfs/sfs_fsops.c
optfile sfs fs/sfs/sfs_inode.c
optfile sfs fs/sfs/sfs_io.c
optfile sfs fs/sfs/sfs_vnops.c
#
# netfs (the networked filesystem - you might write this as one assignment)
#
defoption netfs
#optfile netfs fs/netfs/netfs_fs.c # or whatever
#
# Note that "emufs" is completely contained in the "emu" device.
#
########################################
# #
# Test code #
# #
########################################
file test/arraytest.c
file test/bitmaptest.c
file test/threadlisttest.c
file test/threadtest.c
file test/tt3.c
file test/synchtest.c
file test/semunit.c
file test/kmalloctest.c
file test/fstest.c
optfile net test/nettest.c

1063
kern/conf/config Executable file

File diff suppressed because it is too large Load Diff

67
kern/conf/newvers.sh Executable file
View File

@ -0,0 +1,67 @@
#!/bin/sh
#
# newvers.sh - increment build number in current directory (a build directory)
# and emit vers.c.
# The build number is kept in the file "version".
#
# Usage: newvers.sh CONFIGNAME
#
# Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
# The President and Fellows of Harvard College.
#
# Redistribution and use in source and binary forms, with or without
# modification, are permitted provided that the following conditions
# are met:
# 1. Redistributions of source code must retain the above copyright
# notice, this list of conditions and the following disclaimer.
# 2. Redistributions in binary form must reproduce the above copyright
# notice, this list of conditions and the following disclaimer in the
# documentation and/or other materials provided with the distribution.
# 3. Neither the name of the University nor the names of its contributors
# may be used to endorse or promote products derived from this software
# without specific prior written permission.
#
# THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
# ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
# SUCH DAMAGE.
#
if [ ! -f autoconf.c ]; then
#
# If there's no file autoconf.c, we are in the wrong place.
#
echo "$0: Not in a kernel build directory"
exit 1
fi
if [ "x$1" = x ]; then
echo "Usage: $0 CONFIGNAME"
exit 1
fi
CONFIG="$1"
#
# Get and increment the version number
#
VERS=`cat version 2>/dev/null || echo 0`
VERS=`expr $VERS + 1`
echo "$VERS" > version
#
# Write vers.c
#
echo '/* This file is automatically generated. Edits will be lost.*/' > vers.c
echo "const int buildversion = $VERS;" >> vers.c
echo 'const char buildconfig[] = "'"$CONFIG"'";' >> vers.c

71
kern/dev/generic/beep.c Normal file
View File

@ -0,0 +1,71 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#include <types.h>
#include <kern/errno.h>
#include <lib.h>
#include <generic/beep.h>
#include "autoconf.h"
/*
* Machine-independent generic beep "device".
*
* Basically, all we do is remember something that can be used for
* beeping, and provide the beep() function to the rest of the kernel.
*
* The kernel config mechanism can be used to explicitly choose which
* of the available beeping devices to use, if more than one is
* available.
*/
static struct beep_softc *the_beep = NULL;
int
config_beep(struct beep_softc *bs, int unit)
{
/* We use only the first beep device. */
if (unit!=0) {
return ENODEV;
}
KASSERT(the_beep==NULL);
the_beep = bs;
return 0;
}
void
beep(void)
{
if (the_beep!=NULL) {
the_beep->bs_beep(the_beep->bs_devdata);
}
else {
kprintf("beep: Warning: no beep device\n");
}
}

43
kern/dev/generic/beep.h Normal file
View File

@ -0,0 +1,43 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifndef _GENERIC_BEEP_H_
#define _GENERIC_BEEP_H_
/*
* The device info for the generic MI beep device - a function
* to call and a context pointer for it.
*/
struct beep_softc {
void *bs_devdata;
void (*bs_beep)(void *devdata);
};
#endif /* _GENERIC_BEEP_H_ */

397
kern/dev/generic/console.c Normal file
View File

@ -0,0 +1,397 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* Machine (and hardware) independent console driver.
*
* We expose a simple interface to the rest of the kernel: "putch" to
* print a character, "getch" to read one.
*
* As long as the device we're connected to does, we allow printing in
* an interrupt handler or with interrupts off (by polling),
* transparently to the caller. Note that getch by polling is not
* supported, although such support could be added without undue
* difficulty.
*
* Note that nothing happens until we have a device to write to. A
* buffer of size DELAYBUFSIZE is used to hold output that is
* generated before this point. This means that (1) using kprintf for
* debugging problems that occur early in initialization is awkward,
* and (2) if the system crashes before we find a console, no output
* at all may appear.
*/
#include <types.h>
#include <kern/errno.h>
#include <lib.h>
#include <uio.h>
#include <cpu.h>
#include <thread.h>
#include <current.h>
#include <synch.h>
#include <generic/console.h>
#include <vfs.h>
#include <device.h>
#include "autoconf.h"
/*
* The console device.
*/
static struct con_softc *the_console = NULL;
/*
* Lock so user I/Os are atomic.
* We use two locks so readers waiting for input don't lock out writers.
*/
static struct lock *con_userlock_read = NULL;
static struct lock *con_userlock_write = NULL;
//////////////////////////////////////////////////
/*
* This is for accumulating characters printed before the
* console is set up. Upon console setup they are dumped
* to the actual console; thenceforth this space is unused.
*/
#define DELAYBUFSIZE 1024
static char delayed_outbuf[DELAYBUFSIZE];
static size_t delayed_outbuf_pos=0;
static
void
putch_delayed(int ch)
{
/*
* No synchronization needed: called only during system startup
* by main thread.
*/
KASSERT(delayed_outbuf_pos < sizeof(delayed_outbuf));
delayed_outbuf[delayed_outbuf_pos++] = ch;
}
static
void
flush_delay_buf(void)
{
size_t i;
for (i=0; i<delayed_outbuf_pos; i++) {
putch(delayed_outbuf[i]);
}
delayed_outbuf_pos = 0;
}
//////////////////////////////////////////////////
/*
* Print a character, using polling instead of interrupts to wait for
* I/O completion.
*/
static
void
putch_polled(struct con_softc *cs, int ch)
{
cs->cs_sendpolled(cs->cs_devdata, ch);
}
//////////////////////////////////////////////////
/*
* Print a character, using interrupts to wait for I/O completion.
*/
static
void
putch_intr(struct con_softc *cs, int ch)
{
P(cs->cs_wsem);
cs->cs_send(cs->cs_devdata, ch);
}
/*
* Read a character, using interrupts to wait for I/O completion.
*/
static
int
getch_intr(struct con_softc *cs)
{
unsigned char ret;
P(cs->cs_rsem);
ret = cs->cs_gotchars[cs->cs_gotchars_tail];
cs->cs_gotchars_tail =
(cs->cs_gotchars_tail + 1) % CONSOLE_INPUT_BUFFER_SIZE;
return ret;
}
/*
* Called from underlying device when a read-ready interrupt occurs.
*
* Note: if gotchars_head == gotchars_tail, the buffer is empty. Thus
* if gotchars_head+1 == gotchars_tail, the buffer is full. A slightly
* tidier way to implement this check (that avoids wasting a slot,
* too) would be with a second semaphore used with a nonblocking P,
* but we don't have that in OS/161.
*/
void
con_input(void *vcs, int ch)
{
struct con_softc *cs = vcs;
unsigned nexthead;
nexthead = (cs->cs_gotchars_head + 1) % CONSOLE_INPUT_BUFFER_SIZE;
if (nexthead == cs->cs_gotchars_tail) {
/* overflow; drop character */
return;
}
cs->cs_gotchars[cs->cs_gotchars_head] = ch;
cs->cs_gotchars_head = nexthead;
V(cs->cs_rsem);
}
/*
* Called from underlying device when a write-done interrupt occurs.
*/
void
con_start(void *vcs)
{
struct con_softc *cs = vcs;
V(cs->cs_wsem);
}
//////////////////////////////////////////////////
/*
* Exported interface.
*
* Warning: putch must work even in an interrupt handler or with
* interrupts disabled, and before the console is probed. getch need
* not, and does not.
*/
void
putch(int ch)
{
struct con_softc *cs = the_console;
if (cs==NULL) {
putch_delayed(ch);
}
else if (curthread->t_in_interrupt ||
curthread->t_curspl > 0 ||
curcpu->c_spinlocks > 0) {
putch_polled(cs, ch);
}
else {
putch_intr(cs, ch);
}
}
int
getch(void)
{
struct con_softc *cs = the_console;
KASSERT(cs != NULL);
KASSERT(!curthread->t_in_interrupt && curthread->t_iplhigh_count == 0);
return getch_intr(cs);
}
////////////////////////////////////////////////////////////
/*
* VFS interface functions
*/
static
int
con_eachopen(struct device *dev, int openflags)
{
(void)dev;
(void)openflags;
return 0;
}
static
int
con_io(struct device *dev, struct uio *uio)
{
int result;
char ch;
struct lock *lk;
(void)dev; // unused
if (uio->uio_rw==UIO_READ) {
lk = con_userlock_read;
}
else {
lk = con_userlock_write;
}
KASSERT(lk != NULL);
lock_acquire(lk);
while (uio->uio_resid > 0) {
if (uio->uio_rw==UIO_READ) {
ch = getch();
if (ch=='\r') {
ch = '\n';
}
result = uiomove(&ch, 1, uio);
if (result) {
lock_release(lk);
return result;
}
if (ch=='\n') {
break;
}
}
else {
result = uiomove(&ch, 1, uio);
if (result) {
lock_release(lk);
return result;
}
if (ch=='\n') {
putch('\r');
}
putch(ch);
}
}
lock_release(lk);
return 0;
}
static
int
con_ioctl(struct device *dev, int op, userptr_t data)
{
/* No ioctls. */
(void)dev;
(void)op;
(void)data;
return EINVAL;
}
static const struct device_ops console_devops = {
.devop_eachopen = con_eachopen,
.devop_io = con_io,
.devop_ioctl = con_ioctl,
};
static
int
attach_console_to_vfs(struct con_softc *cs)
{
struct device *dev;
int result;
dev = kmalloc(sizeof(*dev));
if (dev==NULL) {
return ENOMEM;
}
dev->d_ops = &console_devops;
dev->d_blocks = 0;
dev->d_blocksize = 1;
dev->d_data = cs;
result = vfs_adddev("con", dev, 0);
if (result) {
kfree(dev);
return result;
}
return 0;
}
////////////////////////////////////////////////////////////
/*
* Config routine called by autoconf.c after we are attached to something.
*/
int
config_con(struct con_softc *cs, int unit)
{
struct semaphore *rsem, *wsem;
struct lock *rlk, *wlk;
/*
* Only allow one system console.
* Further devices that could be the system console are ignored.
*
* Do not hardwire the console to be "con1" instead of "con0",
* or these asserts will go off.
*/
if (unit>0) {
KASSERT(the_console!=NULL);
return ENODEV;
}
KASSERT(the_console==NULL);
rsem = sem_create("console read", 0);
if (rsem == NULL) {
return ENOMEM;
}
wsem = sem_create("console write", 1);
if (wsem == NULL) {
sem_destroy(rsem);
return ENOMEM;
}
rlk = lock_create("console-lock-read");
if (rlk == NULL) {
sem_destroy(rsem);
sem_destroy(wsem);
return ENOMEM;
}
wlk = lock_create("console-lock-write");
if (wlk == NULL) {
lock_destroy(rlk);
sem_destroy(rsem);
sem_destroy(wsem);
return ENOMEM;
}
cs->cs_rsem = rsem;
cs->cs_wsem = wsem;
cs->cs_gotchars_head = 0;
cs->cs_gotchars_tail = 0;
the_console = cs;
con_userlock_read = rlk;
con_userlock_write = wlk;
flush_delay_buf();
return attach_console_to_vfs(cs);
}

View File

@ -0,0 +1,68 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifndef _GENERIC_CONSOLE_H_
#define _GENERIC_CONSOLE_H_
/*
* Device data for the hardware-independent system console.
*
* devdata, send, and sendpolled are provided by the underlying
* device, and are to be initialized by the attach routine.
*/
#define CONSOLE_INPUT_BUFFER_SIZE 32
struct con_softc {
/* initialized by attach routine */
void *cs_devdata;
void (*cs_send)(void *devdata, int ch);
void (*cs_sendpolled)(void *devdata, int ch);
/* initialized by config routine */
struct semaphore *cs_rsem;
struct semaphore *cs_wsem;
unsigned char cs_gotchars[CONSOLE_INPUT_BUFFER_SIZE];
unsigned cs_gotchars_head; /* next slot to put a char in */
unsigned cs_gotchars_tail; /* next slot to take a char out */
};
/*
* Functions called by lower-level drivers
*/
void con_input(/*struct con_softc*/ void *cs, int ch);
void con_start(/*struct con_softc*/ void *cs);
/*
* Functions called by higher-level code
*
* putch/getch - see <lib.h>
*/
#endif /* _GENERIC_CONSOLE_H_ */

158
kern/dev/generic/random.c Normal file
View File

@ -0,0 +1,158 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#include <types.h>
#include <kern/errno.h>
#include <kern/fcntl.h>
#include <lib.h>
#include <uio.h>
#include <vfs.h>
#include <generic/random.h>
#include "autoconf.h"
/*
* Machine-independent generic randomness device.
*
* Remembers something that's a random source, and provides random()
* and randmax() to the rest of the kernel.
*
* The kernel config mechanism can be used to explicitly choose which
* of the available random sources to use, if more than one is
* available.
*/
static struct random_softc *the_random = NULL;
/*
* VFS device functions.
* open: allow reading only.
*/
static
int
randeachopen(struct device *dev, int openflags)
{
(void)dev;
if (openflags != O_RDONLY) {
return EIO;
}
return 0;
}
/*
* VFS I/O function. Hand off to implementation.
*/
static
int
randio(struct device *dev, struct uio *uio)
{
struct random_softc *rs = dev->d_data;
if (uio->uio_rw != UIO_READ) {
return EIO;
}
return rs->rs_read(rs->rs_devdata, uio);
}
/*
* VFS ioctl function.
*/
static
int
randioctl(struct device *dev, int op, userptr_t data)
{
/*
* We don't support any ioctls.
*/
(void)dev;
(void)op;
(void)data;
return EIOCTL;
}
static const struct device_ops random_devops = {
.devop_eachopen = randeachopen,
.devop_io = randio,
.devop_ioctl = randioctl,
};
/*
* Config function.
*/
int
config_random(struct random_softc *rs, int unit)
{
int result;
/* We use only the first random device. */
if (unit!=0) {
return ENODEV;
}
KASSERT(the_random==NULL);
the_random = rs;
rs->rs_dev.d_ops = &random_devops;
rs->rs_dev.d_blocks = 0;
rs->rs_dev.d_blocksize = 1;
rs->rs_dev.d_data = rs;
/* Add the VFS device structure to the VFS device list. */
result = vfs_adddev("random", &rs->rs_dev, 0);
if (result) {
return result;
}
return 0;
}
/*
* Random number functions exported to the rest of the kernel.
*/
uint32_t
random(void)
{
if (the_random==NULL) {
panic("No random device\n");
}
return the_random->rs_random(the_random->rs_devdata);
}
uint32_t
randmax(void)
{
if (the_random==NULL) {
panic("No random device\n");
}
return the_random->rs_randmax(the_random->rs_devdata);
}

46
kern/dev/generic/random.h Normal file
View File

@ -0,0 +1,46 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifndef _GENERIC_RANDOM_H_
#define _GENERIC_RANDOM_H_
#include <device.h>
struct uio;
struct random_softc {
/* Initialized by lower-level attach routine */
void *rs_devdata;
uint32_t (*rs_random)(void *devdata);
uint32_t (*rs_randmax)(void *devdata);
int (*rs_read)(void *devdata, struct uio *uio);
struct device rs_dev;
};
#endif /* _GENERIC_RANDOM_H_ */

View File

@ -0,0 +1,70 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* Machine-independent generic clock "device".
*
* Basically, all we do is remember something that can be used for
* handling requests for the current time, and provide the gettime()
* function to the rest of the kernel.
*
* The kernel config mechanism can be used to explicitly choose which
* of the available clocks to use, if more than one is available.
*
* The system will panic if gettime() is called and there is no clock.
*/
#include <types.h>
#include <kern/errno.h>
#include <lib.h>
#include <clock.h>
#include <generic/rtclock.h>
#include "autoconf.h"
static struct rtclock_softc *the_clock = NULL;
int
config_rtclock(struct rtclock_softc *rtc, int unit)
{
/* We use only the first clock device. */
if (unit!=0) {
return ENODEV;
}
KASSERT(the_clock==NULL);
the_clock = rtc;
return 0;
}
void
gettime(struct timespec *ts)
{
KASSERT(the_clock!=NULL);
the_clock->rtc_gettime(the_clock->rtc_devdata, ts);
}

View File

@ -0,0 +1,45 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifndef _GENERIC_RTCLOCK_H_
#define _GENERIC_RTCLOCK_H_
/*
* The device info for the generic MI clock device - a function
* to call and a context pointer for it.
*/
struct timespec;
struct rtclock_softc {
void *rtc_devdata;
void (*rtc_gettime)(void *devdata, struct timespec *);
};
#endif /* _GENERIC_RTCLOCK_H_ */

View File

@ -0,0 +1,55 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* Attachment code for having the generic beep device use the LAMEbus
* ltimer device for beeping.
*/
#include <types.h>
#include <lib.h>
#include <generic/beep.h>
#include <lamebus/ltimer.h>
#include "autoconf.h"
struct beep_softc *
attach_beep_to_ltimer(int beepno, struct ltimer_softc *ls)
{
struct beep_softc *bs = kmalloc(sizeof(struct beep_softc));
if (bs==NULL) {
return NULL;
}
(void)beepno; // unused
bs->bs_devdata = ls;
bs->bs_beep = ltimer_beep;
return bs;
}

View File

@ -0,0 +1,59 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* Attachment code for having the generic console device use the LAMEbus
* screen device.
*/
#include <types.h>
#include <lib.h>
#include <generic/console.h>
#include <lamebus/lscreen.h>
#include "autoconf.h"
struct con_softc *
attach_con_to_lscreen(int consno, struct lscreen_softc *ls)
{
struct con_softc *cs = kmalloc(sizeof(struct con_softc));
if (cs==NULL) {
return NULL;
}
cs->cs_devdata = ls;
cs->cs_send = lscreen_write;
cs->cs_sendpolled = lscreen_write;
ls->ls_devdata = cs;
ls->ls_start = con_start;
ls->ls_input = con_input;
return cs;
}

View File

@ -0,0 +1,61 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
/*
* Attachment code for having the generic console device use the LAMEbus
* serial device.
*/
#include <types.h>
#include <lib.h>
#include <generic/console.h>
#include <lamebus/lser.h>
#include "autoconf.h"
struct con_softc *
attach_con_to_lser(int consno, struct lser_softc *ls)
{
struct con_softc *cs = kmalloc(sizeof(struct con_softc));
if (cs==NULL) {
return NULL;
}
(void)consno; // unused
cs->cs_devdata = ls;
cs->cs_send = lser_write;
cs->cs_sendpolled = lser_writepolled;
ls->ls_devdata = cs;
ls->ls_start = con_start;
ls->ls_input = con_input;
return cs;
}

View File

@ -0,0 +1,57 @@
#
# Kernel config definitions for LAMEbus devices.
#
# See conf/conf.kern for more information.
#
# System main bus.
defdevice lamebus dev/lamebus/lamebus.c
# Timer.
defdevice ltimer dev/lamebus/ltimer.c
defattach ltimer* lamebus* dev/lamebus/ltimer_att.c
# Random.
defdevice lrandom dev/lamebus/lrandom.c
defattach lrandom* lamebus* dev/lamebus/lrandom_att.c
# Disk.
defdevice lhd dev/lamebus/lhd.c
defattach lhd* lamebus* dev/lamebus/lhd_att.c
# Serial port.
defdevice lser dev/lamebus/lser.c
defattach lser* lamebus* dev/lamebus/lser_att.c
# Text screen.
defdevice lscreen dev/lamebus/lscreen.c
defattach lscreen* lamebus* dev/lamebus/lscreen_att.c
# Network interface.
defdevice lnet dev/lamebus/lnet.c
defattach lnet* lamebus* dev/lamebus/lnet_att.c
# Trace control device.
defdevice ltrace dev/lamebus/ltrace.c
defattach ltrace* lamebus* dev/lamebus/ltrace_att.c
# Emulator passthrough filesystem.
defdevice emu dev/lamebus/emu.c
defattach emu* lamebus* dev/lamebus/emu_att.c
#
# Attachments to generic interface devices
#
# Consoles.
defattach con0 lser* dev/lamebus/con_lser.c
defattach con0 lscreen* dev/lamebus/con_lscreen.c
# Beeper.
defattach beep* ltimer* dev/lamebus/beep_ltimer.c
# Clock.
defattach rtclock* ltimer* dev/lamebus/rtclock_ltimer.c
# Random.
defattach random0 lrandom* dev/lamebus/random_lrandom.c

1357
kern/dev/lamebus/emu.c Normal file

File diff suppressed because it is too large Load Diff

62
kern/dev/lamebus/emu.h Normal file
View File

@ -0,0 +1,62 @@
/*
* Copyright (c) 2000, 2001, 2002, 2003, 2004, 2005, 2008, 2009
* The President and Fellows of Harvard College.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. Neither the name of the University nor the names of its contributors
* may be used to endorse or promote products derived from this software
* without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE UNIVERSITY AND CONTRIBUTORS ``AS IS'' AND
* ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE UNIVERSITY OR CONTRIBUTORS BE LIABLE
* FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
* DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
* OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
* HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
* LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*/
#ifndef _LAMEBUS_EMU_H_
#define _LAMEBUS_EMU_H_
#define EMU_MAXIO 16384
#define EMU_ROOTHANDLE 0
/*
* The per-device data used by the emufs device driver.
* (Note that this is only a small portion of its actual data;
* all the filesystem stuff goes elsewhere.
*/
struct emu_softc {
/* Initialized by lower-level attach code */
void *e_busdata;
uint32_t e_buspos;
int e_unit;
/* Initialized by config_emu() */
struct lock *e_lock;
struct semaphore *e_sem;
void *e_iobuf;
/* Written by the interrupt handler */
uint32_t e_result;
};
/* Functions called by lower-level drivers */
void emu_irq(/*struct emu_softc*/ void *);
#endif /* _LAMEBUS_EMU_H_ */

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