? loader.stuff.diff Index: forth/loader.4th =================================================================== RCS file: /home/ncvs/src/sys/boot/forth/loader.4th,v retrieving revision 1.11 diff -u -p -r1.11 loader.4th --- forth/loader.4th 2000/09/08 21:11:57 1.11 +++ forth/loader.4th 2000/09/09 04:30:40 @@ -58,32 +58,6 @@ only forth definitions also support-func also support-functions definitions -: bootpath s" /boot/" ; -: modulepath s" module_path" ; - -: saveenv ( addr len | 0 -1 -- addr' len | 0 -1 ) - dup -1 = if exit then - dup allocate abort" Out of memory" - swap 2dup 2>r - move - 2r> -; - -: freeenv ( addr len | 0 -1 ) - -1 = if drop else free abort" Freeing error" then -; - -: restoreenv ( addr len | 0 -1 -- ) - dup -1 = if ( it wasn't set ) - 2drop - modulepath unsetenv - else - over >r - modulepath setenv - r> free abort" Freeing error" - then -; - : set-tempoptions ( addrN lenN ... addr1 len1 N -- addr len 1 | 0 ) \ No options, set the default ones dup 0= if @@ -166,105 +140,33 @@ also support-functions definitions also builtins -: load-kernel ( addr len -- addr len error? ) - s" temp_options" getenv dup -1 = if - drop 2dup 1 - else - 2over 2 - then - - 1 load -; - : load-conf ( args 1 | 0 "args" -- flag ) - 0 1 unload drop - 0= if ( interpreted ) get-arguments then set-tempoptions - - if ( there are arguments ) - load-kernel if ( load command failed ) - \ Set the environment variable module_path, and try loading - \ the kernel again. - - \ First, save module_path value - modulepath getenv saveenv dup -1 = if 0 swap then 2>r - - \ Sets the new value - 2dup modulepath setenv - - \ Try to load the kernel - s" load ${kernel} ${temp_options}" ['] evaluate catch - if ( load failed yet again ) - \ Remove garbage from the stack - 2drop - - \ Try prepending /boot/ - bootpath 2over nip over + allocate - if ( out of memory ) - 2drop 2drop - 2r> restoreenv - 100 exit - then - - 0 2swap strcat 2swap strcat - 2dup modulepath setenv - - drop free if ( freeing memory error ) - 2drop - 2r> restoreenv - 100 exit - then - - \ Now, once more, try to load the kernel - s" load ${kernel} ${temp_options}" ['] evaluate catch - if ( failed once more ) - 2drop - 2r> restoreenv - 100 exit - then - - else ( we found the kernel on the path passed ) - - 2drop ( discard command line arguments ) - - then ( could not load kernel from directory passed ) - - \ Load the remaining modules, if the kernel was loaded at all - ['] load_modules catch if 2r> restoreenv 100 exit then - - \ Return 0 to indicate success - 0 - - \ Keep new module_path - 2r> freeenv - - exit - then ( could not load kernel with name passed ) - - 2drop ( discard command line arguments ) - - else ( try just a straight-forward kernel load ) - s" load ${kernel} ${temp_options}" ['] evaluate catch - if ( kernel load failed ) 2drop 100 exit then - - then ( there are command line arguments ) - - \ Load the remaining modules, if the kernel was loaded at all - ['] load_modules catch if 100 exit then - - \ Return 0 to indicate success - 0 + s" temp_options" getenv -1 <> if 2swap 2 else 1 then + load_kernel_and_modules ; only forth also support-functions also builtins definitions : boot + \ Unload only if a path was passed + >in @ parse-word rot >in ! + if + c@ [char] - <> if + 0 1 unload drop + else + get-arguments 1 boot exit + then + else + 0 1 boot exit + then load-conf ?dup 0= if 0 1 boot then ; : boot-conf + 0 1 unload drop load-conf ?dup 0= if 0 1 autoboot then ; Index: forth/loader.conf =================================================================== RCS file: /home/ncvs/src/sys/boot/forth/loader.conf,v retrieving revision 1.31 diff -u -p -r1.31 loader.conf --- forth/loader.conf 2000/09/05 22:37:45 1.31 +++ forth/loader.conf 2000/09/09 04:30:41 @@ -43,10 +43,10 @@ bitmap_type="splash_image_data" ############################################################## #autoboot_delay="10" # Delay in seconds before autobooting -#bootfile="kernel,kernel.old" # Set the default boot file set +bootfile="kernel" # Set the default boot file set #console="vidconsole" # Set the current console #currdev="disk1s1a" # Set the current device -#module_path="/boot/modules;/modules;/boot/kernel" # Set the module search path +module_path="/boot/modules;/modules;/boot/kernel" # Set the module search path #prompt="\\${interpret}" # Set the command prompt #root_disk_unit="0" # Force the root disk unit number #rootdev="disk1s1a" # Set the root filesystem Index: forth/support.4th =================================================================== RCS file: /home/ncvs/src/sys/boot/forth/support.4th,v retrieving revision 1.6 diff -u -p -r1.6 support.4th --- forth/support.4th 2000/09/08 16:58:31 1.6 +++ forth/support.4th 2000/09/09 04:30:42 @@ -1218,17 +1218,288 @@ variable current_conf_files repeat ; -\ Additional functions used in "start" +\ h00h00 magic used to try loading either a kernel with a given name, +\ or a kernel with the default name in a directory of a given name +\ (the pain!) +: bootpath s" /boot/" ; +: modulepath s" module_path" ; + +\ Functions used to save and restore module_path's value. +: saveenv ( addr len | -1 -- addr' len | 0 -1 ) + ." saveenv" cr + dup -1 = if 0 swap exit then + strdup +; +: freeenv ( addr len | 0 -1 ) + ." freeenv" cr + -1 = if drop else free abort" Freeing error" then +; +: restoreenv ( addr len | 0 -1 -- ) + ." restoreenv" cr + dup -1 = if ( it wasn't set ) + 2drop + modulepath unsetenv + else + over >r + modulepath setenv + r> free abort" Freeing error" + then +; + +: clip_args \ Drop second string if only one argument is passed + ." clip_args" cr + 1 = if + 2swap 2drop + 1 + else + 2 + then +; + +also builtins + +\ Parse filename from a comma-separated list + +: parse-; ( addr len -- addr' len-x addr x ) + ." parse-" cr + over 0 2swap + begin + dup 0 <> + while + over c@ [char] ; <> + while + 1- swap 1+ swap + 2swap 1+ 2swap + repeat then + dup 0 <> if + 1- swap 1+ swap + then + 2swap +; + +\ Try loading one of multiple kernels specified + +: try_multiple_kernels ( addr len addr' len' args -- flag ) + ." try_multiple_kernels" cr + >r + begin + parse-; 2>r + 2over 2r> + r@ clip_args 1 load + while + dup 0= + until + 1 >r \ Failure + else + 0 >r \ Success + then + 2drop 2drop + r> + r> drop +; + +\ Try to load a kernel; the kernel name is taken from one of +\ the following lists, as ordered: +\ +\ 1. The "kernel" environment variable +\ 2. The "bootfile" environment variable +\ +\ Flags are passed, if available. The parameter args must be 2 +\ if flags are being passed, or 1 if they should be ignored. +\ Dummy flags and len must be passed in the latter case. +\ +\ The kernel gets loaded from the current module_path. + +: load_a_kernel ( flags len args -- flag ) + ." load_a_kernel" cr + local args + 2local flags + 0 0 2local kernel + end-locals + + \ Check if a default kernel name exists at all, exits if not + s" kernel" getenv dup -1 <> if + to kernel + flags kernel args try_multiple_kernels + dup 0= if exit then + then + drop + + s" bootfile" getenv dup -1 <> if + to kernel + else + drop + 1 exit \ Failure + then + + \ Try all default kernel names + flags kernel args try_multiple_kernels +; + +\ Try to load a kernel; the kernel name is taken from one of +\ the following lists, as ordered: +\ +\ 1. The "kernel" environment variable +\ 2. The "bootfile" environment variable +\ +\ Flags are passed, if provided. +\ +\ The kernel will be loaded from a directory computed from the +\ path given. Two directories will be tried in the following order: +\ +\ 1. /boot/path +\ 2. path +\ +\ The module_path variable is overridden if load is succesful, by +\ prepending the successful path. + +: load_from_directory ( path len 1 | flags len' path len 2 -- flag ) + ." load_from_directory" cr + local args + 2local path + args 1 = if 0 0 then + 2local flags + 0 0 2local oldmodulepath + 0 0 2local newmodulepath + end-locals + + \ Set the environment variable module_path, and try loading + \ the kernel again. + modulepath getenv saveenv to oldmodulepath + + \ Try prepending /boot/ first + bootpath nip path nip + + oldmodulepath nip dup -1 = if + drop + else + 1+ + + then + allocate + if ( out of memory ) + 1 exit + then + + 0 + bootpath strcat + path strcat + 2dup to newmodulepath + modulepath setenv + + \ Try all default kernel names + flags args load_a_kernel + 0= if ( success ) + oldmodulepath nip -1 <> if + newmodulepath s" ;" strcat + oldmodulepath strcat + modulepath setenv + newmodulepath drop free-memory + oldmodulepath drop free-memory + then + 0 exit + then + + \ Well, try without the prepended /boot/ + path newmodulepath drop swap move + path nip + 2dup to newmodulepath + modulepath setenv + + \ Try all default kernel names + flags args load_a_kernel + if ( failed once more ) + oldmodulepath restoreenv + newmodulepath drop free-memory + 1 + else + oldmodulepath nip -1 <> if + newmodulepath s" ;" strcat + oldmodulepath strcat + modulepath setenv + newmodulepath drop free-memory + oldmodulepath drop free-memory + then + 0 + then +; + +\ Try to load a kernel; the kernel name is taken from one of +\ the following lists, as ordered: +\ +\ 1. The "kernel" environment variable +\ 2. The "bootfile" environment variable +\ 3. The "path" argument +\ +\ Flags are passed, if provided. +\ +\ The kernel will be loaded from a directory computed from the +\ path given. Two directories will be tried in the following order: +\ +\ 1. /boot/path +\ 2. path +\ +\ Unless "path" is meant to be kernel name itself. In that case, it +\ will first be tried as a full path, and, next, search on the +\ directories pointed by module_path. +\ +\ The module_path variable is overridden if load is succesful, by +\ prepending the successful path. + +: load_directory_or_file ( path len 1 | flags len' path len 2 -- flag ) + local args + 2local path + args 1 = if 0 0 then + 2local flags + end-locals + + \ First, assume path is an absolute path to a directory + flags path args clip_args load_from_directory + dup 0= if exit else drop then + + \ Next, assume path points to the kernel + flags path args try_multiple_kernels +; + +: load_kernel_and_modules ( flags len path len' 2 | path len' 1 -- flag ) + load_directory_or_file + 0= if ['] load_modules catch then +; + : initialize ( addr len -- ) strdup conf_files .len ! conf_files .addr ! ; -: load_kernel ( -- ) ( throws: abort ) - s" load ${kernel} ${kernel_options}" ['] evaluate catch - if s" echo Unable to load kernel: ${kernel}" evaluate abort then +: kernel_options ( -- addr len 2 | 0 0 1 ) + ." kernel_options" cr + s" kernel_options" getenv + dup -1 = if 0 0 1 else 2 then +; + +: kernel_and_options + ." kernel_and_options" cr + kernel_options + s" kernel" getenv + rot ; +: load_kernel ( -- ) ( throws: abort ) + ." load_kernel" cr + s" kernel" getenv + dup -1 = if + \ If unset, try any kernel + drop + kernel_options load_a_kernel + else + \ If set, try first directory, next file name + kernel_options >r 2swap r> clip_args load_from_directory + dup if + drop + kernel_and_options try_multiple_kernels + then + then + abort" Unable to load a kernel!" +; + : read-password { size | buf len -- } size allocate if out_of_memory throw then to buf