#! /tclkit
proc load_modules {path} {
set modules [list]
catch {
set fd [open [file join $path load]]
set modules [split [read $fd] "\n"]
close $fd
}
foreach module $modules {
if {![file exists $module]} {
puts stderr "\[module\] File not found: $module"
continue
}
if {[catch {
system::syscall::insmod $module
} err]} {
puts stderr "\[module\] Failed to load $module: $err"
}
}
}
proc locate_config_partition {} {
foreach dev [glob -nocomplain /dev/*] {
unset -nocomplain devinfo
catch {
file stat $dev devinfo
}
if {![info exists devinfo(type)]} {
continue
}
if {$devinfo(type) != "blockSpecial"} {
continue
}
unset -nocomplain fd
catch {
set fd [open $dev]
fconfigure $fd -translation binary
}
if {![info exists fd]} {
continue
}
set magic [read $fd 32]
binary scan $magic H* magic
if {$magic != "1daa459b9772ef5d7d58c814458246c69dbd1d53fa75f396462910250bf7a4b6"} {
continue
}
return $dev
}
return ""
}
proc boot {} {
package require system
# 1. Load kernel modules
load_modules /modules
# 2. Mount devfs
file mkdir /dev
system::syscall::mount devfs /dev devtmpfs [list]
# 3. Locate Config partition
set dev [locate_config_partition]
if {$dev == ""} {
## XXX: Install to tmpfs
## XXX: Offer to do installation
} else {
# 4. Mount config partition
mount_config_partition $dev /config
# 5. Load kernel modules
load_modules /config/modules
# 5. Mount /system (from fstab)
## XXX: TODO
}
# 6. Mount /system/config and populate
catch {
file mkdir /system/config
}
system::syscall::mount tmpfs /system/config tmpfs [list]
# 7. Unmount devfs
system::syscall::umount /dev
file delete -force /dev
vfs::cvfs::Unmount /tclkit
file delete -force /init /root /tclkit /modules
# 8. Pass control to later boot init
if {![file exists /system/apps/appbox-core/default/sbin/init]} {
return -code error "No init found, aborting boot."
}
system::syscall::execve init /system/apps/appbox-core/default/sbin/init
}
if {[catch {
boot
} err]} {
puts stderr "\[boot\] Boot failed: $err"
}
while 1 {
puts -nonewline "> "
flush stdout
gets stdin line
if {[catch {
set ret [eval $line]
} err]} {
set ret $err
}
if {$ret != ""} {
puts $ret
}
}