mirror of
https://github.com/genodelabs/genode.git
synced 2025-02-21 10:01:57 +00:00
Sculpt for The Curious (TC)
This commit updates Early-Adopters (EA) version of Sculpt to the version for The Curious (TC). Most importantly, it contains the new interactive sculpt-manager component that automates many system management and configuration tasks.
This commit is contained in:
parent
5d5756d0cb
commit
3dd81b0d32
@ -8,6 +8,7 @@
|
||||
<rom label="libc.lib.so"/>
|
||||
<rom label="libm.lib.so"/>
|
||||
<rom label="vfs_ttf.lib.so"/>
|
||||
<rom label="Vera.ttf"/>
|
||||
<rom label="VeraMono.ttf"/>
|
||||
<rom label="vfs.lib.so"/>
|
||||
</content>
|
||||
|
@ -10,12 +10,8 @@ _/src/fs_report
|
||||
_/src/nitpicker
|
||||
_/src/global_keys_handler
|
||||
_/src/nit_fb
|
||||
_/src/nit_focus
|
||||
_/src/nit_fader
|
||||
_/src/rtc_drv
|
||||
_/src/top
|
||||
_/src/trace_subject_reporter
|
||||
_/src/cpu_load_display
|
||||
_/src/rom_filter
|
||||
_/src/terminal_log
|
||||
_/src/file_terminal
|
||||
@ -36,8 +32,15 @@ _/src/curl
|
||||
_/src/libssh
|
||||
_/src/zlib
|
||||
_/src/log_core
|
||||
_/src/depot_deploy
|
||||
_/src/part_blk
|
||||
_/src/nic_router
|
||||
_/src/e2fsprogs-minimal
|
||||
_/src/nvme_drv
|
||||
_/src/wm
|
||||
_/src/themed_decorator
|
||||
_/src/floating_window_layouter
|
||||
_/src/libpng
|
||||
_/src/zlib
|
||||
_/src/menu_view
|
||||
_/src/gpt_write
|
||||
_/src/sculpt_manager
|
||||
|
10
repos/gems/recipes/src/sculpt_manager/content.mk
Normal file
10
repos/gems/recipes/src/sculpt_manager/content.mk
Normal file
@ -0,0 +1,10 @@
|
||||
SRC_DIR := src/app/sculpt_manager
|
||||
|
||||
include $(GENODE_DIR)/repos/base/recipes/src/content.inc
|
||||
|
||||
MIRROR_FROM_REP_DIR := include/depot src/app/depot_deploy
|
||||
|
||||
content: $(MIRROR_FROM_REP_DIR)
|
||||
|
||||
$(MIRROR_FROM_REP_DIR):
|
||||
$(mirror_from_rep_dir)
|
1
repos/gems/recipes/src/sculpt_manager/hash
Normal file
1
repos/gems/recipes/src/sculpt_manager/hash
Normal file
@ -0,0 +1 @@
|
||||
2018-05-30-b 63bc6b2712d5fe8eccfc797b1c4062b2bd3fd01e
|
14
repos/gems/recipes/src/sculpt_manager/used_apis
Normal file
14
repos/gems/recipes/src/sculpt_manager/used_apis
Normal file
@ -0,0 +1,14 @@
|
||||
base
|
||||
os
|
||||
report_session
|
||||
file_system_session
|
||||
nic_session
|
||||
timer_session
|
||||
block_session
|
||||
usb_session
|
||||
framebuffer_session
|
||||
platform_session
|
||||
nitpicker_session
|
||||
terminal_session
|
||||
rtc_session
|
||||
input_session
|
@ -48,6 +48,10 @@ install_config {
|
||||
<resource name="RAM" quantum="64M" constrain_phys="yes"/>
|
||||
<binary name="init"/>
|
||||
<route>
|
||||
<service name="ROM" label_last="managed/input_filter">
|
||||
<parent label="input_filter.config"/> </service>
|
||||
<service name="ROM" label_last="numlock_remap">
|
||||
<parent label="numlock_remap.config"/> </service>
|
||||
<service name="ROM" label="config"> <parent label="drivers.config"/> </service>
|
||||
<service name="ROM" label="capslock"> <child name="dynamic_rom"/> </service>
|
||||
<service name="ROM" label="numlock"> <child name="dynamic_rom"/> </service>
|
||||
|
334
repos/gems/run/leitzentrale.run
Normal file
334
repos/gems/run/leitzentrale.run
Normal file
@ -0,0 +1,334 @@
|
||||
create_boot_directory
|
||||
|
||||
proc depot_user {} { return [get_cmd_arg --depot-user genodelabs] }
|
||||
|
||||
import_from_depot [depot_user]/src/[base_src] \
|
||||
[depot_user]/pkg/[drivers_interactive_pkg] \
|
||||
[depot_user]/pkg/fonts_fs \
|
||||
[depot_user]/src/dynamic_rom \
|
||||
[depot_user]/src/report_rom \
|
||||
[depot_user]/src/fs_rom \
|
||||
[depot_user]/src/fs_report \
|
||||
[depot_user]/src/ram_fs \
|
||||
[depot_user]/src/nitpicker \
|
||||
[depot_user]/src/init \
|
||||
[depot_user]/src/libc \
|
||||
[depot_user]/src/wm \
|
||||
[depot_user]/src/themed_decorator \
|
||||
[depot_user]/src/nit_fb \
|
||||
[depot_user]/src/nit_fader \
|
||||
[depot_user]/src/libpng \
|
||||
[depot_user]/src/zlib \
|
||||
[depot_user]/src/menu_view \
|
||||
[depot_user]/src/rom_filter \
|
||||
[depot_user]/src/noux \
|
||||
[depot_user]/src/terminal \
|
||||
[depot_user]/src/posix \
|
||||
[depot_user]/src/ram_blk \
|
||||
[depot_user]/src/part_blk \
|
||||
[depot_user]/src/rump \
|
||||
[depot_user]/src/ncurses \
|
||||
[depot_user]/src/usb_block_drv \
|
||||
[depot_user]/src/bash-minimal \
|
||||
[depot_user]/src/vim-minimal \
|
||||
[depot_user]/src/coreutils-minimal \
|
||||
[depot_user]/src/e2fsprogs-minimal \
|
||||
[depot_user]/src/gpt_write \
|
||||
[depot_user]/src/floating_window_layouter
|
||||
|
||||
install_config {
|
||||
<config>
|
||||
<parent-provides>
|
||||
<service name="ROM"/>
|
||||
<service name="IRQ"/>
|
||||
<service name="IO_MEM"/>
|
||||
<service name="IO_PORT"/>
|
||||
<service name="PD"/>
|
||||
<service name="RM"/>
|
||||
<service name="CPU"/>
|
||||
<service name="LOG"/>
|
||||
</parent-provides>
|
||||
|
||||
<resource name="RAM" preserve="2M"/>
|
||||
|
||||
<default-route>
|
||||
<any-service> <parent/> <any-child/> </any-service>
|
||||
</default-route>
|
||||
<default caps="100"/>
|
||||
|
||||
<start name="timer">
|
||||
<resource name="RAM" quantum="1M"/>
|
||||
<provides> <service name="Timer"/> </provides>
|
||||
</start>
|
||||
|
||||
<start name="drivers" caps="1000">
|
||||
<resource name="RAM" quantum="32M" constrain_phys="yes"/>
|
||||
<binary name="init"/>
|
||||
<route>
|
||||
<service name="ROM" label="config"> <parent label="drivers.config"/> </service>
|
||||
<service name="Timer"> <child name="timer"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
<provides>
|
||||
<service name="Input"/> <service name="Framebuffer"/>
|
||||
</provides>
|
||||
</start>
|
||||
|
||||
<start name="report_rom">
|
||||
<binary name="report_rom"/>
|
||||
<resource name="RAM" quantum="2M"/>
|
||||
<provides> <service name="Report"/> <service name="ROM"/> </provides>
|
||||
<config verbose="no">
|
||||
<policy label="leitzentrale -> manager -> nitpicker_hover"
|
||||
report="nitpicker -> hover"/>
|
||||
<policy label="leitzentrale -> manager -> displays"
|
||||
report="nitpicker -> displays"/>
|
||||
</config>
|
||||
</start>
|
||||
|
||||
<start name="nitpicker">
|
||||
<resource name="RAM" quantum="4M"/>
|
||||
<provides><service name="Nitpicker"/></provides>
|
||||
<config focus="rom">
|
||||
<report hover="yes" displays="yes"/>
|
||||
<background color="#000000"/>
|
||||
<domain name="pointer" layer="1" content="client" label="no" origin="pointer" />
|
||||
<domain name="default" layer="3" content="client" label="no" hover="always" />
|
||||
|
||||
<policy label_prefix="pointer" domain="pointer"/>
|
||||
<default-policy domain="default"/>
|
||||
</config>
|
||||
<route>
|
||||
<service name="Report"> <child name="report_rom"/> </service>
|
||||
<any-service> <parent/> <any-child/></any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="pointer">
|
||||
<resource name="RAM" quantum="1M"/>
|
||||
<route>
|
||||
<service name="Nitpicker"> <child name="nitpicker" /> </service>
|
||||
<any-service> <parent/> <any-child/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="config_fs">
|
||||
<binary name="ram_fs"/>
|
||||
<resource name="RAM" quantum="4M"/>
|
||||
<provides> <service name="File_system"/> </provides>
|
||||
<config>
|
||||
<content>
|
||||
<dir name="managed">
|
||||
<rom name="fonts.config" as="fonts"/>
|
||||
<inline name="runtime"><config/></inline>
|
||||
<inline name="depot_query"><query/></inline>
|
||||
</dir>
|
||||
<inline name="deploy"></inline>
|
||||
</content>
|
||||
<default-policy root="/" writeable="yes"/>
|
||||
</config>
|
||||
</start>
|
||||
|
||||
<start name="config_rom">
|
||||
<resource name="RAM" quantum="1M"/>
|
||||
<binary name="fs_rom"/>
|
||||
<provides> <service name="ROM"/> </provides>
|
||||
<config/>
|
||||
<route>
|
||||
<service name="File_system"> <child name="config_fs"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="report_fs">
|
||||
<binary name="ram_fs"/>
|
||||
<resource name="RAM" quantum="4M"/>
|
||||
<provides> <service name="File_system"/> </provides>
|
||||
<config>
|
||||
<default-policy root="/" writeable="yes"/>
|
||||
</config>
|
||||
</start>
|
||||
|
||||
<start name="fs_report">
|
||||
<resource name="RAM" quantum="1M"/>
|
||||
<provides> <service name="Report"/> </provides>
|
||||
<config> <vfs> <fs/> </vfs> </config>
|
||||
<route>
|
||||
<service name="File_system"> <child name="report_fs"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="report_fs_rom">
|
||||
<resource name="RAM" quantum="1M"/>
|
||||
<binary name="fs_rom"/>
|
||||
<provides> <service name="ROM"/> </provides>
|
||||
<config/>
|
||||
<route>
|
||||
<service name="File_system"> <child name="report_fs"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="leitzentrale_config">
|
||||
<binary name="rom_filter"/>
|
||||
<resource name="RAM" quantum="1M"/>
|
||||
<provides><service name="ROM"/></provides>
|
||||
<route>
|
||||
<service name="ROM" label="config">
|
||||
<parent label="leitzentrale.config"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="usb_active_config_rom">
|
||||
<binary name="dynamic_rom"/>
|
||||
<resource name="RAM" quantum="4M"/>
|
||||
<provides> <service name="ROM"/> </provides>
|
||||
<config>
|
||||
<rom name="usb_active_config">
|
||||
<inline description="USB storage present">
|
||||
<config>
|
||||
<raw> <policy label_suffix="usb-1-2" class="storage"/> </raw>
|
||||
</config>
|
||||
</inline>
|
||||
<sleep milliseconds="5000" />
|
||||
<inline description="USB storage absent">
|
||||
<config/>
|
||||
</inline>
|
||||
<sleep milliseconds="500000" />
|
||||
</rom>
|
||||
</config>
|
||||
</start>
|
||||
|
||||
<start name="ahci-1">
|
||||
<binary name="lx_block"/>
|
||||
<resource name="RAM" quantum="2M"/>
|
||||
<provides> <service name="Block"/> </provides>
|
||||
<config file="ahci-1.img" block_size="512" writeable="yes"/>
|
||||
</start>
|
||||
|
||||
<start name="ahci-2">
|
||||
<binary name="ram_blk"/>
|
||||
<resource name="RAM" quantum="10M"/>
|
||||
<config nofile="ahci-1.img" size="8M" block_size="512"/>
|
||||
<provides> <service name="Block"/> </provides>
|
||||
</start>
|
||||
|
||||
<start name="leitzentrale" caps="4000">
|
||||
<binary name="init"/>
|
||||
<resource name="RAM" quantum="128M"/>
|
||||
<provides> <service name="Nitpicker"/> </provides>
|
||||
<route>
|
||||
<service name="ROM" label="config">
|
||||
<child name="leitzentrale_config"/> </service>
|
||||
<service name="ROM" label_prefix="manager -> config -> ">
|
||||
<child name="config_rom"/> </service>
|
||||
<service name="Nitpicker"> <child name="nitpicker"/> </service>
|
||||
<service name="Timer"> <child name="timer"/> </service>
|
||||
<service name="File_system" label="config">
|
||||
<child name="config_fs" label="rw"/> </service>
|
||||
<service name="File_system" label="report">
|
||||
<child name="report_fs" label="rw"/> </service>
|
||||
<service name="Report"> <child name="fs_report"/> </service>
|
||||
<service name="ROM" label_last="drivers/block_devices">
|
||||
<parent label="block_devices"/> </service>
|
||||
<service name="ROM" label_last="drivers/usb_active_config">
|
||||
<child name="usb_active_config_rom" label="usb_active_config"/> </service>
|
||||
<service name="ROM" label_last="runtime/state">
|
||||
<child name="report_fs_rom" label="runtime/state"/> </service>
|
||||
<service name="ROM" label_last="deploy">
|
||||
<child name="config_rom"/> </service>
|
||||
<service name="ROM" label_last="managed/fonts">
|
||||
<child name="config_rom" label="managed/fonts"/> </service>
|
||||
<service name="ROM" label_prefix="manager -> report">
|
||||
<child name="report_fs_rom"/> </service>
|
||||
<service name="ROM" label="manager -> nitpicker_hover">
|
||||
<child name="report_rom"/> </service>
|
||||
<service name="ROM" label="manager -> displays">
|
||||
<child name="report_rom"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="runtime" caps="50000">
|
||||
<binary name="init"/>
|
||||
<resource name="RAM" quantum="1G"/>
|
||||
<route>
|
||||
<service name="ROM" label="config">
|
||||
<child name="config_rom" label="managed/runtime"/> </service>
|
||||
<service name="ROM" label_prefix="config -> ">
|
||||
<child name="config_rom"/> </service>
|
||||
<service name="File_system" label="config">
|
||||
<child name="config_fs" label="rw"/> </service>
|
||||
<service name="File_system" label="report">
|
||||
<child name="report_fs" label="ro"/> </service>
|
||||
<service name="Block" label_last="ahci-1"> <child name="ahci-1"/> </service>
|
||||
<service name="Block" label_last="ahci-2"> <child name="ahci-2"/> </service>
|
||||
<service name="Block"> <child name="drivers"/> </service>
|
||||
<service name="Usb"> <child name="drivers"/> </service>
|
||||
<service name="Nitpicker" label_prefix="leitzentrale">
|
||||
<child name="leitzentrale"/> </service>
|
||||
<service name="Nitpicker"> <child name="nitpicker"/> </service>
|
||||
<service name="Timer"> <child name="timer"/> </service>
|
||||
<service name="Report"> <child name="fs_report"/> </service>
|
||||
<service name="Report"> <child name="fs_report"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
</config>}
|
||||
|
||||
file copy -force [genode_dir]/repos/gems/recipes/raw/fonts_fs/fonts_fs.config [run_dir]/genode/fonts.config
|
||||
file copy -force [genode_dir]/repos/gems/run/sculpt/leitzentrale.config [run_dir]/genode/
|
||||
file copy -force [genode_dir]/repos/gems/run/sculpt/vimrc [run_dir]/genode/
|
||||
file copy -force [genode_dir]/repos/gems/src/app/backdrop/genode_logo.png [run_dir]/genode/
|
||||
|
||||
proc install_rom_module { name content } {
|
||||
set fd [open [run_dir]/genode/$name w]
|
||||
puts $fd $content
|
||||
close $fd
|
||||
}
|
||||
|
||||
# generate disk image with GPT partition table
|
||||
proc ahci_1_img { } { return "bin/ahci-1.img" }
|
||||
|
||||
catch { exec dd if=/dev/zero of=[ahci_1_img] bs=1M count=10 }
|
||||
exec parted -a none -s [ahci_1_img] -- mklabel gpt \
|
||||
mkpart BOOT fat32 256s 1023s \
|
||||
mkpart GRUB fat32 1024s 1279s \
|
||||
mkpart GENODE ext2 1280s 3700s
|
||||
|
||||
install_rom_module focus {<focus label="leitzentrale -> manager -> fader -> "/>}
|
||||
install_rom_module leitzentrale {<leitzentrale enabled="yes"/>}
|
||||
install_rom_module reset {<reset enabled="no"/>}
|
||||
install_rom_module README {nothing to read here}
|
||||
install_rom_module VERSION {unknown version}
|
||||
|
||||
install_rom_module block_devices {
|
||||
<block_devices>
|
||||
<device label="ahci-1" block_count="123" block_size="1024" model="Model"/>
|
||||
<device label="ahci-2" block_count="123" block_size="1024" model="Broken"/>
|
||||
</block_devices>}
|
||||
|
||||
install_rom_module usb_active_config {
|
||||
<config>
|
||||
<raw> <policy label_suffix="usb-1-2" class="storage"/> </raw>
|
||||
</config>}
|
||||
|
||||
build { server/lx_block app/menu_view app/sculpt_manager }
|
||||
|
||||
build_boot_image { lx_block menu_view sculpt_manager ahci-1.img }
|
||||
|
||||
if {[have_spec linux]} {
|
||||
set max_fds [exec bash -c "ulimit -n"]
|
||||
if {$max_fds < 4096} {
|
||||
puts stderr "\nMaximum number of file descriptors is too low for this run script."
|
||||
puts stderr "You may use the following command to increase the limit:\n"
|
||||
puts stderr " ulimit -n 4096\n"
|
||||
exit 1
|
||||
}
|
||||
}
|
||||
|
||||
run_genode_until forever
|
||||
|
@ -11,16 +11,9 @@ import_from_depot [depot_user]/src/[base_src] \
|
||||
[depot_user]/pkg/sculpt
|
||||
|
||||
proc config_system_content {} { return {\
|
||||
<!-- set 'state' value to "reset" to reboot the machine -->
|
||||
<system state=""/>} }
|
||||
|
||||
|
||||
proc config_trace_subject_reporter_content {} { return {\
|
||||
<config period_ms="2000">
|
||||
<report activity="yes" affinity="yes"/>
|
||||
</config>} }
|
||||
|
||||
|
||||
install_config {
|
||||
<config prio_levels="4"> <!-- set prio_levels to 4 -->
|
||||
<parent-provides>
|
||||
@ -48,21 +41,6 @@ install_config {
|
||||
<provides><service name="Timer"/></provides>
|
||||
</start>
|
||||
|
||||
<start name="top">
|
||||
<resource name="RAM" quantum="2M"/>
|
||||
<config period_ms="60000"/>
|
||||
</start>
|
||||
|
||||
<start name="trace_subject_reporter" >
|
||||
<resource name="RAM" quantum="24M"/>
|
||||
<route>
|
||||
<service name="ROM" label="config">
|
||||
<child name="config_rom" label="trace_subject_reporter.config"/> </service>
|
||||
<service name="Report"> <child name="report_rom"/> </service>
|
||||
<any-service> <parent/> <any-child/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="report_rom">
|
||||
<binary name="report_rom"/>
|
||||
<resource name="RAM" quantum="2M"/>
|
||||
@ -70,25 +48,24 @@ install_config {
|
||||
<config verbose="no">
|
||||
<policy label="leitzentrale_config -> leitzentrale"
|
||||
report="global_keys_handler -> leitzentrale"/>
|
||||
<policy label="leitzentrale_config -> reset"
|
||||
report="global_keys_handler -> reset"/>
|
||||
<policy label="leitzentrale -> trace_subjects"
|
||||
report="trace_subject_reporter -> trace_subjects"/>
|
||||
<policy label="leitzentrale -> manager -> nitpicker_hover"
|
||||
report="nitpicker -> hover"/>
|
||||
<policy label="pointer -> hover" report="nitpicker -> hover"/>
|
||||
<policy label="pointer -> xray"
|
||||
report="global_keys_handler -> leitzentrale"/>
|
||||
<policy label="pointer -> shape" report="shape"/>
|
||||
<policy label="pointer -> shape" report="shape"/>
|
||||
<policy label="drivers -> capslock" report="global_keys_handler -> capslock"/>
|
||||
<policy label="runtime -> capslock" report="global_keys_handler -> capslock"/>
|
||||
<policy label="drivers -> numlock" report="global_keys_handler -> numlock"/>
|
||||
<policy label="runtime -> clicked" report="nitpicker -> clicked"/>
|
||||
<policy label="nit_focus -> focus" report="runtime -> focus"/>
|
||||
<policy label="runtime -> clicked" report="nitpicker -> clicked"/>
|
||||
<policy label="nit_focus -> leitzentrale"
|
||||
report="global_keys_handler -> leitzentrale"/>
|
||||
<policy label="nit_focus -> slides"
|
||||
report="global_keys_handler -> slides"/>
|
||||
<policy label="slides_nit_fb_config -> slides"
|
||||
report="global_keys_handler -> slides"/>
|
||||
<policy label="leitzentrale -> manager -> displays"
|
||||
report="nitpicker -> displays"/>
|
||||
</config>
|
||||
</start>
|
||||
|
||||
@ -105,67 +82,35 @@ install_config {
|
||||
<provides> <service name="File_system"/> </provides>
|
||||
<config>
|
||||
<content>
|
||||
<rom name="fb_drv.config"/>
|
||||
<rom name="nitpicker.config"/>
|
||||
<rom name="fonts.config"/>
|
||||
<rom name="input_filter.config"/>
|
||||
<dir name="managed">
|
||||
<rom name="fonts.config" as="fonts"/>
|
||||
<rom name="fb_drv.config" as="fb_drv"/>
|
||||
<rom name="wlan.config" as="wlan"/>
|
||||
<rom name="installation"/>
|
||||
<rom name="empty_runtime.config" as="runtime"/>
|
||||
<rom name="input_filter.config" as="input_filter"/>
|
||||
<inline name="depot_query"><query/></inline>
|
||||
</dir>
|
||||
<rom name="input_filter.config" as="input_filter"/>
|
||||
<rom name="fb_drv.config" as="fb_drv"/>
|
||||
<rom name="nitpicker.config" as="nitpicker"/>
|
||||
<rom name="numlock_remap.config" as="numlock_remap"/>
|
||||
<rom name="leitzentrale.config" as="leitzentrale"/>
|
||||
<rom name="drivers.config" as="drivers"/>
|
||||
<rom name="manual_deploy.config" as="deploy"/>
|
||||
<rom name="en_us.chargen"/>
|
||||
<rom name="de.chargen"/>
|
||||
<rom name="special.chargen"/>
|
||||
<rom name="numlock_remap.config"/>
|
||||
<rom name="vimrc"/>
|
||||
<rom name="wlan.config"/>
|
||||
<rom name="installation"/>
|
||||
<dir name="leitzentrale">
|
||||
<rom name="leitzentrale.config" as="config"/>
|
||||
</dir>
|
||||
<dir name="examples">
|
||||
<dir name="vm">
|
||||
<dir name="debian">
|
||||
<rom name="machine.vbox"/>
|
||||
<rom name="machine.vdi"/>
|
||||
</dir>
|
||||
</dir>
|
||||
<dir name="depot">
|
||||
<dir name="} [depot_user ] {">
|
||||
<rom name="} [depot_user] {_pubkey" as="pubkey"/>
|
||||
<rom name="} [depot_user] {_download" as="download"/>
|
||||
</dir>
|
||||
</dir>
|
||||
</dir>
|
||||
<dir name="drivers">
|
||||
<rom name="drivers.config" as="config"/>
|
||||
</dir>
|
||||
<dir name="runtime">
|
||||
<rom name="empty_runtime.config" as="config"/>
|
||||
<rom name="empty_runtime.config" as="empty.config" />
|
||||
<rom name="block_runtime.config" as="block.config" />
|
||||
<rom name="load_runtime.config" as="load.config" />
|
||||
<rom name="fs_runtime.config" as="fs.config" />
|
||||
<rom name="download_runtime.config" as="download.config" />
|
||||
<rom name="update_runtime.config" as="update.config" />
|
||||
<rom name="deploy_runtime.config" as="deploy.config" />
|
||||
</dir>
|
||||
<dir name="subinit">
|
||||
<rom name="default_fs_subinit.config" as="default_fs.config" />
|
||||
<rom name="default_nic_subinit.config" as="default_nic.config" />
|
||||
<rom name="default_noux_subinit.config" as="default_noux.config" />
|
||||
<rom name="depot_download.config"/>
|
||||
</dir>
|
||||
<dir name="deploy">
|
||||
<rom name="deploy.config" as="config"/>
|
||||
</dir>
|
||||
<inline name="trace_subject_reporter.config">} [config_trace_subject_reporter_content] {
|
||||
</inline>
|
||||
<inline name="system">} [config_system_content] {
|
||||
</inline>
|
||||
</content>
|
||||
<policy label="config_rom -> " root="/" />
|
||||
<policy label="config_fs_rom -> " root="/" />
|
||||
<policy label="rw" root="/" writeable="yes" />
|
||||
</config>
|
||||
</start>
|
||||
|
||||
<start name="config_rom">
|
||||
<start name="config_fs_rom">
|
||||
<binary name="fs_rom"/>
|
||||
<resource name="RAM" quantum="10M"/>
|
||||
<provides> <service name="ROM"/> </provides>
|
||||
@ -175,6 +120,16 @@ install_config {
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="report_fs_rom">
|
||||
<binary name="fs_rom"/>
|
||||
<resource name="RAM" quantum="3M"/>
|
||||
<provides> <service name="ROM"/> </provides>
|
||||
<route>
|
||||
<service name="File_system"> <child name="report_fs"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="report_fs">
|
||||
<binary name="ram_fs"/>
|
||||
<resource name="RAM" quantum="16M"/>
|
||||
@ -182,10 +137,21 @@ install_config {
|
||||
<config>
|
||||
<content>
|
||||
<inline name="log">### start ###</inline>
|
||||
<dir name="runtime">
|
||||
<inline name="state"><empty/></inline>
|
||||
<dir name="wifi_drv">
|
||||
<inline name="wlan_accesspoints"><empty/></inline>
|
||||
<inline name="wlan_state"> <empty/> </inline>
|
||||
</dir>
|
||||
<dir name="nic_router"> <inline name="state"> <empty/></inline> </dir>
|
||||
<dir name="update"> <inline name="state"> <empty/></inline> </dir>
|
||||
<dir name="depot_query"><inline name="blueprint"><empty/></inline> </dir>
|
||||
</dir>
|
||||
</content>
|
||||
<policy label="fs_report -> " root="/" writeable="yes" />
|
||||
<policy label="log_terminal -> " root="/" writeable="yes" />
|
||||
<policy label="ro" root="/" />
|
||||
<policy label="fs_report -> " root="/" writeable="yes"/>
|
||||
<policy label="log_terminal -> " root="/" writeable="yes"/>
|
||||
<policy label="report_fs_rom -> " root="/"/>
|
||||
<policy label="ro" root="/"/>
|
||||
</config>
|
||||
</start>
|
||||
|
||||
@ -242,15 +208,15 @@ install_config {
|
||||
<route>
|
||||
<service name="LOG"> <child name="log"/> </service>
|
||||
<service name="ROM" label="config">
|
||||
<child name="config_rom" label="drivers/config"/> </service>
|
||||
<service name="ROM" label="input_filter.config"> <child name="config_rom"/> </service>
|
||||
<service name="ROM" label="numlock_remap.config"> <child name="config_rom"/> </service>
|
||||
<service name="ROM" label_suffix=".chargen"> <child name="config_rom"/> </service>
|
||||
<service name="ROM" label_suffix=".remap"> <child name="config_rom"/> </service>
|
||||
<service name="ROM" label="capslock"> <child name="report_rom"/> </service>
|
||||
<service name="ROM" label="numlock"> <child name="report_rom"/> </service>
|
||||
<service name="ROM" label="system"> <child name="config_rom"/> </service>
|
||||
<service name="ROM" label_suffix="fb_drv.config"> <child name="config_rom"/> </service>
|
||||
<child name="config_fs_rom" label="drivers"/> </service>
|
||||
<service name="ROM" label_last="capslock"> <child name="report_rom"/> </service>
|
||||
<service name="ROM" label_last="input_filter.config">
|
||||
<child name="config_fs_rom" label="managed/input_filter"/> </service>
|
||||
<service name="ROM" label_last="fb_drv.config">
|
||||
<child name="config_fs_rom" label="managed/fb_drv"/> </service>
|
||||
<service name="ROM" label_last="numlock_remap.config">
|
||||
<child name="config_fs_rom" label="numlock_remap"/> </service>
|
||||
<service name="ROM" label_last="numlock"> <child name="report_rom"/> </service>
|
||||
<service name="Timer"> <child name="timer"/> </service>
|
||||
<service name="Report"> <child name="fs_report"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
@ -269,7 +235,7 @@ install_config {
|
||||
<provides><service name="Nitpicker"/></provides>
|
||||
<route>
|
||||
<service name="ROM" label="config">
|
||||
<child name="config_rom" label="nitpicker.config"/> </service>
|
||||
<child name="config_fs_rom" label="nitpicker"/> </service>
|
||||
<service name="ROM" label="focus">
|
||||
<child name="nit_focus"/> </service>
|
||||
<service name="Report" label="keystate">
|
||||
@ -292,13 +258,11 @@ install_config {
|
||||
<attribute name="enabled" /> </input>
|
||||
<input name="slides_enabled" rom="slides" node="slides">
|
||||
<attribute name="enabled" /> </input>
|
||||
<input name="runtime_focus" rom="focus" node="focus">
|
||||
<attribute name="label"/> </input>
|
||||
<output node="focus">
|
||||
<if>
|
||||
<has_value input="leitzentrale_enabled" value="yes" />
|
||||
<then>
|
||||
<attribute name="label" value="leitzentrale -> control_fader -> "/>
|
||||
<attribute name="label" value="leitzentrale -> manager -> fader -> "/>
|
||||
</then>
|
||||
<else>
|
||||
<if>
|
||||
@ -307,7 +271,7 @@ install_config {
|
||||
<attribute name="label" value="slides"/>
|
||||
</then>
|
||||
<else>
|
||||
<attribute name="label" input="runtime_focus"/>
|
||||
<attribute name="label" value="runtime -> focus"/>
|
||||
</else>
|
||||
</if>
|
||||
</else>
|
||||
@ -316,7 +280,6 @@ install_config {
|
||||
</config>
|
||||
<route>
|
||||
<service name="ROM" label="leitzentrale"> <child name="report_rom"/> </service>
|
||||
<service name="ROM" label="focus"> <child name="report_rom"/> </service>
|
||||
<service name="ROM" label="slides"> <child name="report_rom"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
@ -338,20 +301,16 @@ install_config {
|
||||
<resource name="RAM" quantum="1M"/>
|
||||
<config>
|
||||
<bool name="leitzentrale" initial="yes"/>
|
||||
<bool name="reset" initial="no"/>
|
||||
<bool name="capslock" initial="no"/>
|
||||
<bool name="numlock" initial="no"/>
|
||||
<bool name="slides" initial="no"/>
|
||||
|
||||
<press name="KEY_PRESENTATION" bool="slides" change="toggle"/>
|
||||
<press name="KEY_RESTART" bool="reset" change="on"/>
|
||||
<release name="KEY_RESTART" bool="reset" change="off"/>
|
||||
<press name="KEY_DASHBOARD" bool="leitzentrale" change="toggle"/>
|
||||
<press name="KEY_CAPSLOCK" bool="capslock" change="toggle"/>
|
||||
<press name="KEY_NUMLOCK" bool="numlock" change="toggle"/>
|
||||
<press name="KEY_PRESENTATION" bool="slides" change="toggle"/>
|
||||
<press name="KEY_DASHBOARD" bool="leitzentrale" change="toggle"/>
|
||||
<press name="KEY_CAPSLOCK" bool="capslock" change="toggle"/>
|
||||
<press name="KEY_NUMLOCK" bool="numlock" change="toggle"/>
|
||||
|
||||
<report name="leitzentrale"> <bool name="leitzentrale"/> </report>
|
||||
<report name="reset"> <bool name="reset"/> </report>
|
||||
<report name="capslock"> <bool name="capslock"/> </report>
|
||||
<report name="numlock"> <bool name="numlock"/> </report>
|
||||
<report name="slides"> <bool name="slides"/> </report>
|
||||
@ -370,33 +329,39 @@ install_config {
|
||||
<provides><service name="ROM"/></provides>
|
||||
<route>
|
||||
<service name="ROM" label="leitzentrale"> <child name="report_rom"/> </service>
|
||||
<service name="ROM" label="reset"> <child name="report_rom"/> </service>
|
||||
<service name="ROM" label="config">
|
||||
<child name="config_rom" label="leitzentrale/config"/> </service>
|
||||
<child name="config_fs_rom" label="leitzentrale"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="leitzentrale" caps="2000" priority="-2">
|
||||
<start name="leitzentrale" caps="4000" priority="-2">
|
||||
<binary name="init"/>
|
||||
<resource name="RAM" quantum="128M"/>
|
||||
<provides> <service name="Nitpicker"/> </provides>
|
||||
<route>
|
||||
<service name="LOG"> <child name="log"/> </service>
|
||||
<service name="ROM" label="config">
|
||||
<child name="leitzentrale_config"/> </service>
|
||||
<service name="ROM" label_last="vimrc">
|
||||
<child name="config_rom"/> </service>
|
||||
<service name="ROM" label_last="fonts.config">
|
||||
<child name="config_rom"/> </service>
|
||||
<service name="ROM" label="trace_subjects">
|
||||
<service name="ROM" label_prefix="report -> ">
|
||||
<child name="report_fs_rom"/> </service>
|
||||
<service name="ROM" label_prefix="manager -> report -> ">
|
||||
<child name="report_fs_rom"/> </service>
|
||||
<service name="ROM" label_prefix="manager -> config -> ">
|
||||
<child name="config_fs_rom"/> </service>
|
||||
<service name="ROM" label_prefix="manager -> displays">
|
||||
<child name="report_rom"/> </service>
|
||||
<service name="ROM" label_prefix="config -> ">
|
||||
<child name="config_fs_rom"/> </service>
|
||||
<service name="ROM" label="manager -> nitpicker_hover">
|
||||
<child name="report_rom"/> </service>
|
||||
<service name="Nitpicker"> <child name="nitpicker"/> </service>
|
||||
<service name="Timer"> <child name="timer"/> </service>
|
||||
<service name="File_system" label="control_noux -> config">
|
||||
<service name="File_system" label="config">
|
||||
<child name="config_fs" label="rw"/> </service>
|
||||
<service name="File_system" label="control_noux -> report">
|
||||
<service name="File_system" label="report">
|
||||
<child name="report_fs" label="ro"/> </service>
|
||||
<service name="File_system" label="log_noux -> report">
|
||||
<service name="File_system" label="report">
|
||||
<child name="report_fs" label="ro"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
@ -409,16 +374,12 @@ install_config {
|
||||
|
||||
<start name="runtime" caps="50000" priority="-3">
|
||||
<binary name="init"/>
|
||||
<resource name="RAM" quantum="12G"/>
|
||||
<resource name="RAM" quantum="32G"/>
|
||||
<route>
|
||||
<service name="ROM" label="config">
|
||||
<child name="config_rom" label="runtime/config"/> </service>
|
||||
<child name="config_fs_rom" label="managed/runtime"/> </service>
|
||||
<service name="ROM" label_prefix="config -> ">
|
||||
<child name="config_rom"/> </service>
|
||||
<service name="ROM" label_suffix="-> vimrc">
|
||||
<child name="config_rom" label="vimrc"/> </service>
|
||||
<service name="ROM" label="system">
|
||||
<child name="config_rom"/> </service>
|
||||
<child name="config_fs_rom"/> </service>
|
||||
<service name="ROM" label="capslock">
|
||||
<child name="report_rom"/> </service>
|
||||
<service name="ROM" label="clicked">
|
||||
@ -432,12 +393,13 @@ install_config {
|
||||
<service name="Platform" label_prefix="acpica">
|
||||
<child name="drivers" label="acpica"/> </service>
|
||||
<service name="Platform"> <child name="drivers"/> </service>
|
||||
<service name="Nitpicker" label_prefix="leitzentrale">
|
||||
<child name="leitzentrale"/> </service>
|
||||
<service name="Nitpicker" label="backdrop">
|
||||
<child name="nitpicker" label="backdrop"/> </service>
|
||||
<service name="Nitpicker"> <child name="nitpicker"/> </service>
|
||||
<service name="Timer"> <child name="timer"/> </service>
|
||||
<service name="Report" label_suffix="-> shape"> <child name="pointer"/> </service>
|
||||
<service name="Report" label="focus"> <child name="report_rom"/> </service>
|
||||
<service name="Report"> <child name="fs_report"/> </service>
|
||||
<service name="LOG" label="unlogged"> <parent/> </service>
|
||||
<service name="LOG"> <child name="log"/> </service>
|
||||
@ -481,11 +443,10 @@ file copy -force [genode_dir]/repos/gems/recipes/raw/drivers_managed-pc/input_fi
|
||||
file copy -force [genode_dir]/repos/gems/recipes/raw/depot_download/depot_download.config \
|
||||
[run_dir]/genode/depot_download.config
|
||||
|
||||
file copy -force [genode_dir]/depot/[depot_user]/pubkey [run_dir]/genode/[depot_user]_pubkey
|
||||
file copy -force [genode_dir]/depot/[depot_user]/download [run_dir]/genode/[depot_user]_download
|
||||
|
||||
file copy -force [genode_dir]/VERSION [run_dir]/genode/
|
||||
|
||||
file copy -force [genode_dir]/repos/gems/src/app/backdrop/genode_logo.png [run_dir]/genode/
|
||||
|
||||
exec gzip -dc [genode_dir]/repos/gems/run/sculpt/machine.vdi.gz > [run_dir]/genode/machine.vdi
|
||||
|
||||
|
||||
@ -502,21 +463,23 @@ close $fd
|
||||
|
||||
|
||||
#
|
||||
# Package-management support
|
||||
#
|
||||
# The package management has two aspects, installation and deployment.
|
||||
# Packages are installed via the 'install' runtime, which takes the
|
||||
# information about the packages to install from 'config/installation'.
|
||||
# Once installed, packages can be deployed via the 'deploy' runtime.
|
||||
# This runtime can be tailored by modifying 'config/deploy/config'.
|
||||
# Assemble 'depot_users.tar' with the keys and download locations of the
|
||||
# depot user found at genode/depot/.
|
||||
#
|
||||
set depot_users_files [exec sh -c "cd [genode_dir]; \
|
||||
find depot -maxdepth 3 -name pubkey \
|
||||
-or -name download"]
|
||||
exec sh -c "tar cf [run_dir]/genode/depot_users.tar -C [genode_dir] \
|
||||
[join $depot_users_files]"
|
||||
|
||||
proc current_pkg { pkg } { return $pkg/[_current_depot_archive_version pkg $pkg] }
|
||||
|
||||
#
|
||||
# Depot packages to be included in the default installation
|
||||
#
|
||||
set pkgs_to_install { sculpt-installation }
|
||||
|
||||
proc current_pkg { pkg } { return $pkg/[_current_depot_archive_version pkg $pkg] }
|
||||
|
||||
set pkgs_to_install { }
|
||||
|
||||
set fd [open [run_dir]/genode/installation w]
|
||||
puts $fd "<installation arch=\"[depot_spec]\">"
|
||||
@ -525,32 +488,17 @@ foreach pkg $pkgs_to_install {
|
||||
puts $fd "</installation>"
|
||||
close $fd
|
||||
|
||||
|
||||
#
|
||||
# Configuration of deploy runtime
|
||||
# Manual configuration of deploy runtime
|
||||
#
|
||||
# This configuration is not provided as a file at run/sculpt/ because some
|
||||
# parts need to be filled in at run-script execution time, in particular the
|
||||
# current versions of the packages to deploy.
|
||||
#
|
||||
append depot_deploy_config {
|
||||
append manual_deploy_config {
|
||||
<config arch="} [depot_spec] {">
|
||||
<static>
|
||||
<parent-provides>
|
||||
<service name="ROM"/>
|
||||
<service name="CPU"/>
|
||||
<service name="PD"/>
|
||||
<service name="RM"/>
|
||||
<service name="LOG"/>
|
||||
<service name="Timer"/>
|
||||
<service name="Nitpicker"/>
|
||||
<service name="File_system"/>
|
||||
<service name="Rtc"/>
|
||||
<service name="Usb"/>
|
||||
<service name="Report"/>
|
||||
<service name="Block"/>
|
||||
<service name="Platform"/>
|
||||
</parent-provides>
|
||||
</static>
|
||||
|
||||
<common_routes>
|
||||
<service name="ROM" label_last="ld.lib.so"> <parent/> </service>
|
||||
<service name="ROM" label_last="init"> <parent/> </service>
|
||||
@ -560,30 +508,16 @@ append depot_deploy_config {
|
||||
<service name="Timer"> <parent/> </service>
|
||||
</common_routes>
|
||||
|
||||
<start name="focus_rom" pkg="} [depot_user]/pkg/[current_pkg rom_filter] {">
|
||||
<config>
|
||||
<output node="focus">
|
||||
<attribute name="label" value="runtime -> dynamic -> wm -> wm -> "/>
|
||||
</output>
|
||||
</config>
|
||||
</start>
|
||||
|
||||
<start name="focus_reporter" pkg="} [depot_user]/pkg/[current_pkg rom_reporter] {">
|
||||
<config> <rom label="focus"/> </config>
|
||||
<route>
|
||||
<service name="ROM" label="focus"> <child name="focus_rom"/> </service>
|
||||
<service name="Report" label="focus"> <parent label="focus"/> </service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<!--
|
||||
<start name="fonts_fs" pkg="} [depot_user]/pkg/[current_pkg fonts_fs] {">
|
||||
<route>
|
||||
<service name="ROM" label="config"> <parent label="fonts.config"/> </service>
|
||||
<service name="ROM" label="config"> <parent label="config -> managed/fonts"/> </service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="wm" pkg="} [depot_user]/pkg/[current_pkg themed_wm] {">
|
||||
<route>
|
||||
<service name="Nitpicker" label="wm -> "> <parent label="focus"/> </service>
|
||||
<service name="Nitpicker"> <parent/> </service>
|
||||
</route>
|
||||
</start>
|
||||
@ -593,7 +527,17 @@ append depot_deploy_config {
|
||||
<service name="Nitpicker"> <parent label="backdrop"/> </service>
|
||||
</route>
|
||||
</start>
|
||||
-->
|
||||
|
||||
<!--
|
||||
<start name="nano3d" pkg="} [depot_user]/pkg/[current_pkg nano3d] {">
|
||||
<route>
|
||||
<service name="Nitpicker"> <child name="wm"/> </service>
|
||||
</route>
|
||||
</start>
|
||||
-->
|
||||
|
||||
<!--
|
||||
<start name="noux" pkg="} [depot_user]/pkg/[current_pkg noux-system] {">
|
||||
<route>
|
||||
<service name="Nitpicker"> <child name="wm"/> </service>
|
||||
@ -604,61 +548,17 @@ append depot_deploy_config {
|
||||
<service name="File_system" label="fonts">
|
||||
<child name="fonts_fs"/> </service>
|
||||
<service name="File_system" label="target">
|
||||
<parent label="rw"/> </service>
|
||||
<service name="ROM" label="vimrc"> <parent/> </service>
|
||||
<child name="default_fs_rw"/> </service>
|
||||
<service name="ROM" label_last="vimrc">
|
||||
<parent label="config -> vimrc"/> </service>
|
||||
</route>
|
||||
</start>
|
||||
-->
|
||||
|
||||
<!--
|
||||
<start name="nano3d" pkg="} [depot_user]/pkg/[current_pkg nano3d] {">
|
||||
<route>
|
||||
<service name="Nitpicker"> <child name="wm"/> </service>
|
||||
</route>
|
||||
</start>
|
||||
-->
|
||||
|
||||
<!--
|
||||
<start name="nic_drv" pkg="} [depot_user]/pkg/[current_pkg wifi] {">
|
||||
<route>
|
||||
<service name="Platform"> <parent label="wifi"/> </service>
|
||||
<service name="Rtc"> <parent/> </service>
|
||||
<service name="Report"> <parent/> </service>
|
||||
<service name="RM"> <parent/> </service>
|
||||
<service name="ROM" label="wlan_configuration">
|
||||
<parent label="wlan.config"/> </service>
|
||||
</route>
|
||||
</start>
|
||||
-->
|
||||
|
||||
<!--
|
||||
<start name="nic_drv" pkg="} [depot_user]/pkg/[current_pkg ipxe_nic_drv] {">
|
||||
<route>
|
||||
<service name="Platform"> <parent label="nic"/> </service>
|
||||
<service name="Report"> <parent/> </service>
|
||||
<service name="RM"> <parent/> </service>
|
||||
</route>
|
||||
</start>
|
||||
-->
|
||||
|
||||
<!--
|
||||
<start name="nic_router" pkg="} [depot_user]/pkg/[current_pkg nic_router-nat] {">
|
||||
<route>
|
||||
<service name="Nic"> <child name="nic_drv"/> </service>
|
||||
</route>
|
||||
</start>
|
||||
-->
|
||||
|
||||
<!--
|
||||
<start name="vm_fs" pkg="} [depot_user]/pkg/[current_pkg chroot] {">
|
||||
<route>
|
||||
<service name="File_system"> <parent label="rw"/> </service>
|
||||
</route>
|
||||
<config> <default-policy path="/vm/debian" writeable="yes"/> </config>
|
||||
</start>
|
||||
|
||||
<start name="shared_fs" pkg="} [depot_user]/pkg/[current_pkg chroot] {">
|
||||
<route>
|
||||
<service name="File_system"> <parent label="rw"/> </service>
|
||||
<service name="File_system"> <child name="default_fs_rw"/> </service>
|
||||
</route>
|
||||
<config> <default-policy path="/shared" writeable="yes"/> </config>
|
||||
</start>
|
||||
@ -671,8 +571,17 @@ append depot_deploy_config {
|
||||
</output>
|
||||
</config>
|
||||
</start>
|
||||
-->
|
||||
|
||||
<start name="vm" pkg="} [depot_user]/pkg/[current_pkg vbox5-nova-sculpt] {">
|
||||
<!--
|
||||
<start name="vm_fs" pkg="} [depot_user]/pkg/[current_pkg chroot] {">
|
||||
<route>
|
||||
<service name="File_system"> <child name="default_fs_rw"/> </service>
|
||||
</route>
|
||||
<config> <default-policy path="/vm/debian" writeable="yes"/> </config>
|
||||
</start>
|
||||
|
||||
<start name="vm" ram="4300M" pkg="} [depot_user]/pkg/[current_pkg vbox5-nova-sculpt] {">
|
||||
<route>
|
||||
<service name="ROM" label="capslock"> <parent label="capslock"/> </service>
|
||||
<service name="ROM" label="platform_info"> <parent/> </service>
|
||||
@ -690,10 +599,79 @@ append depot_deploy_config {
|
||||
</start>
|
||||
-->
|
||||
|
||||
<!--
|
||||
<start name="download_debian" pkg="cnuke/pkg/download_debian/2018-05-30">
|
||||
<route>
|
||||
<service name="File_system" label="fonts"> <child name="fonts_fs"/> </service>
|
||||
<service name="File_system" label="target"> <child name="vm_fs"/> </service>
|
||||
<service name="Nic"> <child name="nic_router"/> </service>
|
||||
<service name="Nitpicker"> <child name="wm"/> </service>
|
||||
<service name="RM"> <parent/> </service>
|
||||
</route>
|
||||
</start>
|
||||
-->
|
||||
|
||||
<!--
|
||||
<start name="top_view" pkg="alex-ab/pkg/top_view/2018-05-29-a">
|
||||
<route>
|
||||
<service name="TRACE"> <parent/> </service>
|
||||
<service name="Timer"> <parent/> </service>
|
||||
<service name="Nitpicker"> <child name="wm"/> </service>
|
||||
<service name="File_system" label="fonts">
|
||||
<child name="fonts_fs"/> </service>
|
||||
</route>
|
||||
</start>
|
||||
-->
|
||||
|
||||
<!--
|
||||
<start name="2048" pkg="ehmry/pkg/2048/18.05">
|
||||
<route>
|
||||
<service name="Nitpicker"> <child name="wm"/> </service>
|
||||
</route>
|
||||
</start>
|
||||
-->
|
||||
|
||||
<!--
|
||||
<start name="vbox5-tc-browser" pkg="alex-ab/pkg/vbox5-tc-firefox-nova-sculpt/2018-05-30">
|
||||
<route>
|
||||
<service name="ROM" label="capslock"> <parent label="capslock"/> </service>
|
||||
<service name="ROM" label="platform_info"> <parent/> </service>
|
||||
<service name="Report" label="shape"> <parent label="wm -> wm -> vm -> shape"/> </service>
|
||||
<service name="RM"> <parent/> </service>
|
||||
<service name="Rtc"> <parent/> </service>
|
||||
<service name="Nitpicker"> <child name="wm"/> </service>
|
||||
<service name="Nic"> <child name="nic_router"/> </service>
|
||||
<service name="File_system" label="shared"> <child name="shared_fs"/> </service>
|
||||
</route>
|
||||
</start>
|
||||
-->
|
||||
|
||||
<!--
|
||||
<start name="seoul-vmm-browser" pkg="alex-ab/pkg/seoul-nova-sculpt/2018-05-30">
|
||||
<route>
|
||||
<service name="ROM" label="platform_info"> <parent/> </service>
|
||||
<service name="RM"> <parent/> </service>
|
||||
<service name="Rtc"> <parent/> </service>
|
||||
<service name="Nitpicker"> <child name="wm"/> </service>
|
||||
<service name="Nic"> <child name="nic_router"/> </service>
|
||||
</route>
|
||||
</start>
|
||||
-->
|
||||
|
||||
<!--
|
||||
<start name="qt5_textedit" pkg="cproc/pkg/qt5_textedit/2018-05-30">
|
||||
<route>
|
||||
<service name="File_system" label="rw"> <parent label="config"/> </service>
|
||||
<service name="Nitpicker"> <child name="wm"/> </service>
|
||||
<service name="Report" label="shape"> <parent label="wm -> wm -> qt5_textedit -> shape"/> </service>
|
||||
</route>
|
||||
</start>
|
||||
-->
|
||||
|
||||
</config>}
|
||||
|
||||
set fd [open [run_dir]/genode/deploy.config w]
|
||||
puts $fd $depot_deploy_config
|
||||
set fd [open [run_dir]/genode/manual_deploy.config w]
|
||||
puts $fd $manual_deploy_config
|
||||
close $fd
|
||||
|
||||
|
||||
|
@ -1,72 +0,0 @@
|
||||
<config>
|
||||
<report init_ram="yes" child_ram="yes" delay_ms="4000"/>
|
||||
|
||||
<parent-provides>
|
||||
<service name="ROM"/>
|
||||
<service name="PD"/>
|
||||
<service name="RM"/>
|
||||
<service name="CPU"/>
|
||||
<service name="LOG"/>
|
||||
<service name="Nitpicker"/>
|
||||
<service name="Timer"/>
|
||||
<service name="Report"/>
|
||||
<service name="Block"/>
|
||||
</parent-provides>
|
||||
|
||||
<default-route> <any-service> <parent/> <any-child/> </any-service> </default-route>
|
||||
|
||||
<default caps="100"/>
|
||||
|
||||
<start name="nit_focus">
|
||||
<resource name="RAM" quantum="1M"/>
|
||||
<config>
|
||||
<policy label_prefix="leitzentrale" focus="no"/>
|
||||
<default-policy focus="yes"/>
|
||||
</config>
|
||||
<route>
|
||||
<service name="ROM" label="clicked"> <parent label="clicked"/> </service>
|
||||
<service name="Report" label="focus"> <parent label="focus"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="nit_fb">
|
||||
<resource name="RAM" quantum="4M"/>
|
||||
<provides> <service name="Framebuffer"/> <service name="Input"/> </provides>
|
||||
<config xpos="200" ypos="50" width="800" height="600"/>
|
||||
</start>
|
||||
|
||||
<start name="terminal">
|
||||
<binary name="terminal"/>
|
||||
<resource name="RAM" quantum="4M"/>
|
||||
<provides> <service name="Terminal"/> </provides>
|
||||
<route>
|
||||
<service name="ROM" label="config"> <parent label="config -> fonts.config"/> </service>
|
||||
<service name="Framebuffer"> <child name="nit_fb"/> </service>
|
||||
<service name="Input"> <child name="nit_fb"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="noux" caps="500">
|
||||
<binary name="noux"/>
|
||||
<resource name="RAM" quantum="100M" />
|
||||
<config>
|
||||
<fstab>
|
||||
<tar name="bash-minimal.tar" />
|
||||
<tar name="coreutils-minimal.tar" />
|
||||
<tar name="vim-minimal.tar" />
|
||||
<tar name="e2fsprogs-minimal.tar" />
|
||||
<dir name="dev">
|
||||
<zero/> <null/>
|
||||
<block name="block" label="default" block_buffer_count="128"/>
|
||||
</dir>
|
||||
</fstab>
|
||||
<start name="/bin/bash">
|
||||
<env name="TERM" value="screen" />
|
||||
<env name="PS1" value="block:$PWD> " />
|
||||
</start>
|
||||
</config>
|
||||
</start>
|
||||
|
||||
</config>
|
@ -1,47 +0,0 @@
|
||||
<config>
|
||||
<parent-provides>
|
||||
<service name="ROM"/>
|
||||
<service name="PD"/>
|
||||
<service name="RM"/>
|
||||
<service name="CPU"/>
|
||||
<service name="LOG"/>
|
||||
<service name="Timer"/>
|
||||
<service name="Block"/>
|
||||
</parent-provides>
|
||||
|
||||
<default-route> <any-service> <parent/> </any-service> </default-route>
|
||||
|
||||
<service name="File_system">
|
||||
<default-policy> <child name="vfs"/> </default-policy> </service>
|
||||
|
||||
<start name="vfs" caps="400">
|
||||
<resource name="RAM" quantum="100M" />
|
||||
<provides> <service name="File_system"/> </provides>
|
||||
<config>
|
||||
<vfs> <rump fs="ext2fs" ram="48M" writeable="yes"/> </vfs>
|
||||
<default-policy root="/" writeable="yes"/>
|
||||
</config>
|
||||
<route>
|
||||
<service name="Block"> <parent label="default"/> </service>
|
||||
<!--
|
||||
<service name="Block"> <child name="part_blk"/> </service>
|
||||
-->
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<!--
|
||||
<start name="part_blk" caps="100">
|
||||
<resource name="RAM" quantum="10M"/>
|
||||
<provides><service name="Block"/></provides>
|
||||
<config use_gpt="yes">
|
||||
<policy label_prefix="vfs" partition="1" writeable="yes"/>
|
||||
</config>
|
||||
<route>
|
||||
<service name="Block"> <parent label="default"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
-->
|
||||
</config>
|
||||
|
@ -1,54 +0,0 @@
|
||||
<config>
|
||||
<parent-provides>
|
||||
<service name="ROM"/>
|
||||
<service name="PD"/>
|
||||
<service name="RM"/>
|
||||
<service name="CPU"/>
|
||||
<service name="LOG"/>
|
||||
<service name="Timer"/>
|
||||
<service name="Platform"/>
|
||||
<service name="Report"/>
|
||||
<service name="Rtc"/>
|
||||
</parent-provides>
|
||||
|
||||
<default-route> <any-service> <parent/> </any-service> </default-route>
|
||||
|
||||
<service name="Nic">
|
||||
<default-policy> <child name="nic"/> </default-policy> </service>
|
||||
|
||||
<!-- wifi driver (default) -->
|
||||
<start name="nic" caps="300">
|
||||
<binary name="wifi_drv" />
|
||||
<resource name="RAM" quantum="54M"/>
|
||||
<provides> <service name="Nic"/> </provides>
|
||||
<config ld_verbose="yes" verbose="yes" use_11n="no" connected_scan_interval="0">
|
||||
<vfs>
|
||||
<dir name="dev"> <log/> <rtc/> <null/>
|
||||
<jitterentropy name="random"/>
|
||||
<jitterentropy name="urandom"/>
|
||||
</dir>
|
||||
<dir name="config"> <ram/> </dir>
|
||||
</vfs>
|
||||
<libc stdout="/dev/null" stderr="/dev/log" rtc="/dev/rtc"/>
|
||||
</config>
|
||||
<route>
|
||||
<service name="ROM" label="wlan_configuration">
|
||||
<parent label="wlan.config"/> </service>
|
||||
<service name="Platform"> <parent label="wifi"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<!-- uncomment for wired NIC driver -->
|
||||
<!-- <start name="nic" caps="300">
|
||||
<binary name="nic_drv" />
|
||||
<resource name="RAM" quantum="16M"/>
|
||||
<provides> <service name="Nic"/> </provides>
|
||||
<config />
|
||||
<route>
|
||||
<service name="Platform"> <parent label="nic"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start> -->
|
||||
</config>
|
||||
|
@ -1,63 +0,0 @@
|
||||
<config>
|
||||
<parent-provides>
|
||||
<service name="ROM"/>
|
||||
<service name="PD"/>
|
||||
<service name="RM"/>
|
||||
<service name="CPU"/>
|
||||
<service name="LOG"/>
|
||||
<service name="Timer"/>
|
||||
<service name="File_system"/>
|
||||
<service name="Nitpicker"/>
|
||||
</parent-provides>
|
||||
|
||||
<default-route> <any-service> <parent/> <any-child/> </any-service> </default-route>
|
||||
|
||||
<default caps="100"/>
|
||||
|
||||
<start name="nit_fb">
|
||||
<resource name="RAM" quantum="4M"/>
|
||||
<provides> <service name="Framebuffer"/> <service name="Input"/> </provides>
|
||||
<config xpos="10" ypos="10" width="800" height="600"/>
|
||||
</start>
|
||||
|
||||
<start name="terminal">
|
||||
<binary name="terminal"/>
|
||||
<resource name="RAM" quantum="4M"/>
|
||||
<provides> <service name="Terminal"/> </provides>
|
||||
<route>
|
||||
<service name="ROM" label="config"> <parent label="fonts.config"/> </service>
|
||||
<service name="Framebuffer"> <child name="nit_fb"/> </service>
|
||||
<service name="Input"> <child name="nit_fb"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="noux" caps="500">
|
||||
<binary name="noux"/>
|
||||
<resource name="RAM" quantum="64M" />
|
||||
<exit propagate="yes"/>
|
||||
<config>
|
||||
<fstab>
|
||||
<tar name="bash-minimal.tar" />
|
||||
<tar name="coreutils-minimal.tar" />
|
||||
<tar name="vim-minimal.tar" />
|
||||
<dir name="dev"> <zero/> <null/> </dir>
|
||||
<dir name="rw"> <fs label="target"/> </dir>
|
||||
<dir name="config"> <fs label="config"/> </dir>
|
||||
<dir name="tmp"> <ram /> </dir>
|
||||
<dir name="share"> <dir name="vim"> <rom name="vimrc"/> </dir> </dir>
|
||||
</fstab>
|
||||
<start name="/bin/bash">
|
||||
<env name="TERM" value="screen" />
|
||||
<env name="PS1" value="noux:$PWD> " />
|
||||
</start>
|
||||
</config>
|
||||
<route>
|
||||
<service name="File_system" label="target"> <parent label="target"/> </service>
|
||||
<service name="File_system" label="config"> <parent label="config"/> </service>
|
||||
<service name="Terminal"> <child name="terminal"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
</config>
|
||||
|
@ -1,119 +0,0 @@
|
||||
<config verbose="no" prio_levels="2">
|
||||
|
||||
<report init_ram="yes" requested="yes" child_ram="yes" delay_ms="2000" buffer="128K"/>
|
||||
|
||||
<parent-provides>
|
||||
<service name="ROM"/>
|
||||
<service name="PD"/>
|
||||
<service name="RM"/>
|
||||
<service name="CPU"/>
|
||||
<service name="LOG"/>
|
||||
<service name="Nitpicker"/>
|
||||
<service name="Timer"/>
|
||||
<service name="Block"/>
|
||||
<service name="Report"/>
|
||||
<service name="Rtc"/>
|
||||
<service name="Usb"/>
|
||||
<service name="File_system"/>
|
||||
<service name="Platform"/>
|
||||
</parent-provides>
|
||||
|
||||
<default-route> <any-service> <parent/> <any-child/> </any-service> </default-route>
|
||||
|
||||
<default caps="100"/>
|
||||
|
||||
<start name="fs" caps="500">
|
||||
<resource name="RAM" quantum="114M"/>
|
||||
<binary name="init"/>
|
||||
<route>
|
||||
<service name="ROM" label="config">
|
||||
<parent label="config -> subinit/default_fs.config"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
<provides> <service name="File_system"/> <service name="Block"/> </provides>
|
||||
</start>
|
||||
|
||||
<start name="depot_fs" priority="0">
|
||||
<binary name="chroot"/>
|
||||
<resource name="RAM" quantum="1M" />
|
||||
<provides> <service name="File_system"/> </provides>
|
||||
<config> <default-policy path="/depot"/> </config>
|
||||
<route>
|
||||
<service name="File_system"> <child name="fs"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="report_rom">
|
||||
<binary name="report_rom"/>
|
||||
<resource name="RAM" quantum="1M"/>
|
||||
<provides> <service name="Report"/> <service name="ROM"/> </provides>
|
||||
<config verbose="no">
|
||||
<policy label="depot_deploy -> blueprint" report="depot_query -> blueprint"/>
|
||||
<policy label="depot_query -> query" report="depot_deploy -> query"/>
|
||||
<policy label="dynamic -> config" report="depot_deploy -> init.config"/>
|
||||
</config>
|
||||
</start>
|
||||
|
||||
<start name="depot_rom">
|
||||
<binary name="fs_rom"/>
|
||||
<resource name="RAM" quantum="80M"/>
|
||||
<provides> <service name="ROM"/> </provides>
|
||||
<route>
|
||||
<service name="File_system"> <child name="depot_fs"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="depot_query">
|
||||
<resource name="RAM" quantum="1M"/>
|
||||
<config query="rom">
|
||||
<vfs> <dir name="depot"> <fs/> </dir> </vfs>
|
||||
</config>
|
||||
<route>
|
||||
<service name="ROM" label="query"> <child name="report_rom"/> </service>
|
||||
<service name="Report"> <child name="report_rom"/> </service>
|
||||
<service name="File_system"> <child name="depot_fs"/> </service>
|
||||
<any-service> <parent/> <any-child/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="depot_deploy">
|
||||
<resource name="RAM" quantum="1M"/>
|
||||
<route>
|
||||
<service name="ROM" label="config">
|
||||
<parent label="config -> deploy/config"/> </service>
|
||||
<service name="ROM" label="blueprint"> <child name="report_rom"/> </service>
|
||||
<service name="Report"> <child name="report_rom"/> </service>
|
||||
<any-service> <parent/> <any-child/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="dynamic" caps="30000">
|
||||
<resource name="RAM" quantum="12G"/>
|
||||
<binary name="init"/>
|
||||
<route>
|
||||
<service name="ROM" label_last="ld.lib.so"> <parent/> </service>
|
||||
<service name="ROM" label_last="init"> <parent/> </service>
|
||||
<service name="ROM" label_last="vimrc"> <parent/> </service>
|
||||
<service name="ROM" label_last="slides.pdf"> <parent/> </service>
|
||||
<service name="ROM" label_last="capslock"> <parent label="capslock"/> </service>
|
||||
<service name="ROM" label_last="platform_info"> <parent/> </service>
|
||||
<service name="ROM" label_last="wlan.config">
|
||||
<parent label="config -> wlan.config"/> </service>
|
||||
<service name="ROM" label_last="fonts.config">
|
||||
<parent label="config -> fonts.config"/> </service>
|
||||
<service name="ROM" label="config"> <child name="report_rom"/> </service>
|
||||
<service name="ROM" label="clicked"> <parent label="clicked"/> </service>
|
||||
<service name="ROM"> <child name="depot_rom"/> </service>
|
||||
<service name="Report" label="focus"> <parent label="focus"/> </service>
|
||||
<service name="Nitpicker" label="backdrop"> <parent label="backdrop"/> </service>
|
||||
<service name="File_system" label="config"> <parent label="config"/> </service>
|
||||
<service name="File_system" label="report"> <parent label="report"/> </service>
|
||||
<service name="File_system" label="rw"> <child name="fs"/> </service>
|
||||
<service name="Block" label_prefix="default"> <child name="fs"/> </service>
|
||||
<any-service> <parent/> <any-child/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
</config>
|
@ -1,144 +0,0 @@
|
||||
<config verbose="yes" prio_levels="2">
|
||||
|
||||
<report init_ram="yes" requested="yes" child_ram="yes" delay_ms="2000" buffer="128K"/>
|
||||
|
||||
<parent-provides>
|
||||
<service name="ROM"/>
|
||||
<service name="PD"/>
|
||||
<service name="RM"/>
|
||||
<service name="CPU"/>
|
||||
<service name="LOG"/>
|
||||
<service name="Nitpicker"/>
|
||||
<service name="Timer"/>
|
||||
<service name="Block"/>
|
||||
<service name="Report"/>
|
||||
<service name="Rtc"/>
|
||||
<service name="File_system"/>
|
||||
<service name="Platform"/>
|
||||
</parent-provides>
|
||||
|
||||
<default-route> <any-service> <parent/> <any-child/> </any-service> </default-route>
|
||||
|
||||
<default caps="100"/>
|
||||
|
||||
<start name="nit_focus">
|
||||
<resource name="RAM" quantum="1M"/>
|
||||
<config>
|
||||
<policy label_prefix="leitzentrale" focus="no"/>
|
||||
<default-policy focus="yes"/>
|
||||
</config>
|
||||
<route>
|
||||
<service name="ROM" label="clicked"> <parent label="clicked"/> </service>
|
||||
<service name="Report" label="focus"> <parent label="focus"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="fs" caps="500">
|
||||
<resource name="RAM" quantum="114M"/>
|
||||
<binary name="init"/>
|
||||
<route>
|
||||
<service name="ROM" label="config">
|
||||
<parent label="config -> subinit/default_fs.config"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
<provides> <service name="File_system"/> </provides>
|
||||
</start>
|
||||
|
||||
<start name="noux" caps="1000">
|
||||
<resource name="RAM" quantum="80M"/>
|
||||
<binary name="init"/>
|
||||
<route>
|
||||
<service name="ROM" label="config">
|
||||
<parent label="config -> subinit/default_noux.config"/> </service>
|
||||
<service name="ROM" label="fonts.config">
|
||||
<parent label="config -> fonts.config"/> </service>
|
||||
<service name="File_system" label="config">
|
||||
<parent label="config"/> </service>
|
||||
<service name="File_system" label="target">
|
||||
<child name="fs"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="nic" caps="500">
|
||||
<resource name="RAM" quantum="60M"/>
|
||||
<binary name="init"/>
|
||||
<route>
|
||||
<service name="ROM" label="config">
|
||||
<parent label="config -> subinit/default_nic.config"/> </service>
|
||||
<service name="ROM" label="wlan.config">
|
||||
<parent label="config -> wlan.config"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
<provides> <service name="Nic"/> </provides>
|
||||
</start>
|
||||
|
||||
<start name="nic_router" caps="300">
|
||||
<resource name="RAM" quantum="10M"/>
|
||||
<provides><service name="Nic"/></provides>
|
||||
<config verbose_domain_state="yes">
|
||||
<default-policy domain="default" />
|
||||
<domain name="uplink">
|
||||
<nat domain="default" tcp-ports="1000" udp-ports="1000"/>
|
||||
</domain>
|
||||
<domain name="default" interface="10.0.1.1/24">
|
||||
<dhcp-server ip_first="10.0.1.2"
|
||||
ip_last="10.0.1.200"
|
||||
ip_lease_time_sec="360"
|
||||
dns_server="1.1.1.1"/>
|
||||
<tcp dst="0.0.0.0/0"><permit-any domain="uplink"/></tcp>
|
||||
<udp dst="0.0.0.0/0"><permit-any domain="uplink"/></udp>
|
||||
</domain>
|
||||
</config>
|
||||
<route>
|
||||
<service name="Nic"> <child name="nic"/> </service>
|
||||
<any-service> <parent/> <any-child/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<!--
|
||||
<start name="download_fs">
|
||||
<binary name="chroot"/>
|
||||
<resource name="RAM" quantum="1M" />
|
||||
<provides> <service name="File_system"/> </provides>
|
||||
<config> <default-policy path="/vm/debian" writeable="yes"/> </config>
|
||||
<route>
|
||||
<service name="File_system"> <child name="fs"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="fetchurl" caps="500">
|
||||
<resource name="RAM" quantum="32M"/>
|
||||
<config>
|
||||
<libc stdout="/dev/log" stderr="/dev/log" rtc="/dev/rtc" socket="/socket"/>
|
||||
<vfs>
|
||||
<dir name="etc">
|
||||
<inline name="resolv.conf">nameserver 1.1.1.1</inline>
|
||||
<inline name="hosts"/>
|
||||
</dir>
|
||||
<dir name="socket">
|
||||
<lxip dhcp="yes"/>
|
||||
</dir>
|
||||
<dir name="download"> <fs label="download"/> </dir>
|
||||
<dir name="dev">
|
||||
<log/> <null/> <inline name="rtc">2000-01-01 00:00</inline>
|
||||
<inline name="random">01234567890123456789</inline>
|
||||
</dir>
|
||||
</vfs>
|
||||
|
||||
<fetch url="https://cdimage.debian.org/debian-cd/current/amd64/iso-cd/debian-9.3.0-amd64-netinst.iso"
|
||||
path="/download/installer.iso"/>
|
||||
|
||||
</config>
|
||||
<route>
|
||||
<service name="File_system"> <child name="download_fs"/> </service>
|
||||
<service name="Nic"> <child name="nic_router"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
-->
|
||||
|
||||
</config>
|
||||
|
@ -1,9 +1,19 @@
|
||||
<config>
|
||||
<vfs>
|
||||
<rom name="Vera.ttf"/>
|
||||
<rom name="VeraMono.ttf"/>
|
||||
<dir name="fonts">
|
||||
<dir name="title">
|
||||
<ttf name="regular" path="/Vera.ttf" size_px="18" cache="256K"/>
|
||||
</dir>
|
||||
<dir name="text">
|
||||
<ttf name="regular" path="/Vera.ttf" size_px="14" cache="256K"/>
|
||||
</dir>
|
||||
<dir name="annotation">
|
||||
<ttf name="regular" path="/Vera.ttf" size_px="11" cache="256K"/>
|
||||
</dir>
|
||||
<dir name="monospace">
|
||||
<ttf name="regular" path="/VeraMono.ttf" size_px="16" cache="256K"/>
|
||||
<ttf name="regular" path="/VeraMono.ttf" size_px="14" cache="256K"/>
|
||||
</dir>
|
||||
</dir>
|
||||
</vfs>
|
||||
|
@ -1,63 +0,0 @@
|
||||
<config verbose="yes">
|
||||
|
||||
<report init_ram="yes" requested="yes" child_ram="yes" delay_ms="2000" buffer="128K"/>
|
||||
|
||||
<parent-provides>
|
||||
<service name="ROM"/>
|
||||
<service name="PD"/>
|
||||
<service name="RM"/>
|
||||
<service name="CPU"/>
|
||||
<service name="LOG"/>
|
||||
<service name="Nitpicker"/>
|
||||
<service name="Timer"/>
|
||||
<service name="Report"/>
|
||||
<service name="Block"/>
|
||||
<service name="File_system"/>
|
||||
</parent-provides>
|
||||
|
||||
<default-route> <any-service> <parent/> <any-child/> </any-service> </default-route>
|
||||
|
||||
<default caps="100"/>
|
||||
|
||||
<start name="nit_focus">
|
||||
<resource name="RAM" quantum="1M"/>
|
||||
<config>
|
||||
<policy label_prefix="leitzentrale" focus="no"/>
|
||||
<default-policy focus="yes"/>
|
||||
</config>
|
||||
<route>
|
||||
<service name="ROM" label="clicked"> <parent label="clicked"/> </service>
|
||||
<service name="Report" label="focus"> <parent label="focus"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="fs" caps="500">
|
||||
<resource name="RAM" quantum="114M"/>
|
||||
<binary name="init"/>
|
||||
<route>
|
||||
<service name="ROM" label="config">
|
||||
<parent label="config -> subinit/default_fs.config"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
<provides> <service name="File_system"/> </provides>
|
||||
</start>
|
||||
|
||||
<start name="noux" version="fs" caps="1000">
|
||||
<resource name="RAM" quantum="80M"/>
|
||||
<binary name="init"/>
|
||||
<route>
|
||||
<service name="ROM" label="config">
|
||||
<parent label="config -> subinit/default_noux.config"/> </service>
|
||||
<service name="ROM" label="fonts.config">
|
||||
<parent label="config -> fonts.config"/> </service>
|
||||
<service name="File_system" label="config">
|
||||
<parent label="config"/> </service>
|
||||
<service name="File_system" label="target">
|
||||
<child name="fs"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
</config>
|
||||
|
@ -1,8 +1,6 @@
|
||||
<config>
|
||||
<input name="leitzentrale_enabled" rom="leitzentrale" node="leitzentrale">
|
||||
<attribute name="enabled" /> </input>
|
||||
<input name="reset_enabled" rom="reset" node="reset">
|
||||
<attribute name="enabled" /> </input>
|
||||
|
||||
<output node="config">
|
||||
<inline>
|
||||
@ -12,6 +10,7 @@
|
||||
<service name="RM"/>
|
||||
<service name="CPU"/>
|
||||
<service name="LOG"/>
|
||||
<service name="Report"/>
|
||||
<service name="Nitpicker"/>
|
||||
<service name="Timer"/>
|
||||
<service name="File_system"/>
|
||||
@ -20,50 +19,202 @@
|
||||
<default-route> <any-service> <parent/> </any-service> </default-route>
|
||||
|
||||
<default caps="100"/>
|
||||
|
||||
<service name="Nitpicker">
|
||||
<default-policy> <child name="wm"/> </default-policy> </service>
|
||||
|
||||
</inline>
|
||||
<if>
|
||||
<has_value input="leitzentrale_enabled" value="yes" />
|
||||
<then>
|
||||
<inline>
|
||||
<start name="control_fader">
|
||||
<start name="fader">
|
||||
<binary name="nit_fader"/>
|
||||
<resource name="RAM" quantum="19M"/>
|
||||
<resource name="RAM" quantum="22M"/>
|
||||
<provides> <service name="Nitpicker"/> </provides>
|
||||
<config alpha="190"/>
|
||||
</start>
|
||||
<start name="log_fader">
|
||||
<binary name="nit_fader"/>
|
||||
<resource name="RAM" quantum="8M"/>
|
||||
<provides> <service name="Nitpicker"/> </provides>
|
||||
<config alpha="200"/>
|
||||
<config alpha="210"/>
|
||||
<route>
|
||||
<service name="Nitpicker"> <child name="manager"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
</inline>
|
||||
</then>
|
||||
<else>
|
||||
<inline>
|
||||
<start name="control_fader">
|
||||
<start name="fader">
|
||||
<binary name="nit_fader"/>
|
||||
<resource name="RAM" quantum="19M"/>
|
||||
<provides> <service name="Nitpicker"/> </provides>
|
||||
<config alpha="0"/>
|
||||
</start>
|
||||
<start name="log_fader">
|
||||
<binary name="nit_fader"/>
|
||||
<resource name="RAM" quantum="8M"/>
|
||||
<resource name="RAM" quantum="22M"/>
|
||||
<provides> <service name="Nitpicker"/> </provides>
|
||||
<config alpha="0"/>
|
||||
<route>
|
||||
<service name="Nitpicker"> <child name="manager"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
</inline>
|
||||
</else>
|
||||
</if>
|
||||
<inline>
|
||||
<start name="control_nit_fb">
|
||||
<binary name="nit_fb"/>
|
||||
<resource name="RAM" quantum="8M"/>
|
||||
<start name="nit_fb">
|
||||
<resource name="RAM" quantum="10M"/>
|
||||
<provides> <service name="Framebuffer"/> <service name="Input"/> </provides>
|
||||
<config xpos="2" ypos="2" width="-416" height="-4"/>
|
||||
<config/>
|
||||
<route>
|
||||
<service name="Nitpicker"> <child name="control_fader"/> </service>
|
||||
<service name="Nitpicker"> <child name="fader"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="nitpicker" caps="200">
|
||||
<resource name="RAM" quantum="6M"/>
|
||||
<provides> <service name="Nitpicker"/> </provides>
|
||||
<config focus="rom">
|
||||
<background color="#272f45"/>
|
||||
<domain name="default" layer="1" content="client" label="no" hover="always" focus="click"/>
|
||||
<default-policy domain="default"/>
|
||||
</config>
|
||||
<route>
|
||||
<service name="Input"> <child name="nit_fb"/> </service>
|
||||
<service name="Framebuffer"> <child name="nit_fb"/> </service>
|
||||
<service name="ROM" label="focus"> <child name="report_rom"/> </service>
|
||||
<service name="Report"> <child name="report_rom"/> </service>
|
||||
<any-service> <parent/> <any-child/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="report_rom">
|
||||
<resource name="RAM" quantum="4M"/>
|
||||
<provides>
|
||||
<service name="Report"/>
|
||||
<service name="ROM"/>
|
||||
</provides>
|
||||
<config verbose="no">
|
||||
<policy label="layouter -> window_list" report="wm -> window_list"/>
|
||||
<policy label="layouter -> focus_request" report="wm -> focus_request"/>
|
||||
<policy label="decorator -> window_layout" report="layouter -> window_layout"/>
|
||||
<policy label="wm -> resize_request" report="layouter -> resize_request"/>
|
||||
<policy label="decorator -> pointer" report="wm -> pointer"/>
|
||||
<policy label="layouter -> hover" report="decorator -> hover"/>
|
||||
<policy label="layouter -> decorator_margins" report="decorator -> decorator_margins"/>
|
||||
<policy label="wm -> focus" report="layouter -> focus"/>
|
||||
<policy label="gui -> config" report="manager -> gui_config"/>
|
||||
<policy label="gui -> menu_view -> dialog" report="manager -> menu_dialog"/>
|
||||
<policy label="manager -> menu_view_hover" report="gui -> menu_view -> hover"/>
|
||||
<policy label="nitpicker -> focus" report="manager -> focus"/>
|
||||
</config>
|
||||
</start>
|
||||
|
||||
<start name="wm" caps="150">
|
||||
<resource name="RAM" quantum="2M"/>
|
||||
<provides> <service name="Nitpicker"/> </provides>
|
||||
<config>
|
||||
<policy label_prefix="decorator" role="decorator"/>
|
||||
<policy label_prefix="layouter" role="layouter"/>
|
||||
</config>
|
||||
<route>
|
||||
<service name="ROM" label="resize_request"> <child name="report_rom"/> </service>
|
||||
<service name="ROM" label="focus"> <child name="report_rom"/> </service>
|
||||
<service name="Report"> <child name="report_rom"/> </service>
|
||||
<service name="Nitpicker"> <child name="nitpicker"/> </service>
|
||||
<any-service> <parent/> <any-child/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="layouter">
|
||||
<binary name="floating_window_layouter"/>
|
||||
<resource name="RAM" quantum="2M"/>
|
||||
<config/>
|
||||
<route>
|
||||
<service name="ROM" label="window_list"> <child name="report_rom"/> </service>
|
||||
<service name="ROM" label="focus_request"> <child name="report_rom"/> </service>
|
||||
<service name="ROM" label="hover"> <child name="report_rom"/> </service>
|
||||
<service name="ROM" label="decorator_margins"> <child name="report_rom"/> </service>
|
||||
<service name="Report"> <child name="report_rom"/> </service>
|
||||
<service name="Nitpicker"> <child name="wm"/> </service>
|
||||
<any-service> <child name="wm"/> <parent/> <any-child/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="decorator" caps="200">
|
||||
<binary name="themed_decorator"/>
|
||||
<resource name="RAM" quantum="8M"/>
|
||||
<config>
|
||||
<libc/>
|
||||
<vfs> <tar name="plain_decorator_theme.tar"/> </vfs>
|
||||
</config>
|
||||
<route>
|
||||
<service name="ROM" label="window_layout"> <child name="report_rom"/> </service>
|
||||
<service name="ROM" label="pointer"> <child name="report_rom"/> </service>
|
||||
<service name="Report" label="decorator_margins"> <child name="report_rom"/> </service>
|
||||
<service name="Report" label="hover"> <child name="report_rom"/> </service>
|
||||
<service name="Nitpicker"> <child name="wm"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="config_fs_report">
|
||||
<binary name="fs_report"/>
|
||||
<resource name="RAM" quantum="1M"/>
|
||||
<provides> <service name="Report"/> </provides>
|
||||
<config> <vfs> <fs/> </vfs> </config>
|
||||
<route>
|
||||
<service name="File_system"> <parent label="config"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="manager" caps="200">
|
||||
<binary name="sculpt_manager"/>
|
||||
<resource name="RAM" quantum="16M"/>
|
||||
<provides> <service name="Nitpicker"/> </provides>
|
||||
<config/>
|
||||
<route>
|
||||
<service name="Report" label="runtime_config">
|
||||
<child name="config_fs_report" label="managed -> runtime"/> </service>
|
||||
<service name="Report" label="wlan_config">
|
||||
<child name="config_fs_report" label="managed -> wlan"/> </service>
|
||||
<service name="Report" label="fonts_config">
|
||||
<child name="config_fs_report" label="managed -> fonts"/> </service>
|
||||
<service name="Report" label="nic_router_config">
|
||||
<child name="config_fs_report" label="managed -> nic_router"/> </service>
|
||||
<service name="Report" label="fb_drv_config">
|
||||
<child name="config_fs_report" label="managed -> fb_drv"/> </service>
|
||||
<service name="Report" label="input_filter_config">
|
||||
<child name="config_fs_report" label="managed -> input_filter"/> </service>
|
||||
<service name="Report" label="installation_config">
|
||||
<child name="config_fs_report" label="managed -> installation"/> </service>
|
||||
<service name="Report" label="depot_query">
|
||||
<child name="config_fs_report" label="managed -> depot_query"/> </service>
|
||||
<service name="Report"> <child name="report_rom"/> </service>
|
||||
<service name="ROM" label="nitpicker_hover"> <parent/> </service>
|
||||
<service name="ROM" label_prefix="report ->"> <parent/> </service>
|
||||
<service name="ROM" label="menu_view_hover"> <child name="report_rom"/> </service>
|
||||
<service name="Nitpicker"> <parent/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="fonts_fs" caps="100">
|
||||
<binary name="vfs"/>
|
||||
<resource name="RAM" quantum="4M"/>
|
||||
<provides> <service name="File_system"/> </provides>
|
||||
<route>
|
||||
<service name="ROM" label="config">
|
||||
<parent label="config -> managed/fonts"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="gui" caps="1400">
|
||||
<binary name="init"/>
|
||||
<resource name="RAM" quantum="12M"/>
|
||||
<route>
|
||||
<service name="ROM" label="config"> <child name="report_rom"/> </service>
|
||||
<service name="ROM" label_last="dialog"> <child name="report_rom"/> </service>
|
||||
<service name="Nitpicker"> <child name="nitpicker"/> </service>
|
||||
<service name="File_system" label="fonts"> <child name="fonts_fs"/> </service>
|
||||
<service name="Report" label_last="hover"> <child name="report_rom"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
@ -74,7 +225,7 @@
|
||||
<provides> <service name="Framebuffer"/> <service name="Input"/> </provides>
|
||||
<config origin="top_right" xpos="-412" ypos="2" width="410" height="-4"/>
|
||||
<route>
|
||||
<service name="Nitpicker"> <child name="log_fader"/> </service>
|
||||
<service name="Nitpicker"> <child name="nitpicker"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
@ -114,63 +265,11 @@
|
||||
</start>
|
||||
</config>
|
||||
<route>
|
||||
<service name="File_system"> <parent label="report"/> </service>
|
||||
<any-service> <child name="log_terminal"/> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<!--
|
||||
<start name="cpu_load_display">
|
||||
<resource name="RAM" quantum="6M"/>
|
||||
<route>
|
||||
<service name="ROM" label="trace_subjects"> <parent label="trace_subjects"/> </service>
|
||||
<any-service> <parent/> <any-child/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
-->
|
||||
|
||||
</inline>
|
||||
<if>
|
||||
<has_value input="reset_enabled" value="no" />
|
||||
<then>
|
||||
<inline>
|
||||
<start name="control_terminal">
|
||||
<binary name="terminal"/>
|
||||
<resource name="RAM" quantum="8M"/>
|
||||
<provides> <service name="Terminal"/> </provides>
|
||||
<route>
|
||||
<service name="ROM" label="config"> <parent label="fonts.config"/> </service>
|
||||
<any-service> <child name="control_nit_fb"/> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="control_noux" caps="1000">
|
||||
<binary name="noux"/>
|
||||
<resource name="RAM" quantum="48M" />
|
||||
<config>
|
||||
<fstab>
|
||||
<tar name="coreutils-minimal.tar" />
|
||||
<tar name="vim-minimal.tar" />
|
||||
<tar name="bash-minimal.tar" />
|
||||
<dir name="dev"> <zero/> <null/> </dir>
|
||||
<dir name="config"> <fs label="config"/> </dir>
|
||||
<dir name="report"> <fs label="report"/> </dir>
|
||||
<dir name="tmp"> <ram /> </dir>
|
||||
<dir name="share"> <dir name="vim"> <rom name="vimrc"/> </dir> </dir>
|
||||
<rom name="README"/>
|
||||
<rom name="VERSION"/>
|
||||
</fstab>
|
||||
<start name="/bin/bash">
|
||||
<env name="TERM" value="screen" />
|
||||
<env name="PS1" value="genode:$PWD> " />
|
||||
</start>
|
||||
</config>
|
||||
<route>
|
||||
<any-service> <child name="control_terminal"/> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
</inline>
|
||||
</then>
|
||||
</if>
|
||||
</output>
|
||||
</config>
|
||||
|
@ -1,69 +0,0 @@
|
||||
<config>
|
||||
|
||||
<report init_ram="yes" requested="yes" child_ram="yes" delay_ms="2000" buffer="128K"/>
|
||||
|
||||
<parent-provides>
|
||||
<service name="ROM"/>
|
||||
<service name="PD"/>
|
||||
<service name="RM"/>
|
||||
<service name="CPU"/>
|
||||
<service name="LOG"/>
|
||||
<service name="Nitpicker"/>
|
||||
<service name="Timer"/>
|
||||
<service name="Report"/>
|
||||
<service name="Block"/>
|
||||
<service name="File_system"/>
|
||||
</parent-provides>
|
||||
|
||||
<default-route> <any-service> <parent/> <any-child/> </any-service> </default-route>
|
||||
|
||||
<default caps="100"/>
|
||||
|
||||
<start name="fs" caps="500">
|
||||
<resource name="RAM" quantum="114M"/>
|
||||
<binary name="init"/>
|
||||
<route>
|
||||
<service name="ROM" label="config">
|
||||
<parent label="config -> subinit/default_fs.config"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
<provides> <service name="File_system"/> </provides>
|
||||
</start>
|
||||
|
||||
<start name="noux" caps="500" version="initial">
|
||||
<binary name="noux"/>
|
||||
<resource name="RAM" quantum="100M" />
|
||||
<config stdout="/dev/null" stderr="/dev/null" stdin="/dev/null">
|
||||
<fstab>
|
||||
<inline name=".bash_profile">
|
||||
export VERSION=`cat /VERSION`
|
||||
cp /rw/config/$VERSION/* /config/
|
||||
cp /rw/config/$VERSION/subinit/*.config /config/subinit/
|
||||
cp /rw/config/$VERSION/deploy/* /config/deploy/
|
||||
cp /rw/config/$VERSION/leitzentrale/config /config/leitzentrale/
|
||||
cp /rw/config/$VERSION/runtime/*.config /config/runtime/
|
||||
cp /rw/config/$VERSION/runtime/config /config/runtime/
|
||||
</inline>
|
||||
<tar name="bash-minimal.tar" />
|
||||
<tar name="coreutils-minimal.tar" />
|
||||
<dir name="dev"> <zero/> <null/> <log/> </dir>
|
||||
<dir name="rw"> <fs label="target"/> </dir>
|
||||
<dir name="config"> <fs label="config"/> </dir>
|
||||
<rom name="VERSION"/>
|
||||
</fstab>
|
||||
<start name="/bin/bash">
|
||||
<env name="TERM" value="screen" />
|
||||
<env name="PS1" value="fs:$PWD> " />
|
||||
<env name="HOME" value="/" />
|
||||
<arg value="--login"/>
|
||||
</start>
|
||||
</config>
|
||||
<route>
|
||||
<service name="File_system" label="target"> <child name="fs"/> </service>
|
||||
<service name="File_system" label="config"> <parent label="config"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
</config>
|
||||
|
@ -1,5 +1,5 @@
|
||||
<config focus="rom">
|
||||
<report hover="yes" focus="yes" clicked="yes" keystate="no"/>
|
||||
<report hover="yes" focus="yes" clicked="yes" keystate="no" displays="yes"/>
|
||||
<background color="#131415"/>
|
||||
<domain name="pointer" layer="1" content="client" label="no" origin="pointer" />
|
||||
<domain name="leitzentrale" layer="2" content="client" label="no" hover="always" focus="click" />
|
||||
@ -9,8 +9,8 @@
|
||||
<domain name="desktop" layer="4" content="client" label="no" hover="always" focus="click" />
|
||||
<domain name="background" layer="5" content="client" label="no" hover="always" focus="transient" />
|
||||
|
||||
<policy label_prefix="runtime -> dynamic -> wm -> wm -> decorator" domain="decorator"/>
|
||||
<policy label_prefix="runtime -> dynamic -> wm" domain="desktop"/>
|
||||
<policy label_prefix="runtime -> wm -> wm -> decorator" domain="decorator"/>
|
||||
<policy label_prefix="runtime -> wm" domain="desktop"/>
|
||||
|
||||
<policy label_prefix="pointer" domain="pointer"/>
|
||||
<policy label_prefix="leitzentrale -> " domain="leitzentrale"/>
|
||||
@ -22,5 +22,5 @@
|
||||
<global-key name="KEY_DASHBOARD" label="global_keys_handler -> input" />
|
||||
<global-key name="KEY_CAPSLOCK" label="global_keys_handler -> input" />
|
||||
<global-key name="KEY_NUMLOCK" label="global_keys_handler -> input" />
|
||||
<global-key name="KEY_SCREEN" label="runtime -> dynamic -> wm -> wm -> decorator" />
|
||||
<global-key name="KEY_SCREEN" label="runtime -> wm -> wm -> decorator" />
|
||||
</config>
|
||||
|
@ -1,121 +0,0 @@
|
||||
<config verbose="yes" prio_levels="2">
|
||||
|
||||
<report init_ram="yes" requested="yes" child_ram="yes" delay_ms="2000" buffer="128K"/>
|
||||
|
||||
<parent-provides>
|
||||
<service name="ROM"/>
|
||||
<service name="PD"/>
|
||||
<service name="RM"/>
|
||||
<service name="CPU"/>
|
||||
<service name="LOG"/>
|
||||
<service name="Nitpicker"/>
|
||||
<service name="Timer"/>
|
||||
<service name="Block"/>
|
||||
<service name="Report"/>
|
||||
<service name="Rtc"/>
|
||||
<service name="File_system"/>
|
||||
<service name="Platform"/>
|
||||
</parent-provides>
|
||||
|
||||
<default-route> <any-service> <parent/> <any-child/> </any-service> </default-route>
|
||||
|
||||
<default caps="100"/>
|
||||
|
||||
<start name="nic" caps="500">
|
||||
<resource name="RAM" quantum="60M"/>
|
||||
<binary name="init"/>
|
||||
<route>
|
||||
<service name="ROM" label="config">
|
||||
<parent label="config -> subinit/default_nic.config"/> </service>
|
||||
<service name="ROM" label="wlan.config">
|
||||
<parent label="config -> wlan.config"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
<provides> <service name="Nic"/> </provides>
|
||||
</start>
|
||||
|
||||
<start name="nic_router" caps="300">
|
||||
<resource name="RAM" quantum="10M"/>
|
||||
<provides><service name="Nic"/></provides>
|
||||
<config verbose_domain_state="yes">
|
||||
<default-policy domain="default" />
|
||||
<domain name="uplink">
|
||||
<nat domain="default" tcp-ports="1000" udp-ports="1000"/>
|
||||
</domain>
|
||||
<domain name="default" interface="10.0.1.1/24">
|
||||
<dhcp-server ip_first="10.0.1.2"
|
||||
ip_last="10.0.1.200"
|
||||
ip_lease_time_sec="360"
|
||||
dns_server="1.1.1.1"/>
|
||||
<tcp dst="0.0.0.0/0"><permit-any domain="uplink"/></tcp>
|
||||
<udp dst="0.0.0.0/0"><permit-any domain="uplink"/></udp>
|
||||
</domain>
|
||||
</config>
|
||||
<route>
|
||||
<service name="Nic"> <child name="nic"/> </service>
|
||||
<any-service> <parent/> <any-child/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="fs" caps="500">
|
||||
<resource name="RAM" quantum="114M"/>
|
||||
<binary name="init"/>
|
||||
<route>
|
||||
<service name="ROM" label="config">
|
||||
<parent label="config -> subinit/default_fs.config"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
<provides> <service name="File_system"/> </provides>
|
||||
</start>
|
||||
|
||||
<start name="depot_fs" priority="0">
|
||||
<binary name="chroot"/>
|
||||
<resource name="RAM" quantum="1M" />
|
||||
<provides> <service name="File_system"/> </provides>
|
||||
<config> <default-policy path="/depot" writeable="yes"/> </config>
|
||||
<route>
|
||||
<service name="File_system"> <child name="fs"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="public_fs" priority="0">
|
||||
<binary name="chroot"/>
|
||||
<resource name="RAM" quantum="1M" />
|
||||
<provides> <service name="File_system"/> </provides>
|
||||
<config> <default-policy path="/public" writeable="yes"/> </config>
|
||||
<route>
|
||||
<service name="File_system"> <child name="fs"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
<start name="depot_download" caps="2000">
|
||||
<binary name="init"/>
|
||||
<resource name="RAM" quantum="64M"/>
|
||||
<route>
|
||||
<service name="ROM" label="config">
|
||||
<parent label="config -> subinit/depot_download.config"/> </service>
|
||||
<service name="ROM" label_last="installation">
|
||||
<parent label="config -> installation"/> </service>
|
||||
<service name="File_system" label="depot">
|
||||
<child name="depot_fs" label="depot"/> </service>
|
||||
<service name="File_system" label="public">
|
||||
<child name="public_fs" label="public"/> </service>
|
||||
<service name="File_system" label="depot_rw">
|
||||
<child name="depot_fs" label="depot_rw"/> </service>
|
||||
<service name="File_system" label="public_rw">
|
||||
<child name="public_fs" label="public_rw"/> </service>
|
||||
<service name="LOG" label="dynamic -> fetchurl">
|
||||
<parent label="fetchurl"/> </service>
|
||||
<service name="LOG" label="dynamic -> verify">
|
||||
<parent label="verify"/> </service>
|
||||
<service name="LOG" label="dynamic -> extract">
|
||||
<parent label="extract"/> </service>
|
||||
<service name="Nic"> <child name="nic_router"/> </service>
|
||||
<any-service> <parent/> </any-service>
|
||||
</route>
|
||||
</start>
|
||||
|
||||
</config>
|
||||
|
@ -12,7 +12,7 @@ if {![file exists bin/sculpt-ahci.raw]} {
|
||||
catch { exec dd if=/dev/zero of=$disk_image bs=1M count=512 }
|
||||
}
|
||||
append qemu_args " -device ahci,id=ahci "
|
||||
append qemu_args " -drive id=hdd,file=$disk_image,format=raw,if=none -device ide-hd,drive=hdd,bus=ahci.0 "
|
||||
append qemu_args " -drive id=hdd,file=$disk_image,format=raw,if=none -device ide-hd,drive=hdd,bus=ahci.1 "
|
||||
|
||||
# attach small NVMe disk to Qemu to experiment with file-system access
|
||||
if {$use_nvme} {
|
||||
|
@ -217,6 +217,8 @@ class Depot_deploy::Child : public List_model<Child>::Element
|
||||
xml.attribute("source", "no");
|
||||
});
|
||||
}
|
||||
|
||||
bool incomplete() const { return _pkg_incomplete; }
|
||||
};
|
||||
|
||||
|
||||
|
@ -102,6 +102,14 @@ class Depot_deploy::Children
|
||||
_children.for_each([&] (Child const &child) {
|
||||
child.gen_installation_entry(xml); });
|
||||
}
|
||||
|
||||
bool any_incomplete() const {
|
||||
|
||||
bool result = false;
|
||||
_children.for_each([&] (Child const &child) {
|
||||
result |= child.incomplete(); });
|
||||
return result;
|
||||
}
|
||||
};
|
||||
|
||||
#endif /* _CHILDREN_H_ */
|
||||
|
88
repos/gems/src/app/sculpt_manager/deploy.cc
Normal file
88
repos/gems/src/app/sculpt_manager/deploy.cc
Normal file
@ -0,0 +1,88 @@
|
||||
/*
|
||||
* \brief Sculpt deploy management
|
||||
* \author Norman Feske
|
||||
* \date 2018-04-30
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
/* local includes */
|
||||
#include <deploy.h>
|
||||
|
||||
|
||||
void Sculpt::Deploy::handle_deploy()
|
||||
{
|
||||
Xml_node const manual_deploy = _manual_deploy_rom.xml();
|
||||
|
||||
/* determine CPU architecture of deployment */
|
||||
_arch = manual_deploy.attribute_value("arch", Arch());
|
||||
if (!_arch.valid())
|
||||
warning("manual deploy config lacks 'arch' attribute");
|
||||
|
||||
try { _children.apply_config(manual_deploy); }
|
||||
catch (...) {
|
||||
error("spurious exception during deploy update (apply_config)"); }
|
||||
|
||||
/* update query for blueprints of all unconfigured start nodes */
|
||||
if (_arch.valid()) {
|
||||
_depot_query_reporter.generate([&] (Xml_generator &xml) {
|
||||
xml.attribute("arch", _arch);
|
||||
xml.attribute("version", _query_version.value);
|
||||
_children.gen_queries(xml);
|
||||
});
|
||||
}
|
||||
|
||||
/*
|
||||
* Apply blueprint after 'gen_queries'. Otherwise the application of a
|
||||
* stale blueprint may flag children whose pkgs have been installed in the
|
||||
* meanwhile as incomplete, suppressing their respective queries.
|
||||
*/
|
||||
try {
|
||||
Xml_node const blueprint = _blueprint_rom.xml();
|
||||
|
||||
/* apply blueprint, except when stale */
|
||||
typedef String<32> Version;
|
||||
Version const version = blueprint.attribute_value("version", Version());
|
||||
if (version == Version(_query_version.value))
|
||||
_children.apply_blueprint(_blueprint_rom.xml());
|
||||
}
|
||||
catch (...) {
|
||||
error("spurious exception during deploy update (apply_blueprint)"); }
|
||||
|
||||
/* feed missing packages to installation queue */
|
||||
if (!_installation.try_generate_manually_managed())
|
||||
_installation.generate([&] (Xml_generator &xml) {
|
||||
xml.attribute("arch", _arch);
|
||||
_children.gen_installation_entries(xml); });
|
||||
|
||||
_runtime_config_generator.generate_runtime_config();
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Deploy::gen_runtime_start_nodes(Xml_generator &xml) const
|
||||
{
|
||||
xml.node("start", [&] () {
|
||||
gen_fs_rom_start_content(xml, "depot_rom", "depot",
|
||||
depot_rom_state.ram_quota); });
|
||||
|
||||
xml.node("start", [&] () {
|
||||
gen_depot_query_start_content(xml); });
|
||||
|
||||
Xml_node const manual_deploy = _manual_deploy_rom.xml();
|
||||
|
||||
/* insert content of '<static>' node as is */
|
||||
if (manual_deploy.has_sub_node("static")) {
|
||||
Xml_node static_config = manual_deploy.sub_node("static");
|
||||
xml.append(static_config.content_base(), static_config.content_size());
|
||||
}
|
||||
|
||||
/* generate start nodes for deployed packages */
|
||||
if (manual_deploy.has_sub_node("common_routes"))
|
||||
_children.gen_start_nodes(xml, manual_deploy.sub_node("common_routes"),
|
||||
"depot_rom");
|
||||
}
|
121
repos/gems/src/app/sculpt_manager/deploy.h
Normal file
121
repos/gems/src/app/sculpt_manager/deploy.h
Normal file
@ -0,0 +1,121 @@
|
||||
/*
|
||||
* \brief Sculpt deploy management
|
||||
* \author Norman Feske
|
||||
* \date 2018-04-30
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _DEPLOY_H_
|
||||
#define _DEPLOY_H_
|
||||
|
||||
/* Genode includes */
|
||||
#include <base/attached_rom_dataspace.h>
|
||||
#include <os/reporter.h>
|
||||
|
||||
/* included from depot_deploy tool */
|
||||
#include <children.h>
|
||||
|
||||
/* local includes */
|
||||
#include <types.h>
|
||||
#include <runtime.h>
|
||||
#include <managed_config.h>
|
||||
|
||||
namespace Sculpt { struct Deploy; }
|
||||
|
||||
|
||||
struct Sculpt::Deploy
|
||||
{
|
||||
Env &_env;
|
||||
|
||||
Allocator &_alloc;
|
||||
|
||||
Runtime_config_generator &_runtime_config_generator;
|
||||
|
||||
typedef String<16> Arch;
|
||||
Arch _arch { };
|
||||
|
||||
struct Query_version { unsigned value; } _query_version { 0 };
|
||||
|
||||
struct Depot_rom_state { Ram_quota ram_quota; };
|
||||
|
||||
Depot_rom_state depot_rom_state { 32*1024*1024 };
|
||||
|
||||
Attached_rom_dataspace _manual_deploy_rom { _env, "config -> deploy" };
|
||||
|
||||
Attached_rom_dataspace _blueprint_rom { _env, "report -> runtime/depot_query/blueprint" };
|
||||
|
||||
Expanding_reporter _depot_query_reporter { _env, "query", "depot_query"};
|
||||
|
||||
bool _manual_installation_scheduled = false;
|
||||
|
||||
Managed_config<Deploy> _installation {
|
||||
_env, "installation", "installation", *this, &Deploy::_handle_installation };
|
||||
|
||||
void _handle_installation(Xml_node manual_config)
|
||||
{
|
||||
_manual_installation_scheduled = manual_config.has_sub_node("archive");
|
||||
handle_deploy();
|
||||
}
|
||||
|
||||
Depot_deploy::Children _children { _alloc };
|
||||
|
||||
bool update_needed() const
|
||||
{
|
||||
return _manual_installation_scheduled || _children.any_incomplete();
|
||||
}
|
||||
|
||||
void handle_deploy();
|
||||
|
||||
void _handle_manual_deploy()
|
||||
{
|
||||
_manual_deploy_rom.update();
|
||||
_query_version.value++;
|
||||
handle_deploy();
|
||||
}
|
||||
|
||||
void _handle_blueprint()
|
||||
{
|
||||
_blueprint_rom.update();
|
||||
handle_deploy();
|
||||
}
|
||||
|
||||
void gen_runtime_start_nodes(Xml_generator &) const;
|
||||
|
||||
Signal_handler<Deploy> _manual_deploy_handler {
|
||||
_env.ep(), *this, &Deploy::_handle_manual_deploy };
|
||||
|
||||
Signal_handler<Deploy> _blueprint_handler {
|
||||
_env.ep(), *this, &Deploy::_handle_blueprint };
|
||||
|
||||
void restart()
|
||||
{
|
||||
/* ignore stale query results */
|
||||
_query_version.value++;
|
||||
|
||||
_children.apply_config(Xml_node("<config/>"));
|
||||
}
|
||||
|
||||
void reattempt_after_installation()
|
||||
{
|
||||
_children.reset_incomplete();
|
||||
handle_deploy();
|
||||
}
|
||||
|
||||
Deploy(Env &env, Allocator &alloc,
|
||||
Runtime_config_generator &runtime_config_generator)
|
||||
:
|
||||
_env(env), _alloc(alloc),
|
||||
_runtime_config_generator(runtime_config_generator)
|
||||
{
|
||||
_manual_deploy_rom.sigh(_manual_deploy_handler);
|
||||
_blueprint_rom.sigh(_blueprint_handler);
|
||||
}
|
||||
};
|
||||
|
||||
#endif /* _DEPLOY_H_ */
|
104
repos/gems/src/app/sculpt_manager/gui.cc
Normal file
104
repos/gems/src/app/sculpt_manager/gui.cc
Normal file
@ -0,0 +1,104 @@
|
||||
/*
|
||||
* \brief Sculpt GUI management
|
||||
* \author Norman Feske
|
||||
* \date 2018-04-30
|
||||
*
|
||||
* The GUI is based on a dynamically configured init component, which hosts
|
||||
* one menu-view component for each dialog.
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
/* Genode includes */
|
||||
#include <base/log.h>
|
||||
|
||||
/* local includes */
|
||||
#include <gui.h>
|
||||
|
||||
|
||||
void Sculpt::Gui::_gen_menu_view_start_content(Xml_generator &xml,
|
||||
Label const &label,
|
||||
Point pos) const
|
||||
{
|
||||
xml.attribute("version", version.value);
|
||||
|
||||
gen_common_start_content(xml, label, Cap_quota{150}, Ram_quota{8*1024*1024});
|
||||
|
||||
gen_named_node(xml, "binary", "menu_view");
|
||||
|
||||
xml.node("config", [&] () {
|
||||
xml.attribute("xpos", pos.x());
|
||||
xml.attribute("ypos", pos.y());
|
||||
xml.attribute("width", menu_width);
|
||||
xml.node("libc", [&] () { xml.attribute("stderr", "/dev/log"); });
|
||||
xml.node("report", [&] () { xml.attribute("hover", "yes"); });
|
||||
xml.node("vfs", [&] () {
|
||||
gen_named_node(xml, "tar", "menu_view_styles.tar");
|
||||
gen_named_node(xml, "dir", "styles", [&] () {
|
||||
gen_named_node(xml, "dir", "frame", [&] () {
|
||||
gen_named_node(xml, "dir", "logo", [&] () {
|
||||
gen_named_node(xml, "rom", "background.png", [&] () {
|
||||
xml.attribute("label", "genode_logo.png"); }); }); }); });
|
||||
|
||||
gen_named_node(xml, "dir", "fonts", [&] () {
|
||||
xml.node("fs", [&] () {
|
||||
xml.attribute("label", "fonts"); }); });
|
||||
gen_named_node(xml, "dir", "dev", [&] () {
|
||||
xml.node("log", [&] () { }); });
|
||||
});
|
||||
});
|
||||
|
||||
xml.node("route", [&] () {
|
||||
gen_parent_rom_route(xml, "menu_view");
|
||||
gen_parent_rom_route(xml, "ld.lib.so");
|
||||
gen_parent_rom_route(xml, "vfs.lib.so");
|
||||
gen_parent_rom_route(xml, "libc.lib.so");
|
||||
gen_parent_rom_route(xml, "libm.lib.so");
|
||||
gen_parent_rom_route(xml, "libpng.lib.so");
|
||||
gen_parent_rom_route(xml, "zlib.lib.so");
|
||||
gen_parent_rom_route(xml, "menu_view_styles.tar");
|
||||
gen_parent_rom_route(xml, "genode_logo.png");
|
||||
gen_parent_route<Cpu_session> (xml);
|
||||
gen_parent_route<Pd_session> (xml);
|
||||
gen_parent_route<Log_session> (xml);
|
||||
gen_parent_route<Timer::Session> (xml);
|
||||
gen_parent_route<Nitpicker::Session> (xml);
|
||||
|
||||
gen_service_node<Rom_session>(xml, [&] () {
|
||||
xml.attribute("label", "dialog");
|
||||
xml.node("parent", [&] () { }); });
|
||||
|
||||
gen_service_node<Report::Session>(xml, [&] () {
|
||||
xml.attribute("label", "hover");
|
||||
xml.node("parent", [&] () { }); });
|
||||
|
||||
gen_service_node<::File_system::Session>(xml, [&] () {
|
||||
xml.attribute("label", "fonts");
|
||||
xml.node("parent", [&] () {
|
||||
xml.attribute("label", "fonts"); }); });
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Gui::_generate_config(Xml_generator &xml) const
|
||||
{
|
||||
xml.node("parent-provides", [&] () {
|
||||
gen_parent_service<Rom_session>(xml);
|
||||
gen_parent_service<Cpu_session>(xml);
|
||||
gen_parent_service<Pd_session>(xml);
|
||||
gen_parent_service<Log_session>(xml);
|
||||
gen_parent_service<Timer::Session>(xml);
|
||||
gen_parent_service<Report::Session>(xml);
|
||||
gen_parent_service<Nitpicker::Session>(xml);
|
||||
gen_parent_service<::File_system::Session>(xml);
|
||||
});
|
||||
|
||||
xml.node("start", [&] () {
|
||||
_gen_menu_view_start_content(xml, "menu_view", Point(0, 0)); });
|
||||
}
|
||||
|
54
repos/gems/src/app/sculpt_manager/gui.h
Normal file
54
repos/gems/src/app/sculpt_manager/gui.h
Normal file
@ -0,0 +1,54 @@
|
||||
/*
|
||||
* \brief Sculpt GUI management
|
||||
* \author Norman Feske
|
||||
* \date 2018-04-30
|
||||
*
|
||||
* The GUI is based on a dynamically configured init component, which hosts
|
||||
* one menu-view component for each dialog.
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _GUI_H_
|
||||
#define _GUI_H_
|
||||
|
||||
/* Genode includes */
|
||||
#include <os/reporter.h>
|
||||
|
||||
/* local includes */
|
||||
#include <types.h>
|
||||
#include <xml.h>
|
||||
|
||||
namespace Sculpt { struct Gui; }
|
||||
|
||||
|
||||
struct Sculpt::Gui
|
||||
{
|
||||
Env &_env;
|
||||
|
||||
Expanding_reporter _config { _env, "config", "gui_config" };
|
||||
|
||||
typedef String<32> Label;
|
||||
|
||||
struct Version { unsigned value; } version { 0 };
|
||||
|
||||
unsigned menu_width = 0;
|
||||
|
||||
void _gen_menu_view_start_content(Xml_generator &, Label const &, Point) const;
|
||||
|
||||
void _generate_config(Xml_generator &) const;
|
||||
|
||||
void generate_config()
|
||||
{
|
||||
_config.generate([&] (Xml_generator &xml) { _generate_config(xml); });
|
||||
}
|
||||
|
||||
Gui(Env &env) : _env(env) { }
|
||||
};
|
||||
|
||||
#endif /* _GUI_H_ */
|
30
repos/gems/src/app/sculpt_manager/input_event_handler.h
Normal file
30
repos/gems/src/app/sculpt_manager/input_event_handler.h
Normal file
@ -0,0 +1,30 @@
|
||||
/*
|
||||
* \brief Interface for handling input events
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-02
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _INPUT_EVENT_HANDLER_H_
|
||||
#define _INPUT_EVENT_HANDLER_H_
|
||||
|
||||
/* Genode includes */
|
||||
#include <input/event.h>
|
||||
|
||||
/* local includes */
|
||||
#include "types.h"
|
||||
|
||||
namespace Sculpt { struct Input_event_handler; }
|
||||
|
||||
struct Sculpt::Input_event_handler : Interface
|
||||
{
|
||||
virtual void handle_input_event(Input::Event const &) = 0;
|
||||
};
|
||||
|
||||
#endif /* _INPUT_EVENT_HANDLER_H_ */
|
77
repos/gems/src/app/sculpt_manager/keyboard_focus.h
Normal file
77
repos/gems/src/app/sculpt_manager/keyboard_focus.h
Normal file
@ -0,0 +1,77 @@
|
||||
/*
|
||||
* \brief Keyboard-focus policy
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-23
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _KEYBOARD_FOCUS_H_
|
||||
#define _KEYBOARD_FOCUS_H_
|
||||
|
||||
/* Genode includes */
|
||||
#include <os/reporter.h>
|
||||
|
||||
/* local includes */
|
||||
#include <types.h>
|
||||
#include <view/network_dialog.h>
|
||||
|
||||
namespace Sculpt { struct Keyboard_focus; }
|
||||
|
||||
struct Sculpt::Keyboard_focus
|
||||
{
|
||||
enum Target { INITIAL, WPA_PASSPHRASE, WM } target { INITIAL };
|
||||
|
||||
Expanding_reporter _focus_reporter;
|
||||
|
||||
Network_dialog const &_network_dialog;
|
||||
Wpa_passphrase &_wpa_passphrase;
|
||||
|
||||
void update()
|
||||
{
|
||||
Target const orig_target = target;
|
||||
|
||||
target = WM;
|
||||
|
||||
if (_network_dialog.need_keyboard_focus_for_passphrase())
|
||||
target = WPA_PASSPHRASE;
|
||||
|
||||
if (orig_target == target)
|
||||
return;
|
||||
|
||||
if (orig_target == WPA_PASSPHRASE)
|
||||
_wpa_passphrase = Wpa_passphrase { };
|
||||
|
||||
_focus_reporter.generate([&] (Xml_generator &xml) {
|
||||
switch (target) {
|
||||
|
||||
case WPA_PASSPHRASE:
|
||||
xml.attribute("label", "manager -> input");
|
||||
break;
|
||||
|
||||
case INITIAL:
|
||||
case WM:
|
||||
xml.attribute("label", "wm -> ");
|
||||
break;
|
||||
};
|
||||
});
|
||||
}
|
||||
|
||||
Keyboard_focus(Env &env,
|
||||
Network_dialog const &network_dialog,
|
||||
Wpa_passphrase &wpa_passphrase)
|
||||
:
|
||||
_focus_reporter(env, "focus", "focus"),
|
||||
_network_dialog(network_dialog),
|
||||
_wpa_passphrase(wpa_passphrase)
|
||||
{
|
||||
update();
|
||||
}
|
||||
};
|
||||
|
||||
#endif /* _KEYBOARD_FOCUS_H_ */
|
662
repos/gems/src/app/sculpt_manager/main.cc
Normal file
662
repos/gems/src/app/sculpt_manager/main.cc
Normal file
@ -0,0 +1,662 @@
|
||||
/*
|
||||
* \brief Sculpt system manager
|
||||
* \author Norman Feske
|
||||
* \date 2018-04-30
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
/* Genode includes */
|
||||
#include <base/component.h>
|
||||
#include <base/heap.h>
|
||||
#include <base/attached_rom_dataspace.h>
|
||||
#include <os/reporter.h>
|
||||
#include <nitpicker_session/connection.h>
|
||||
|
||||
/* included from depot_deploy tool */
|
||||
#include <children.h>
|
||||
|
||||
/* local includes */
|
||||
#include <model/child_exit_state.h>
|
||||
#include <view/download_status.h>
|
||||
#include <gui.h>
|
||||
#include <nitpicker.h>
|
||||
#include <runtime.h>
|
||||
#include <keyboard_focus.h>
|
||||
#include <network.h>
|
||||
#include <storage.h>
|
||||
#include <deploy.h>
|
||||
|
||||
namespace Sculpt { struct Main; }
|
||||
|
||||
|
||||
struct Sculpt::Main : Input_event_handler,
|
||||
Dialog::Generator,
|
||||
Runtime_config_generator,
|
||||
Runtime_info,
|
||||
Storage::Target_user
|
||||
{
|
||||
Env &_env;
|
||||
|
||||
Heap _heap { _env.ram(), _env.rm() };
|
||||
|
||||
Constructible<Nitpicker::Connection> _nitpicker { };
|
||||
|
||||
Signal_handler<Main> _input_handler {
|
||||
_env.ep(), *this, &Main::_handle_input };
|
||||
|
||||
void _handle_input()
|
||||
{
|
||||
_nitpicker->input()->for_each_event([&] (Input::Event const &ev) {
|
||||
handle_input_event(ev); });
|
||||
}
|
||||
|
||||
Signal_handler<Main> _nitpicker_mode_handler {
|
||||
_env.ep(), *this, &Main::_handle_nitpicker_mode };
|
||||
|
||||
void _handle_nitpicker_mode();
|
||||
|
||||
Managed_config<Main> _fonts_config {
|
||||
_env, "config", "fonts", *this, &Main::_handle_fonts_config };
|
||||
|
||||
void _handle_fonts_config(Xml_node) { _handle_nitpicker_mode(); }
|
||||
|
||||
Managed_config<Main> _input_filter_config {
|
||||
_env, "config", "input_filter", *this, &Main::_handle_input_filter_config };
|
||||
|
||||
void _handle_input_filter_config(Xml_node)
|
||||
{
|
||||
_input_filter_config.try_generate_manually_managed();
|
||||
}
|
||||
|
||||
bool _first_hover_report = true;
|
||||
|
||||
Attached_rom_dataspace _nitpicker_hover { _env, "nitpicker_hover" };
|
||||
|
||||
Signal_handler<Main> _nitpicker_hover_handler {
|
||||
_env.ep(), *this, &Main::_handle_nitpicker_hover };
|
||||
|
||||
void _handle_nitpicker_hover();
|
||||
|
||||
|
||||
/***************************
|
||||
** Configuration loading **
|
||||
***************************/
|
||||
|
||||
Prepare_version _prepare_version { 0 };
|
||||
Prepare_version _prepare_completed { 0 };
|
||||
|
||||
bool _prepare_in_progress() const
|
||||
{
|
||||
return _prepare_version.value != _prepare_completed.value;
|
||||
}
|
||||
|
||||
|
||||
Storage _storage { _env, _heap, *this, *this, *this };
|
||||
|
||||
/**
|
||||
* Storage::Target_user interface
|
||||
*/
|
||||
void use_storage_target(Storage_target const &target) override
|
||||
{
|
||||
_storage._sculpt_partition = target;
|
||||
|
||||
/* trigger loading of the configuration from the sculpt partition */
|
||||
_prepare_version.value++;
|
||||
|
||||
_deploy.restart();
|
||||
|
||||
generate_runtime_config();
|
||||
}
|
||||
|
||||
|
||||
Network _network { _env, _heap, *this, *this, *this };
|
||||
|
||||
|
||||
/************
|
||||
** Update **
|
||||
************/
|
||||
|
||||
Attached_rom_dataspace _update_state_rom {
|
||||
_env, "report -> runtime/update/state" };
|
||||
|
||||
void _handle_update_state();
|
||||
|
||||
Signal_handler<Main> _update_state_handler {
|
||||
_env.ep(), *this, &Main::_handle_update_state };
|
||||
|
||||
bool _update_running() const { return _storage._sculpt_partition.valid()
|
||||
&& !_prepare_in_progress()
|
||||
&& _network.ready()
|
||||
&& _deploy.update_needed(); };
|
||||
|
||||
Deploy _deploy { _env, _heap, *this };
|
||||
|
||||
|
||||
|
||||
/************
|
||||
** Global **
|
||||
************/
|
||||
|
||||
Gui _gui { _env };
|
||||
|
||||
Expanding_reporter _dialog_reporter { _env, "dialog", "menu_dialog" };
|
||||
|
||||
Attached_rom_dataspace _hover_rom { _env, "menu_view_hover" };
|
||||
|
||||
Signal_handler<Main> _hover_handler {
|
||||
_env.ep(), *this, &Main::_handle_hover };
|
||||
|
||||
struct Hovered { enum Dialog { NONE, STORAGE, NETWORK } value; };
|
||||
|
||||
Hovered::Dialog _hovered_dialog { Hovered::NONE };
|
||||
|
||||
template <typename FN>
|
||||
void _apply_to_hovered_dialog(Hovered::Dialog dialog, FN const &fn)
|
||||
{
|
||||
if (dialog == Hovered::STORAGE) fn(_storage.dialog);
|
||||
if (dialog == Hovered::NETWORK) fn(_network.dialog);
|
||||
}
|
||||
|
||||
void _handle_hover();
|
||||
|
||||
/**
|
||||
* Dialog::Generator interface
|
||||
*/
|
||||
void generate_dialog() override
|
||||
{
|
||||
_dialog_reporter.generate([&] (Xml_generator &xml) {
|
||||
|
||||
xml.node("vbox", [&] () {
|
||||
gen_named_node(xml, "frame", "logo", [&] () {
|
||||
xml.node("float", [&] () {
|
||||
xml.node("frame", [&] () {
|
||||
xml.attribute("style", "logo"); }); }); });
|
||||
|
||||
if (_manually_managed_runtime)
|
||||
return;
|
||||
|
||||
_storage.dialog.generate(xml);
|
||||
_network.dialog.generate(xml);
|
||||
|
||||
gen_named_node(xml, "frame", "runtime", [&] () {
|
||||
xml.node("vbox", [&] () {
|
||||
gen_named_node(xml, "label", "title", [&] () {
|
||||
xml.attribute("text", "Runtime");
|
||||
xml.attribute("font", "title/regular");
|
||||
});
|
||||
|
||||
Xml_node const state = _update_state_rom.xml();
|
||||
if (_update_running() && state.has_sub_node("archive"))
|
||||
gen_download_status(xml, state);
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
Attached_rom_dataspace _runtime_state { _env, "report -> runtime/state" };
|
||||
|
||||
/**
|
||||
* Runtime_info interface
|
||||
*/
|
||||
bool present_in_runtime(Start_name const &name) const override
|
||||
{
|
||||
bool present = false;
|
||||
_runtime_state.xml().for_each_sub_node("child", [&] (Xml_node child) {
|
||||
if (child.attribute_value("name", Start_name()) == name)
|
||||
present = true; });
|
||||
return present;
|
||||
}
|
||||
|
||||
Managed_config<Main> _runtime_config {
|
||||
_env, "config", "runtime", *this, &Main::_handle_runtime };
|
||||
|
||||
bool _manually_managed_runtime = false;
|
||||
|
||||
void _handle_runtime(Xml_node config)
|
||||
{
|
||||
_manually_managed_runtime = !config.has_type("empty");
|
||||
generate_runtime_config();
|
||||
generate_dialog();
|
||||
}
|
||||
|
||||
void _generate_runtime_config(Xml_generator &) const;
|
||||
|
||||
/**
|
||||
* Runtime_config_generator interface
|
||||
*/
|
||||
void generate_runtime_config() override
|
||||
{
|
||||
if (!_runtime_config.try_generate_manually_managed())
|
||||
_runtime_config.generate([&] (Xml_generator &xml) {
|
||||
_generate_runtime_config(xml); });
|
||||
}
|
||||
|
||||
Signal_handler<Main> _runtime_state_handler {
|
||||
_env.ep(), *this, &Main::_handle_runtime_state };
|
||||
|
||||
void _handle_runtime_state();
|
||||
|
||||
Keyboard_focus _keyboard_focus { _env, _network.dialog, _network.wpa_passphrase };
|
||||
|
||||
/**
|
||||
* Input_event_handler interface
|
||||
*/
|
||||
void handle_input_event(Input::Event const &ev) override
|
||||
{
|
||||
if (ev.key_press(Input::BTN_LEFT)) {
|
||||
if (_hovered_dialog == Hovered::STORAGE) _storage.dialog.click(_storage);
|
||||
if (_hovered_dialog == Hovered::NETWORK) _network.dialog.click(_network);
|
||||
}
|
||||
|
||||
if (ev.key_release(Input::BTN_LEFT))
|
||||
_storage.dialog.clack(_storage);
|
||||
|
||||
if (_keyboard_focus.target == Keyboard_focus::WPA_PASSPHRASE)
|
||||
ev.handle_press([&] (Input::Keycode, Codepoint code) {
|
||||
_network.handle_key_press(code); });
|
||||
|
||||
if (ev.press())
|
||||
_keyboard_focus.update();
|
||||
}
|
||||
|
||||
Managed_config<Main> _fb_drv_config {
|
||||
_env, "config", "fb_drv", *this, &Main::_handle_fb_drv_config };
|
||||
|
||||
void _handle_fb_drv_config(Xml_node)
|
||||
{
|
||||
_fb_drv_config.try_generate_manually_managed();
|
||||
}
|
||||
|
||||
Attached_rom_dataspace _nitpicker_displays { _env, "displays" };
|
||||
|
||||
Signal_handler<Main> _nitpicker_displays_handler {
|
||||
_env.ep(), *this, &Main::_handle_nitpicker_displays };
|
||||
|
||||
void _handle_nitpicker_displays()
|
||||
{
|
||||
_nitpicker_displays.update();
|
||||
|
||||
if (!_nitpicker_displays.xml().has_sub_node("display"))
|
||||
return;
|
||||
|
||||
if (_nitpicker.constructed())
|
||||
return;
|
||||
|
||||
/*
|
||||
* Since nitpicker has successfully issued the first 'displays' report,
|
||||
* there is a good chance that the framebuffer driver is running. This
|
||||
* is a good time to activate the GUI.
|
||||
*/
|
||||
_nitpicker.construct(_env, "input");
|
||||
_nitpicker->input()->sigh(_input_handler);
|
||||
_nitpicker->mode_sigh(_nitpicker_mode_handler);
|
||||
|
||||
/*
|
||||
* Adjust GUI parameters to initial nitpicker mode
|
||||
*/
|
||||
_handle_nitpicker_mode();
|
||||
|
||||
/*
|
||||
* Avoid 'Constructible<Nitpicker::Root>' because it requires the
|
||||
* definition of 'Nitpicker::Session_component'.
|
||||
*/
|
||||
static Nitpicker::Root gui_nitpicker(_env, _heap, *this);
|
||||
|
||||
_gui.generate_config();
|
||||
}
|
||||
|
||||
Main(Env &env) : _env(env)
|
||||
{
|
||||
_runtime_state.sigh(_runtime_state_handler);
|
||||
_nitpicker_displays.sigh(_nitpicker_displays_handler);
|
||||
|
||||
/*
|
||||
* Subscribe to reports
|
||||
*/
|
||||
_update_state_rom.sigh(_update_state_handler);
|
||||
_nitpicker_hover .sigh(_nitpicker_hover_handler);
|
||||
_hover_rom .sigh(_hover_handler);
|
||||
|
||||
/*
|
||||
* Generate initial configurations
|
||||
*/
|
||||
_network.wifi_disconnect();
|
||||
|
||||
/*
|
||||
* Import initial report content
|
||||
*/
|
||||
_storage.handle_storage_devices_update();
|
||||
_deploy.handle_deploy();
|
||||
|
||||
generate_runtime_config();
|
||||
generate_dialog();
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
void Sculpt::Main::_handle_nitpicker_mode()
|
||||
{
|
||||
if (!_fonts_config.try_generate_manually_managed()) {
|
||||
|
||||
Framebuffer::Mode const mode = _nitpicker->mode();
|
||||
|
||||
float const text_size = (float)mode.height() / 60.0;
|
||||
|
||||
_gui.menu_width = text_size*21;
|
||||
|
||||
_fonts_config.generate([&] (Xml_generator &xml) {
|
||||
xml.node("vfs", [&] () {
|
||||
gen_named_node(xml, "rom", "Vera.ttf");
|
||||
gen_named_node(xml, "rom", "VeraMono.ttf");
|
||||
gen_named_node(xml, "dir", "fonts", [&] () {
|
||||
|
||||
auto gen_ttf_dir = [&] (char const *dir_name,
|
||||
char const *ttf_path, float size_px) {
|
||||
|
||||
gen_named_node(xml, "dir", dir_name, [&] () {
|
||||
gen_named_node(xml, "ttf", "regular", [&] () {
|
||||
xml.attribute("path", ttf_path);
|
||||
xml.attribute("size_px", size_px);
|
||||
xml.attribute("cache", "256K");
|
||||
});
|
||||
});
|
||||
};
|
||||
|
||||
gen_ttf_dir("title", "/Vera.ttf", text_size*1.25);
|
||||
gen_ttf_dir("text", "/Vera.ttf", text_size);
|
||||
gen_ttf_dir("annotation", "/Vera.ttf", text_size*0.8);
|
||||
gen_ttf_dir("monospace", "/VeraMono.ttf", text_size);
|
||||
});
|
||||
});
|
||||
xml.node("default-policy", [&] () { xml.attribute("root", "/fonts"); });
|
||||
});
|
||||
}
|
||||
|
||||
_gui.version.value++;
|
||||
_gui.generate_config();
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Main::_handle_hover()
|
||||
{
|
||||
_hover_rom.update();
|
||||
Xml_node const hover = _hover_rom.xml();
|
||||
|
||||
Hovered::Dialog const orig_hovered_dialog = _hovered_dialog;
|
||||
|
||||
typedef String<32> Top_level_frame;
|
||||
Top_level_frame const top_level_frame =
|
||||
query_attribute<Top_level_frame>(hover, "dialog", "vbox", "frame", "name");
|
||||
|
||||
_hovered_dialog = Hovered::NONE;
|
||||
if (top_level_frame == "network") _hovered_dialog = Hovered::NETWORK;
|
||||
if (top_level_frame == "storage") _hovered_dialog = Hovered::STORAGE;
|
||||
|
||||
if (orig_hovered_dialog != _hovered_dialog)
|
||||
_apply_to_hovered_dialog(orig_hovered_dialog, [&] (Dialog &dialog) {
|
||||
dialog.hover(Xml_node("<hover/>")); });
|
||||
|
||||
_apply_to_hovered_dialog(_hovered_dialog, [&] (Dialog &dialog) {
|
||||
dialog.hover(hover.sub_node("dialog").sub_node("vbox")
|
||||
.sub_node("frame")); });
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Main::_handle_nitpicker_hover()
|
||||
{
|
||||
if (!_first_hover_report)
|
||||
return;
|
||||
|
||||
if (!_storage._discovery_state.discovery_in_progress())
|
||||
return;
|
||||
|
||||
_nitpicker_hover.update();
|
||||
|
||||
Xml_node const hover = _nitpicker_hover.xml();
|
||||
|
||||
if (!hover.has_type("hover"))
|
||||
return;
|
||||
|
||||
_first_hover_report = false;
|
||||
|
||||
if (hover.attribute_value("active", false) == true)
|
||||
_storage._discovery_state.user_intervention = true;
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Main::_handle_update_state()
|
||||
{
|
||||
_update_state_rom.update();
|
||||
generate_dialog();
|
||||
|
||||
bool const installation_complete =
|
||||
!_update_state_rom.xml().has_sub_node("archive");
|
||||
|
||||
if (installation_complete)
|
||||
_deploy.reattempt_after_installation();
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Main::_handle_runtime_state()
|
||||
{
|
||||
_runtime_state.update();
|
||||
|
||||
Xml_node state = _runtime_state.xml();
|
||||
|
||||
bool reconfigure_runtime = false;
|
||||
|
||||
/* check for completed storage operations */
|
||||
_storage._storage_devices.for_each([&] (Storage_device &device) {
|
||||
|
||||
device.for_each_partition([&] (Partition &partition) {
|
||||
|
||||
Storage_target const target { device.label, partition.number };
|
||||
|
||||
if (partition.check_in_progress) {
|
||||
String<64> name(target.label(), ".fsck.ext2");
|
||||
Child_exit_state exit_state(state, name);
|
||||
|
||||
if (exit_state.exited) {
|
||||
if (exit_state.code != 0)
|
||||
error("file-system check failed");
|
||||
if (exit_state.code == 0)
|
||||
log("file-system check succeeded");
|
||||
|
||||
partition.check_in_progress = 0;
|
||||
reconfigure_runtime = true;
|
||||
_storage.dialog.reset_operation();
|
||||
}
|
||||
}
|
||||
|
||||
if (partition.format_in_progress) {
|
||||
String<64> name(target.label(), ".mkfs.ext2");
|
||||
Child_exit_state exit_state(state, name);
|
||||
|
||||
if (exit_state.exited) {
|
||||
if (exit_state.code != 0)
|
||||
error("file-system creation failed");
|
||||
|
||||
partition.format_in_progress = false;
|
||||
partition.file_system.type = File_system::EXT2;
|
||||
|
||||
if (partition.whole_device())
|
||||
device.rediscover();
|
||||
|
||||
reconfigure_runtime = true;
|
||||
_storage.dialog.reset_operation();
|
||||
}
|
||||
}
|
||||
|
||||
/* respond to completion of file-system resize operation */
|
||||
if (partition.fs_resize_in_progress) {
|
||||
Child_exit_state exit_state(state, Start_name(target.label(), ".resize2fs"));
|
||||
if (exit_state.exited) {
|
||||
partition.fs_resize_in_progress = false;
|
||||
reconfigure_runtime = true;
|
||||
device.rediscover();
|
||||
_storage.dialog.reset_operation();
|
||||
}
|
||||
}
|
||||
|
||||
}); /* for each partition */
|
||||
|
||||
/* respond to completion of GPT relabeling */
|
||||
if (device.relabel_in_progress()) {
|
||||
Child_exit_state exit_state(state, device.relabel_start_name());
|
||||
if (exit_state.exited) {
|
||||
device.rediscover();
|
||||
reconfigure_runtime = true;
|
||||
_storage.dialog.reset_operation();
|
||||
}
|
||||
}
|
||||
|
||||
/* respond to completion of GPT expand */
|
||||
if (device.gpt_expand_in_progress()) {
|
||||
Child_exit_state exit_state(state, device.expand_start_name());
|
||||
if (exit_state.exited) {
|
||||
|
||||
/* kick off resize2fs */
|
||||
device.for_each_partition([&] (Partition &partition) {
|
||||
if (partition.gpt_expand_in_progress) {
|
||||
partition.gpt_expand_in_progress = false;
|
||||
partition.fs_resize_in_progress = true;
|
||||
}
|
||||
});
|
||||
|
||||
reconfigure_runtime = true;
|
||||
_storage.dialog.reset_operation();
|
||||
}
|
||||
}
|
||||
|
||||
}); /* for each device */
|
||||
|
||||
/* remove prepare subsystem when finished */
|
||||
{
|
||||
Child_exit_state exit_state(state, "prepare");
|
||||
if (exit_state.exited) {
|
||||
_prepare_completed = _prepare_version;
|
||||
|
||||
/* trigger deployment */
|
||||
_deploy.handle_deploy();
|
||||
|
||||
/* trigger update and deploy */
|
||||
reconfigure_runtime = true;
|
||||
}
|
||||
}
|
||||
|
||||
/* upgrade ram_fs quota on demand */
|
||||
state.for_each_sub_node("child", [&] (Xml_node child) {
|
||||
|
||||
if (child.attribute_value("name", String<16>()) == "ram_fs"
|
||||
&& child.has_sub_node("ram")
|
||||
&& child.sub_node("ram").has_attribute("requested")) {
|
||||
|
||||
_storage._ram_fs_state.ram_quota.value *= 2;
|
||||
reconfigure_runtime = true;
|
||||
generate_dialog();
|
||||
}
|
||||
});
|
||||
|
||||
/* upgrade depot_rom quota on demand */
|
||||
state.for_each_sub_node("child", [&] (Xml_node child) {
|
||||
|
||||
if (child.attribute_value("name", String<16>()) == "depot_rom"
|
||||
&& child.has_sub_node("ram")
|
||||
&& child.sub_node("ram").has_attribute("requested")) {
|
||||
|
||||
_deploy.depot_rom_state.ram_quota.value *= 2;
|
||||
reconfigure_runtime = true;
|
||||
}
|
||||
});
|
||||
|
||||
/*
|
||||
* Re-attempt NIC-router configuration as the uplink may have become
|
||||
* available in the meantime.
|
||||
*/
|
||||
_network.reattempt_nic_router_config();
|
||||
|
||||
if (reconfigure_runtime)
|
||||
generate_runtime_config();
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Main::_generate_runtime_config(Xml_generator &xml) const
|
||||
{
|
||||
xml.attribute("verbose", "yes");
|
||||
|
||||
xml.node("report", [&] () {
|
||||
xml.attribute("init_ram", "yes");
|
||||
xml.attribute("init_caps", "yes");
|
||||
xml.attribute("child_ram", "yes");
|
||||
xml.attribute("delay_ms", 4*500);
|
||||
xml.attribute("buffer", "64K");
|
||||
});
|
||||
|
||||
xml.node("parent-provides", [&] () {
|
||||
gen_parent_service<Rom_session>(xml);
|
||||
gen_parent_service<Cpu_session>(xml);
|
||||
gen_parent_service<Pd_session>(xml);
|
||||
gen_parent_service<Rm_session>(xml);
|
||||
gen_parent_service<Log_session>(xml);
|
||||
gen_parent_service<Timer::Session>(xml);
|
||||
gen_parent_service<Report::Session>(xml);
|
||||
gen_parent_service<Platform::Session>(xml);
|
||||
gen_parent_service<Block::Session>(xml);
|
||||
gen_parent_service<Usb::Session>(xml);
|
||||
gen_parent_service<::File_system::Session>(xml);
|
||||
gen_parent_service<Nitpicker::Session>(xml);
|
||||
gen_parent_service<Rtc::Session>(xml);
|
||||
gen_parent_service<Trace::Session>(xml);
|
||||
});
|
||||
|
||||
_storage.gen_runtime_start_nodes(xml);
|
||||
|
||||
/*
|
||||
* Load configuration and update depot config on the sculpt partition
|
||||
*/
|
||||
if (_storage._sculpt_partition.valid() && _prepare_in_progress())
|
||||
xml.node("start", [&] () {
|
||||
gen_prepare_start_content(xml, _prepare_version); });
|
||||
|
||||
if (_storage.any_file_system_inspected())
|
||||
gen_file_browser(xml, _storage._storage_devices, _storage._ram_fs_state,
|
||||
_storage._file_browser_version);
|
||||
|
||||
/*
|
||||
* Spawn chroot instances for accessing '/depot' and '/public'. The
|
||||
* chroot instances implicitly refer to the 'default_fs_rw'.
|
||||
*/
|
||||
if (_storage._sculpt_partition.valid()) {
|
||||
|
||||
auto chroot = [&] (Start_name const &name, Path const &path, Writeable w) {
|
||||
xml.node("start", [&] () {
|
||||
gen_chroot_start_content(xml, name, path, w); }); };
|
||||
|
||||
chroot("depot_rw", "/depot", WRITEABLE);
|
||||
chroot("depot", "/depot", READ_ONLY);
|
||||
chroot("public_rw", "/public", WRITEABLE);
|
||||
}
|
||||
|
||||
_network.gen_runtime_start_nodes(xml);
|
||||
|
||||
if (_update_running())
|
||||
xml.node("start", [&] () {
|
||||
gen_update_start_content(xml); });
|
||||
|
||||
if (_storage._sculpt_partition.valid() && !_prepare_in_progress())
|
||||
_deploy.gen_runtime_start_nodes(xml);
|
||||
}
|
||||
|
||||
|
||||
void Component::construct(Genode::Env &env)
|
||||
{
|
||||
static Sculpt::Main main(env);
|
||||
}
|
||||
|
99
repos/gems/src/app/sculpt_manager/managed_config.h
Normal file
99
repos/gems/src/app/sculpt_manager/managed_config.h
Normal file
@ -0,0 +1,99 @@
|
||||
/*
|
||||
* \brief Management of configurations that can be overridden by the user
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-25
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _MANAGED_CONFIG_H_
|
||||
#define _MANAGED_CONFIG_H_
|
||||
|
||||
/* Genode includes */
|
||||
#include <os/reporter.h>
|
||||
#include <base/attached_rom_dataspace.h>
|
||||
|
||||
/* local includes */
|
||||
#include <types.h>
|
||||
|
||||
namespace Sculpt { template <typename> struct Managed_config; }
|
||||
|
||||
|
||||
template <typename HANDLER>
|
||||
struct Sculpt::Managed_config
|
||||
{
|
||||
Env &_env;
|
||||
|
||||
typedef String<20> Xml_node_name;
|
||||
typedef String<32> Rom_name;
|
||||
|
||||
enum Mode { MANAGED, MANUAL } _mode { MANAGED };
|
||||
|
||||
HANDLER &_obj;
|
||||
|
||||
void (HANDLER::*_handle) (Xml_node);
|
||||
|
||||
/*
|
||||
* Configuration supplied by the user
|
||||
*/
|
||||
Attached_rom_dataspace _manual_config_rom;
|
||||
|
||||
/*
|
||||
* Resulting configuration
|
||||
*/
|
||||
Expanding_reporter _config;
|
||||
|
||||
Signal_handler<Managed_config> _manual_config_handler {
|
||||
_env.ep(), *this, &Managed_config::_handle_manual_config };
|
||||
|
||||
void _handle_manual_config()
|
||||
{
|
||||
_manual_config_rom.update();
|
||||
|
||||
Xml_node const config = _manual_config_rom.xml();
|
||||
|
||||
_mode = config.has_type("empty") ? MANAGED : MANUAL;
|
||||
|
||||
(_obj.*_handle)(config);
|
||||
}
|
||||
|
||||
/**
|
||||
* \return true if manually-managed configuration could be used
|
||||
*/
|
||||
bool try_generate_manually_managed()
|
||||
{
|
||||
if (_mode == MANAGED)
|
||||
return false;
|
||||
|
||||
/*
|
||||
* If a manually managed config at 'config/' is provided, copy its
|
||||
* content to the effective config at 'config/managed/'.
|
||||
*/
|
||||
_config.generate(_manual_config_rom.xml());
|
||||
return true;
|
||||
}
|
||||
|
||||
template <typename FN>
|
||||
void generate(FN const &fn)
|
||||
{
|
||||
_config.generate([&] (Xml_generator &xml) { fn(xml); });
|
||||
}
|
||||
|
||||
Managed_config(Env &env, Xml_node_name const &xml_node_name,
|
||||
Rom_name const &rom_name,
|
||||
HANDLER &obj, void (HANDLER::*handle) (Xml_node))
|
||||
:
|
||||
_env(env), _obj(obj), _handle(handle),
|
||||
_manual_config_rom(_env, Label("config -> ", rom_name).string()),
|
||||
_config(_env, xml_node_name.string(), Label(rom_name, "_config").string())
|
||||
{
|
||||
_manual_config_rom.sigh(_manual_config_handler);
|
||||
}
|
||||
};
|
||||
|
||||
#endif /* _MANAGED_CONFIG_H_ */
|
82
repos/gems/src/app/sculpt_manager/model/access_point.h
Normal file
82
repos/gems/src/app/sculpt_manager/model/access_point.h
Normal file
@ -0,0 +1,82 @@
|
||||
/*
|
||||
* \brief Representation of a wireless access point
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-07
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _MODEL__ACCESS_POINT_H_
|
||||
#define _MODEL__ACCESS_POINT_H_
|
||||
|
||||
#include "types.h"
|
||||
|
||||
namespace Sculpt {
|
||||
|
||||
struct Access_point;
|
||||
struct Access_point_update_policy;
|
||||
|
||||
typedef List_model<Access_point> Access_points;
|
||||
};
|
||||
|
||||
|
||||
struct Sculpt::Access_point : List_model<Access_point>::Element
|
||||
{
|
||||
typedef String<32> Bssid;
|
||||
typedef String<32> Ssid;
|
||||
|
||||
enum Protection { UNKNOWN, UNPROTECTED, WPA_PSK };
|
||||
|
||||
Bssid const bssid;
|
||||
Ssid const ssid;
|
||||
Protection const protection;
|
||||
|
||||
unsigned quality = 0;
|
||||
|
||||
Access_point(Bssid const &bssid, Ssid const &ssid, Protection protection)
|
||||
: bssid(bssid), ssid(ssid), protection(protection) { }
|
||||
|
||||
bool unprotected() const { return protection == UNPROTECTED; }
|
||||
bool wpa_protected() const { return protection == WPA_PSK; }
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Policy for transforming a 'wlan_accesspoints' report into a list model
|
||||
*/
|
||||
struct Sculpt::Access_point_update_policy : List_model<Access_point>::Update_policy
|
||||
{
|
||||
Allocator &_alloc;
|
||||
|
||||
Access_point_update_policy(Allocator &alloc) : _alloc(alloc) { }
|
||||
|
||||
void destroy_element(Access_point &elem) { destroy(_alloc, &elem); }
|
||||
|
||||
Access_point &create_element(Xml_node node)
|
||||
{
|
||||
auto const protection = node.attribute_value("protection", String<16>());
|
||||
|
||||
return *new (_alloc)
|
||||
Access_point(node.attribute_value("bssid", Access_point::Bssid()),
|
||||
node.attribute_value("ssid", Access_point::Ssid()),
|
||||
protection == "WPA-PSK" ? Access_point::Protection::WPA_PSK :
|
||||
Access_point::Protection::UNPROTECTED);
|
||||
}
|
||||
|
||||
void update_element(Access_point &ap, Xml_node node)
|
||||
{
|
||||
ap.quality = node.attribute_value("quality", 0UL);
|
||||
}
|
||||
|
||||
static bool element_matches_xml_node(Access_point const &elem, Xml_node node)
|
||||
{
|
||||
return node.attribute_value("ssid", Access_point::Ssid()) == elem.ssid;
|
||||
}
|
||||
};
|
||||
|
||||
#endif /* _MODEL__ACCESS_POINT_H_ */
|
73
repos/gems/src/app/sculpt_manager/model/block_device.h
Normal file
73
repos/gems/src/app/sculpt_manager/model/block_device.h
Normal file
@ -0,0 +1,73 @@
|
||||
/*
|
||||
* \brief Representation of AHCI and NVMe devices
|
||||
* \author Norman Feske
|
||||
* \date 2018-04-30
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _MODEL__BLOCK_DEVICE_H_
|
||||
#define _MODEL__BLOCK_DEVICE_H_
|
||||
|
||||
#include "storage_device.h"
|
||||
|
||||
namespace Sculpt {
|
||||
|
||||
struct Block_device;
|
||||
struct Block_device_update_policy;
|
||||
|
||||
typedef List_model<Block_device> Block_devices;
|
||||
};
|
||||
|
||||
|
||||
struct Sculpt::Block_device : List_model<Block_device>::Element,
|
||||
Storage_device
|
||||
{
|
||||
typedef String<16> Model;
|
||||
|
||||
Model const model;
|
||||
|
||||
Block_device(Env &env, Allocator &alloc, Signal_context_capability sigh,
|
||||
Label const &label, Model const &model, Capacity capacity)
|
||||
:
|
||||
Storage_device(env, alloc, label, capacity, sigh), model(model)
|
||||
{ }
|
||||
};
|
||||
|
||||
|
||||
struct Sculpt::Block_device_update_policy : List_model<Block_device>::Update_policy
|
||||
{
|
||||
Env &_env;
|
||||
Allocator &_alloc;
|
||||
|
||||
Signal_context_capability _sigh;
|
||||
|
||||
Block_device_update_policy(Env &env, Allocator &alloc, Signal_context_capability sigh)
|
||||
: _env(env), _alloc(alloc), _sigh(sigh) { }
|
||||
|
||||
void destroy_element(Block_device &elem) { destroy(_alloc, &elem); }
|
||||
|
||||
Block_device &create_element(Xml_node node)
|
||||
{
|
||||
return *new (_alloc)
|
||||
Block_device(_env, _alloc, _sigh,
|
||||
node.attribute_value("label", Block_device::Label()),
|
||||
node.attribute_value("model", Block_device::Model()),
|
||||
Capacity { node.attribute_value("block_size", 0ULL)
|
||||
* node.attribute_value("block_count", 0ULL) });
|
||||
}
|
||||
|
||||
void update_element(Block_device &, Xml_node) { }
|
||||
|
||||
static bool element_matches_xml_node(Block_device const &elem, Xml_node node)
|
||||
{
|
||||
return node.attribute_value("label", Block_device::Label()) == elem.label;
|
||||
}
|
||||
};
|
||||
|
||||
#endif /* _MODEL__BLOCK_DEVICE_H_ */
|
37
repos/gems/src/app/sculpt_manager/model/capacity.h
Normal file
37
repos/gems/src/app/sculpt_manager/model/capacity.h
Normal file
@ -0,0 +1,37 @@
|
||||
/*
|
||||
* \brief Printable byte capacity
|
||||
* \author Norman Feske
|
||||
* \date 2018-04-30
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _MODEL__CAPACITY_H_
|
||||
#define _MODEL__CAPACITY_H_
|
||||
|
||||
#include "types.h"
|
||||
|
||||
namespace Sculpt { struct Capacity; }
|
||||
|
||||
struct Sculpt::Capacity
|
||||
{
|
||||
uint64_t value;
|
||||
|
||||
void print(Output &out) const
|
||||
{
|
||||
uint64_t const KB = 1024, MB = 1024*KB, GB = 1024*MB;
|
||||
typedef String<64> Text;
|
||||
Text const text = (value > GB) ? Text((float)value/GB, " GiB")
|
||||
: (value > MB) ? Text((float)value/MB, " MiB")
|
||||
: (value > KB) ? Text((float)value/KB, " KiB")
|
||||
: Text(value, " bytes");
|
||||
Genode::print(out, text);
|
||||
}
|
||||
};
|
||||
|
||||
#endif /* _MODEL__CAPACITY_H_ */
|
47
repos/gems/src/app/sculpt_manager/model/child_exit_state.h
Normal file
47
repos/gems/src/app/sculpt_manager/model/child_exit_state.h
Normal file
@ -0,0 +1,47 @@
|
||||
/*
|
||||
* \brief Utility for querying the child-exit state from init's state report
|
||||
* \author Norman Feske
|
||||
* \date 2018-04-30
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _MODEL__CHILD_EXIT_STATE_H_
|
||||
#define _MODEL__CHILD_EXIT_STATE_H_
|
||||
|
||||
/* Genode includes */
|
||||
#include <util/xml_node.h>
|
||||
|
||||
/* local includes */
|
||||
#include "types.h"
|
||||
|
||||
namespace Sculpt { struct Child_exit_state; }
|
||||
|
||||
struct Sculpt::Child_exit_state
|
||||
{
|
||||
bool exists = false;
|
||||
bool exited = false;
|
||||
int code = 0;
|
||||
|
||||
typedef String<64> Name;
|
||||
|
||||
Child_exit_state(Xml_node init_state, Name const &name)
|
||||
{
|
||||
init_state.for_each_sub_node("child", [&] (Xml_node child) {
|
||||
if (child.attribute_value("name", Name()) == name) {
|
||||
exists = true;
|
||||
if (child.has_attribute("exited")) {
|
||||
exited = true;
|
||||
code = child.attribute_value("exited", 0L);
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
};
|
||||
|
||||
#endif /* _MODEL__CHILD_EXIT_STATE_H_ */
|
100
repos/gems/src/app/sculpt_manager/model/discovery_state.h
Normal file
100
repos/gems/src/app/sculpt_manager/model/discovery_state.h
Normal file
@ -0,0 +1,100 @@
|
||||
/*
|
||||
* \brief State of automated selection of the sculpt partition
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-16
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _MODEL__DISCOVERY_STATE_H_
|
||||
#define _MODEL__DISCOVERY_STATE_H_
|
||||
|
||||
/* Genode includes */
|
||||
#include <util/xml_node.h>
|
||||
|
||||
/* local includes */
|
||||
#include <types.h>
|
||||
#include <model/storage_target.h>
|
||||
#include <model/storage_devices.h>
|
||||
|
||||
namespace Sculpt { struct Discovery_state; }
|
||||
|
||||
struct Sculpt::Discovery_state
|
||||
{
|
||||
bool user_intervention = false;
|
||||
|
||||
bool _done = false;
|
||||
|
||||
bool discovery_in_progress() const { return !_done; }
|
||||
|
||||
Storage_target detect_default_target(Storage_devices const &devices)
|
||||
{
|
||||
/* apply the automated selection only once */
|
||||
if (_done)
|
||||
return Storage_target { };
|
||||
|
||||
/* user intervention disarms the built-in selection policy */
|
||||
if (user_intervention)
|
||||
return Storage_target { };
|
||||
|
||||
/* defer decision until the low-level device enumeration is complete */
|
||||
if (!devices.all_devices_enumerated())
|
||||
return Storage_target { };
|
||||
|
||||
/*
|
||||
* As long as not all devices are completely known, it is too early to
|
||||
* take a decision.
|
||||
*/
|
||||
bool all_devices_discovered = true;
|
||||
devices.for_each([&] (Storage_device const &device) {
|
||||
if (device.state == Storage_device::UNKNOWN)
|
||||
all_devices_discovered = false; });
|
||||
|
||||
if (!all_devices_discovered)
|
||||
return Storage_target { };
|
||||
|
||||
/*
|
||||
* Search for a partition with the magic label "GENODE*", or - if no
|
||||
* such partition is present - a whole-device file system.
|
||||
*
|
||||
* Prefer USB storage devices over block devices. If no partition with
|
||||
* the magic label is present but a block device that is formatted as
|
||||
* a file system (the Sculpt EA way), this block device is selected.
|
||||
*/
|
||||
Storage_target target { };
|
||||
auto check_partitions = [&] (Storage_device const &device) {
|
||||
|
||||
device.for_each_partition([&] (Partition const &partition) {
|
||||
if (!partition.whole_device()
|
||||
&& partition.label == "GENODE*"
|
||||
&& partition.file_system.accessible())
|
||||
target = Storage_target { device.label, partition.number }; });
|
||||
};
|
||||
|
||||
if (!target.valid())
|
||||
devices.usb_storage_devices.for_each([&] (Storage_device const &device) {
|
||||
check_partitions(device); });
|
||||
|
||||
if (!target.valid())
|
||||
devices.block_devices.for_each([&] (Storage_device const &device) {
|
||||
check_partitions(device); });
|
||||
|
||||
if (!target.valid())
|
||||
devices.block_devices.for_each([&] (Storage_device const &device) {
|
||||
if (device.whole_device
|
||||
&& device.whole_device_partition->file_system.accessible())
|
||||
target = Storage_target { device.label, Partition::Number() }; });
|
||||
|
||||
if (target.valid())
|
||||
_done = true;
|
||||
|
||||
return target;
|
||||
}
|
||||
};
|
||||
|
||||
#endif /* _MODEL__DISCOVERY_STATE_H_ */
|
41
repos/gems/src/app/sculpt_manager/model/nic_state.h
Normal file
41
repos/gems/src/app/sculpt_manager/model/nic_state.h
Normal file
@ -0,0 +1,41 @@
|
||||
/*
|
||||
* \brief State of the NIC session provided by the NIC router
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-08
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _MODEL__NIC_STATE_H_
|
||||
#define _MODEL__NIC_STATE_H_
|
||||
|
||||
#include "types.h"
|
||||
|
||||
namespace Sculpt { struct Nic_state; }
|
||||
|
||||
|
||||
struct Sculpt::Nic_state
|
||||
{
|
||||
typedef String<32> Ipv4;
|
||||
|
||||
Ipv4 ipv4;
|
||||
|
||||
static Nic_state from_xml(Xml_node node)
|
||||
{
|
||||
Ipv4 result { };
|
||||
node.for_each_sub_node("domain", [&] (Xml_node domain) {
|
||||
if (domain.attribute_value("name", String<16>()) == "uplink")
|
||||
result = domain.attribute_value("ipv4", Ipv4()); });
|
||||
|
||||
return Nic_state { result };
|
||||
}
|
||||
|
||||
bool ready() const { return ipv4.valid(); }
|
||||
};
|
||||
|
||||
#endif /* _MODEL__NIC_STATE_H_ */
|
40
repos/gems/src/app/sculpt_manager/model/nic_target.h
Normal file
40
repos/gems/src/app/sculpt_manager/model/nic_target.h
Normal file
@ -0,0 +1,40 @@
|
||||
/*
|
||||
* \brief Argument type for denoting a network interface
|
||||
* \author Norman Feske
|
||||
* \date 2018-04-30
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _MODEL__NIC_TARGET_H_
|
||||
#define _MODEL__NIC_TARGET_H_
|
||||
|
||||
#include "types.h"
|
||||
|
||||
namespace Sculpt { struct Nic_target; }
|
||||
|
||||
|
||||
struct Sculpt::Nic_target : Noncopyable
|
||||
{
|
||||
enum Type { OFF, LOCAL, WIRED, WIFI } type { OFF };
|
||||
|
||||
enum Policy { MANAGED, MANUAL } policy { MANAGED };
|
||||
|
||||
bool manual() const { return policy == MANUAL; }
|
||||
bool managed() const { return policy == MANAGED; }
|
||||
|
||||
bool local() const { return type == LOCAL; }
|
||||
bool wired() const { return type == WIRED; }
|
||||
bool wifi() const { return type == WIFI; }
|
||||
|
||||
bool nic_router_needed() const { return type != OFF; }
|
||||
|
||||
bool ready() const { return type == WIRED || type == WIFI; }
|
||||
};
|
||||
|
||||
#endif /* _MODEL__NIC_TARGET_H_ */
|
170
repos/gems/src/app/sculpt_manager/model/partition.h
Normal file
170
repos/gems/src/app/sculpt_manager/model/partition.h
Normal file
@ -0,0 +1,170 @@
|
||||
/*
|
||||
* \brief Representation of block-device partition
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-02
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _MODEL__PARTITION_H_
|
||||
#define _MODEL__PARTITION_H_
|
||||
|
||||
#include "types.h"
|
||||
#include "capacity.h"
|
||||
|
||||
namespace Sculpt {
|
||||
|
||||
struct File_system;
|
||||
struct Partition;
|
||||
struct Partition_update_policy;
|
||||
|
||||
typedef List_model<Partition> Partitions;
|
||||
};
|
||||
|
||||
|
||||
struct Sculpt::File_system
|
||||
{
|
||||
enum Type { UNKNOWN, EXT2, FAT32 } type;
|
||||
|
||||
bool accessible() const { return type == EXT2 || type == FAT32; }
|
||||
|
||||
bool expandable() const { return type == EXT2; }
|
||||
|
||||
File_system(Type type) : type(type) { }
|
||||
};
|
||||
|
||||
|
||||
struct Sculpt::Partition : List_model<Partition>::Element
|
||||
{
|
||||
typedef String<16> Number;
|
||||
typedef String<32> Label;
|
||||
|
||||
enum Expandable { FIXED_SIZE, EXPANDABLE };
|
||||
|
||||
Number const number;
|
||||
Label const label;
|
||||
Capacity const capacity;
|
||||
|
||||
Expandable const _expandable;
|
||||
|
||||
Label next_label = label; /* used to set/unset the default partition */
|
||||
|
||||
File_system file_system;
|
||||
|
||||
bool check_in_progress = false;
|
||||
bool format_in_progress = false;
|
||||
bool file_system_inspected = false;
|
||||
bool gpt_expand_in_progress = false;
|
||||
bool fs_resize_in_progress = false;
|
||||
|
||||
bool relabel_in_progress() const { return label != next_label; }
|
||||
|
||||
bool expand_in_progress() const { return gpt_expand_in_progress
|
||||
|| fs_resize_in_progress; }
|
||||
|
||||
bool checkable() const { return file_system.type == File_system::EXT2; }
|
||||
|
||||
bool expandable() const
|
||||
{
|
||||
return file_system.expandable() && _expandable == EXPANDABLE;
|
||||
}
|
||||
|
||||
bool idle() const { return !check_in_progress
|
||||
&& !format_in_progress
|
||||
&& !file_system_inspected
|
||||
&& !relabel_in_progress(); }
|
||||
|
||||
bool genode_default() const { return label == "GENODE*"; }
|
||||
bool genode() const { return label == "GENODE" || genode_default(); }
|
||||
|
||||
void toggle_default_label()
|
||||
{
|
||||
if (label == "GENODE") next_label = Label("GENODE*");
|
||||
if (label == "GENODE*") next_label = Label("GENODE");
|
||||
}
|
||||
|
||||
struct Args
|
||||
{
|
||||
Number number;
|
||||
Label label;
|
||||
Capacity capacity;
|
||||
Expandable expandable;
|
||||
File_system::Type fs_type;
|
||||
|
||||
static Args from_xml(Xml_node node)
|
||||
{
|
||||
auto const file_system = node.attribute_value("file_system", String<16>());
|
||||
File_system::Type const fs_type = (file_system == "Ext2") ? File_system::EXT2
|
||||
: (file_system == "FAT32") ? File_system::FAT32
|
||||
: File_system::UNKNOWN;
|
||||
|
||||
Number const number = node.attribute_value("number", Number());
|
||||
|
||||
unsigned long const block_size =
|
||||
node.attribute_value("block_size", 512ULL);
|
||||
|
||||
unsigned long long const expandable =
|
||||
node.attribute_value("expandable", 0ULL);
|
||||
|
||||
return Args { number == "0" ? Number{} : number,
|
||||
node.attribute_value("name", Label()),
|
||||
Capacity { node.attribute_value("length", 0ULL)*block_size },
|
||||
(expandable*block_size > 1024*1024) ? EXPANDABLE : FIXED_SIZE,
|
||||
fs_type };
|
||||
}
|
||||
|
||||
static Args whole_device(Capacity capacity)
|
||||
{
|
||||
return { Number{}, "", capacity, FIXED_SIZE, File_system::UNKNOWN };
|
||||
};
|
||||
};
|
||||
|
||||
Partition(Args const &args)
|
||||
:
|
||||
number(args.number), label(args.label), capacity(args.capacity),
|
||||
_expandable(args.expandable), file_system(args.fs_type)
|
||||
{ }
|
||||
|
||||
bool whole_device() const { return !number.valid(); }
|
||||
};
|
||||
|
||||
|
||||
/**
|
||||
* Policy for transforming a part_blk report into a list of partitions
|
||||
*/
|
||||
struct Sculpt::Partition_update_policy : List_model<Partition>::Update_policy
|
||||
{
|
||||
Allocator &_alloc;
|
||||
|
||||
Partition_update_policy(Allocator &alloc) : _alloc(alloc) { }
|
||||
|
||||
void destroy_element(Partition &elem) { destroy(_alloc, &elem); }
|
||||
|
||||
Partition &create_element(Xml_node node)
|
||||
{
|
||||
return *new (_alloc) Partition(Partition::Args::from_xml(node));
|
||||
}
|
||||
|
||||
void update_element(Partition &, Xml_node) { }
|
||||
|
||||
static bool node_is_element(Xml_node node)
|
||||
{
|
||||
/*
|
||||
* Partition "0" is a pseudo partition that refers to the whole device
|
||||
* with no partition table.
|
||||
*/
|
||||
return (node.attribute_value("number", Partition::Number()) != "0");
|
||||
}
|
||||
|
||||
static bool element_matches_xml_node(Partition const &elem, Xml_node node)
|
||||
{
|
||||
return node.attribute_value("number", Partition::Number()) == elem.number;
|
||||
}
|
||||
};
|
||||
|
||||
#endif /* _MODEL__PARTITION_H_ */
|
36
repos/gems/src/app/sculpt_manager/model/ram_fs_state.h
Normal file
36
repos/gems/src/app/sculpt_manager/model/ram_fs_state.h
Normal file
@ -0,0 +1,36 @@
|
||||
/*
|
||||
* \brief Runtime state of the RAM file system
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-15
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _MODEL__RAM_FS_STATE_H_
|
||||
#define _MODEL__RAM_FS_STATE_H_
|
||||
|
||||
/* Genode includes */
|
||||
#include <util/xml_node.h>
|
||||
|
||||
/* local includes */
|
||||
#include "types.h"
|
||||
|
||||
namespace Sculpt { struct Ram_fs_state; }
|
||||
|
||||
struct Sculpt::Ram_fs_state : Noncopyable
|
||||
{
|
||||
static Ram_quota initial_ram() { return Ram_quota{1024*1024}; }
|
||||
|
||||
Ram_quota ram_quota = initial_ram();
|
||||
|
||||
struct Version { unsigned value; } version { 0 };
|
||||
|
||||
bool inspected = false;
|
||||
};
|
||||
|
||||
#endif /* _MODEL__RAM_FS_STATE_H_ */
|
252
repos/gems/src/app/sculpt_manager/model/storage_device.h
Normal file
252
repos/gems/src/app/sculpt_manager/model/storage_device.h
Normal file
@ -0,0 +1,252 @@
|
||||
/*
|
||||
* \brief Common representation of all storage devices
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-02
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _MODEL__STORAGE_DEVICE_H_
|
||||
#define _MODEL__STORAGE_DEVICE_H_
|
||||
|
||||
#include "types.h"
|
||||
#include "partition.h"
|
||||
#include "capacity.h"
|
||||
#include "xml.h"
|
||||
|
||||
namespace Sculpt { struct Storage_device; };
|
||||
|
||||
|
||||
struct Sculpt::Storage_device
|
||||
{
|
||||
enum State {
|
||||
UNKNOWN, /* partition information not yet known */
|
||||
USED, /* part_blk is running and has reported partition info */
|
||||
RELEASED /* partition info is known but part_blk is not running */
|
||||
};
|
||||
|
||||
Allocator &_alloc;
|
||||
|
||||
typedef String<32> Label;
|
||||
|
||||
Label const label;
|
||||
|
||||
Capacity capacity; /* non-const because USB storage devices need to update it */
|
||||
|
||||
State state { UNKNOWN };
|
||||
|
||||
bool whole_device = false;
|
||||
|
||||
Reconstructible<Partition> whole_device_partition {
|
||||
Partition::Args::whole_device(capacity) };
|
||||
|
||||
Partitions partitions { };
|
||||
|
||||
Attached_rom_dataspace _partitions_rom;
|
||||
|
||||
unsigned _part_blk_version = 0;
|
||||
|
||||
/**
|
||||
* Trigger the rediscovery of the device, e.g., after partitioning of after
|
||||
* formatting the whole device.
|
||||
*/
|
||||
void rediscover()
|
||||
{
|
||||
state = UNKNOWN;
|
||||
_part_blk_version++;
|
||||
|
||||
Partition_update_policy policy(_alloc);
|
||||
partitions.update_from_xml(policy, Xml_node("<partitions/>"));
|
||||
}
|
||||
|
||||
void process_part_blk_report()
|
||||
{
|
||||
_partitions_rom.update();
|
||||
|
||||
Xml_node const report = _partitions_rom.xml();
|
||||
if (!report.has_type("partitions"))
|
||||
return;
|
||||
|
||||
whole_device = (report.attribute_value("type", String<16>()) == "disk");
|
||||
|
||||
Partition_update_policy policy(_alloc);
|
||||
partitions.update_from_xml(policy, report);
|
||||
|
||||
/*
|
||||
* Import whole-device partition information.
|
||||
*
|
||||
* Ignore reports that come in while the device is in use. Otherwise,
|
||||
* the reconstruction of 'whole_device_partition' would wrongly reset
|
||||
* the partition state such as the 'file_system_inspected' flag.
|
||||
*/
|
||||
if (!whole_device_partition.constructed() || whole_device_partition->idle()) {
|
||||
whole_device_partition.construct(Partition::Args::whole_device(capacity));
|
||||
report.for_each_sub_node("partition", [&] (Xml_node partition) {
|
||||
if (partition.attribute_value("number", Partition::Number()) == "0")
|
||||
whole_device_partition.construct(Partition::Args::from_xml(partition)); });
|
||||
}
|
||||
|
||||
/* finish initial discovery phase */
|
||||
if (state == UNKNOWN)
|
||||
state = RELEASED;
|
||||
}
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*
|
||||
* \param label label of block device
|
||||
* \param sigh signal handler to be notified on partition-info updates
|
||||
*/
|
||||
Storage_device(Env &env, Allocator &alloc, Label const &label,
|
||||
Capacity capacity, Signal_context_capability sigh)
|
||||
:
|
||||
_alloc(alloc), label(label), capacity(capacity),
|
||||
_partitions_rom(env, String<80>("report -> runtime/", label, ".part_blk/partitions").string())
|
||||
{
|
||||
_partitions_rom.sigh(sigh);
|
||||
process_part_blk_report();
|
||||
}
|
||||
|
||||
~Storage_device()
|
||||
{
|
||||
/* release partition info */
|
||||
rediscover();
|
||||
}
|
||||
|
||||
bool part_blk_needed_for_discovery() const
|
||||
{
|
||||
return state == UNKNOWN;
|
||||
}
|
||||
|
||||
bool part_blk_needed_for_access() const
|
||||
{
|
||||
bool needed_for_access = false;
|
||||
partitions.for_each([&] (Partition const &partition) {
|
||||
needed_for_access |= partition.check_in_progress;
|
||||
needed_for_access |= partition.format_in_progress;
|
||||
needed_for_access |= partition.file_system_inspected;
|
||||
needed_for_access |= partition.fs_resize_in_progress;
|
||||
});
|
||||
|
||||
if (whole_device_partition->format_in_progress
|
||||
|| whole_device_partition->check_in_progress) {
|
||||
needed_for_access = false;
|
||||
}
|
||||
|
||||
return needed_for_access;
|
||||
}
|
||||
|
||||
/**
|
||||
* Generate content of start node for part_blk
|
||||
*
|
||||
* \param service_name name of server that provides the block device, or
|
||||
* if invalid, request block device from parent.
|
||||
*/
|
||||
inline void gen_part_blk_start_content(Xml_generator &xml, Label const &server_name) const;
|
||||
|
||||
template <typename FN>
|
||||
void for_each_partition(FN const &fn) const
|
||||
{
|
||||
fn(*whole_device_partition);
|
||||
partitions.for_each([&] (Partition const &partition) { fn(partition); });
|
||||
}
|
||||
|
||||
template <typename FN>
|
||||
void for_each_partition(FN const &fn)
|
||||
{
|
||||
fn(*whole_device_partition);
|
||||
partitions.for_each([&] (Partition &partition) { fn(partition); });
|
||||
}
|
||||
|
||||
bool all_partitions_idle() const
|
||||
{
|
||||
bool idle = true;
|
||||
partitions.for_each([&] (Partition const &partition) {
|
||||
idle &= partition.idle(); });
|
||||
return idle;
|
||||
}
|
||||
|
||||
bool relabel_in_progress() const
|
||||
{
|
||||
bool result = false;
|
||||
partitions.for_each([&] (Partition const &partition) {
|
||||
result |= partition.relabel_in_progress(); });
|
||||
return result;
|
||||
}
|
||||
|
||||
bool gpt_expand_in_progress() const
|
||||
{
|
||||
bool result = false;
|
||||
partitions.for_each([&] (Partition const &partition) {
|
||||
result |= partition.gpt_expand_in_progress; });
|
||||
return result;
|
||||
}
|
||||
|
||||
bool fs_resize_in_progress() const
|
||||
{
|
||||
bool result = false;
|
||||
partitions.for_each([&] (Partition const &partition) {
|
||||
result |= partition.fs_resize_in_progress; });
|
||||
return result;
|
||||
}
|
||||
|
||||
bool expand_in_progress() const
|
||||
{
|
||||
return gpt_expand_in_progress() || fs_resize_in_progress();
|
||||
}
|
||||
|
||||
Start_name relabel_start_name() const { return Start_name(label, ".relabel"); }
|
||||
Start_name expand_start_name() const { return Start_name(label, ".expand"); }
|
||||
};
|
||||
|
||||
|
||||
void Sculpt::Storage_device::gen_part_blk_start_content(Xml_generator &xml,
|
||||
Label const &server_name) const
|
||||
{
|
||||
xml.attribute("version", _part_blk_version);
|
||||
|
||||
gen_common_start_content(xml, Label(label, ".part_blk"),
|
||||
Cap_quota{100}, Ram_quota{8*1024*1024});
|
||||
|
||||
gen_named_node(xml, "binary", "part_blk");
|
||||
|
||||
xml.node("config", [&] () {
|
||||
xml.node("report", [&] () { xml.attribute("partitions", "yes"); });
|
||||
|
||||
for (unsigned i = 1; i < 10; i++) {
|
||||
xml.node("policy", [&] () {
|
||||
xml.attribute("label", i);
|
||||
xml.attribute("partition", i);
|
||||
xml.attribute("writeable", "yes");
|
||||
});
|
||||
}
|
||||
});
|
||||
|
||||
gen_provides<Block::Session>(xml);
|
||||
|
||||
xml.node("route", [&] () {
|
||||
gen_parent_rom_route(xml, "part_blk");
|
||||
gen_parent_rom_route(xml, "ld.lib.so");
|
||||
gen_parent_route<Cpu_session> (xml);
|
||||
gen_parent_route<Pd_session> (xml);
|
||||
gen_parent_route<Log_session> (xml);
|
||||
|
||||
gen_service_node<Block::Session>(xml, [&] () {
|
||||
if (server_name.valid())
|
||||
gen_named_node(xml, "child", server_name);
|
||||
else
|
||||
xml.node("parent", [&] () {
|
||||
xml.attribute("label", label); }); });
|
||||
|
||||
gen_service_node<Report::Session>(xml, [&] () {
|
||||
xml.attribute("label", "partitions");
|
||||
xml.node("parent", [&] () { }); });
|
||||
});
|
||||
}
|
||||
|
||||
#endif /* _MODEL__STORAGE_DEVICE_H_ */
|
86
repos/gems/src/app/sculpt_manager/model/storage_devices.h
Normal file
86
repos/gems/src/app/sculpt_manager/model/storage_devices.h
Normal file
@ -0,0 +1,86 @@
|
||||
/*
|
||||
* \brief Registry of known storage devices
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-03
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _MODEL__STORAGE_DEVICES_
|
||||
#define _MODEL__STORAGE_DEVICES_
|
||||
|
||||
#include "types.h"
|
||||
#include "block_device.h"
|
||||
#include "usb_storage_device.h"
|
||||
|
||||
namespace Sculpt { struct Storage_devices; }
|
||||
|
||||
|
||||
struct Sculpt::Storage_devices
|
||||
{
|
||||
Block_devices block_devices { };
|
||||
Usb_storage_devices usb_storage_devices { };
|
||||
|
||||
bool _block_devices_report_valid = false;
|
||||
bool _usb_active_config_valid = false;
|
||||
|
||||
/**
|
||||
* Update 'block_devices' from 'block_devices' report
|
||||
*/
|
||||
template <typename POLICY>
|
||||
void update_block_devices_from_xml(POLICY &policy, Xml_node node)
|
||||
{
|
||||
block_devices.update_from_xml(policy, node);
|
||||
|
||||
if (node.has_type("block_devices"))
|
||||
_block_devices_report_valid = true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Update 'usb_storage_devices' from 'usb_active_config' report
|
||||
*/
|
||||
template <typename POLICY>
|
||||
void update_usb_storage_devices_from_xml(POLICY &policy, Xml_node node)
|
||||
{
|
||||
usb_storage_devices.update_from_xml(policy, node);
|
||||
|
||||
if (node.has_type("raw"))
|
||||
_usb_active_config_valid = true;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return true as soon as the storage-device information from the drivers
|
||||
* subsystem is complete.
|
||||
*/
|
||||
bool all_devices_enumerated() const
|
||||
{
|
||||
return _block_devices_report_valid && _usb_active_config_valid;
|
||||
}
|
||||
|
||||
template <typename FN>
|
||||
void for_each(FN const &fn) const
|
||||
{
|
||||
block_devices.for_each([&] (Block_device const &dev) {
|
||||
fn(dev); });
|
||||
|
||||
usb_storage_devices.for_each([&] (Usb_storage_device const &dev) {
|
||||
fn(dev); });
|
||||
}
|
||||
|
||||
template <typename FN>
|
||||
void for_each(FN const &fn)
|
||||
{
|
||||
block_devices.for_each([&] (Block_device &dev) {
|
||||
fn(dev); });
|
||||
|
||||
usb_storage_devices.for_each([&] (Usb_storage_device &dev) {
|
||||
fn(dev); });
|
||||
}
|
||||
};
|
||||
|
||||
#endif /* _MODEL__STORAGE_DEVICES_ */
|
85
repos/gems/src/app/sculpt_manager/model/storage_target.h
Normal file
85
repos/gems/src/app/sculpt_manager/model/storage_target.h
Normal file
@ -0,0 +1,85 @@
|
||||
/*
|
||||
* \brief Argument type for denoting a storage target
|
||||
* \author Norman Feske
|
||||
* \date 2018-04-30
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _MODEL__STORAGE_TARGET_H_
|
||||
#define _MODEL__STORAGE_TARGET_H_
|
||||
|
||||
#include "types.h"
|
||||
#include "storage_device.h"
|
||||
|
||||
namespace Sculpt { struct Storage_target; }
|
||||
|
||||
|
||||
struct Sculpt::Storage_target
|
||||
{
|
||||
typedef String<Storage_device::Label::capacity() + 4> Label;
|
||||
|
||||
Storage_device::Label device;
|
||||
Partition::Number partition;
|
||||
|
||||
bool operator == (Storage_target const &other) const
|
||||
{
|
||||
return (device == other.device) && (partition == other.partition);
|
||||
}
|
||||
|
||||
bool operator != (Storage_target const &other) const { return !(*this == other); }
|
||||
|
||||
bool valid() const { return device.valid(); }
|
||||
|
||||
/**
|
||||
* Return string to be used as session label referring to the target
|
||||
*/
|
||||
Label label() const
|
||||
{
|
||||
return partition.valid() ? Label(device, ".", partition) : Label(device);
|
||||
}
|
||||
|
||||
Label fs() const { return Label(label(), ".fs"); }
|
||||
|
||||
bool ram_fs() const { return device == "ram_fs"; }
|
||||
|
||||
void gen_block_session_route(Xml_generator &xml) const
|
||||
{
|
||||
bool const ahci = (Label(Cstring(device.string(), 4)) == "ahci");
|
||||
bool const nvme = (Label(Cstring(device.string(), 4)) == "nvme");
|
||||
bool const usb = (Label(Cstring(device.string(), 3)) == "usb");
|
||||
|
||||
bool const whole_device = !partition.valid();
|
||||
|
||||
xml.node("service", [&] () {
|
||||
xml.attribute("name", Block::Session::service_name());
|
||||
|
||||
if (whole_device) {
|
||||
|
||||
if (ahci || nvme)
|
||||
xml.node("parent", [&] () { xml.attribute("label", device); });
|
||||
|
||||
if (usb)
|
||||
xml.node("child", [&] () {
|
||||
xml.attribute("name", Label(device, ".drv"));
|
||||
xml.attribute("label", partition);
|
||||
});
|
||||
}
|
||||
|
||||
/* access partition */
|
||||
else {
|
||||
xml.node("child", [&] () {
|
||||
xml.attribute("name", Label(device, ".part_blk"));
|
||||
xml.attribute("label", partition);
|
||||
});
|
||||
}
|
||||
});
|
||||
}
|
||||
};
|
||||
|
||||
#endif /* _MODEL__STORAGE_TARGET_H_ */
|
172
repos/gems/src/app/sculpt_manager/model/usb_storage_device.h
Normal file
172
repos/gems/src/app/sculpt_manager/model/usb_storage_device.h
Normal file
@ -0,0 +1,172 @@
|
||||
/*
|
||||
* \brief Representation of USB storage devices
|
||||
* \author Norman Feske
|
||||
* \date 2018-04-30
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _MODEL__USB_STORAGE_DEVICE_H_
|
||||
#define _MODEL__USB_STORAGE_DEVICE_H_
|
||||
|
||||
#include "storage_device.h"
|
||||
|
||||
namespace Sculpt {
|
||||
|
||||
struct Usb_storage_device;
|
||||
struct Usb_storage_device_update_policy;
|
||||
|
||||
typedef List_model<Usb_storage_device> Usb_storage_devices;
|
||||
};
|
||||
|
||||
|
||||
struct Sculpt::Usb_storage_device : List_model<Usb_storage_device>::Element,
|
||||
Storage_device
|
||||
{
|
||||
/**
|
||||
* Information that is reported asynchronously by 'usb_block_drv'
|
||||
*/
|
||||
struct Driver_info
|
||||
{
|
||||
typedef String<28> Vendor;
|
||||
typedef String<48> Product;
|
||||
|
||||
Vendor const vendor;
|
||||
Product const product;
|
||||
|
||||
Driver_info(Xml_node device)
|
||||
:
|
||||
vendor (device.attribute_value("vendor", Vendor())),
|
||||
product(device.attribute_value("product", Product()))
|
||||
{ }
|
||||
};
|
||||
|
||||
/* information provided asynchronously by usb_block_drv */
|
||||
Constructible<Driver_info> driver_info { };
|
||||
|
||||
Attached_rom_dataspace _driver_report_rom;
|
||||
|
||||
void process_driver_report()
|
||||
{
|
||||
_driver_report_rom.update();
|
||||
|
||||
Xml_node report = _driver_report_rom.xml();
|
||||
|
||||
if (!report.has_sub_node("device"))
|
||||
return;
|
||||
|
||||
Xml_node device = report.sub_node("device");
|
||||
|
||||
capacity = Capacity { device.attribute_value("block_count", 0ULL)
|
||||
* device.attribute_value("block_size", 0ULL) };
|
||||
|
||||
driver_info.construct(device);
|
||||
}
|
||||
|
||||
bool usb_block_drv_needed() const
|
||||
{
|
||||
bool drv_needed = false;
|
||||
for_each_partition([&] (Partition const &partition) {
|
||||
drv_needed |= partition.check_in_progress
|
||||
|| partition.format_in_progress
|
||||
|| partition.file_system_inspected
|
||||
|| partition.relabel_in_progress()
|
||||
|| partition.expand_in_progress(); });
|
||||
|
||||
return drv_needed || Storage_device::state == UNKNOWN;
|
||||
}
|
||||
|
||||
Label usb_block_drv_name() const { return Label(label, ".drv"); }
|
||||
|
||||
Usb_storage_device(Env &env, Allocator &alloc, Signal_context_capability sigh,
|
||||
Label const &label)
|
||||
:
|
||||
Storage_device(env, alloc, label, Capacity{0}, sigh),
|
||||
_driver_report_rom(env, String<80>("report -> runtime/", usb_block_drv_name(),
|
||||
"/devices").string())
|
||||
{
|
||||
_driver_report_rom.sigh(sigh);
|
||||
process_driver_report();
|
||||
}
|
||||
|
||||
inline void gen_usb_block_drv_start_content(Xml_generator &xml) const;
|
||||
};
|
||||
|
||||
|
||||
void Sculpt::Usb_storage_device::gen_usb_block_drv_start_content(Xml_generator &xml) const
|
||||
{
|
||||
gen_common_start_content(xml, usb_block_drv_name(),
|
||||
Cap_quota{100}, Ram_quota{4*1024*1024});
|
||||
|
||||
gen_named_node(xml, "binary", "usb_block_drv");
|
||||
|
||||
xml.node("config", [&] () {
|
||||
xml.attribute("report", "yes");
|
||||
xml.attribute("writeable", "yes");
|
||||
});
|
||||
|
||||
gen_provides<Block::Session>(xml);
|
||||
|
||||
xml.node("route", [&] () {
|
||||
gen_parent_rom_route(xml, "usb_block_drv");
|
||||
gen_parent_rom_route(xml, "ld.lib.so");
|
||||
gen_parent_route<Cpu_session> (xml);
|
||||
gen_parent_route<Pd_session> (xml);
|
||||
gen_parent_route<Log_session> (xml);
|
||||
gen_parent_route<Timer::Session> (xml);
|
||||
|
||||
gen_service_node<Usb::Session>(xml, [&] () {
|
||||
xml.node("parent", [&] () {
|
||||
xml.attribute("label", label); }); });
|
||||
|
||||
gen_service_node<Report::Session>(xml, [&] () {
|
||||
xml.node("parent", [&] () { }); });
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
struct Sculpt::Usb_storage_device_update_policy
|
||||
:
|
||||
List_model<Usb_storage_device>::Update_policy
|
||||
{
|
||||
Env &_env;
|
||||
Allocator &_alloc;
|
||||
|
||||
Signal_context_capability _sigh;
|
||||
|
||||
Usb_storage_device_update_policy(Env &env, Allocator &alloc,
|
||||
Signal_context_capability sigh)
|
||||
:
|
||||
_env(env), _alloc(alloc), _sigh(sigh)
|
||||
{ }
|
||||
|
||||
typedef Usb_storage_device::Label Label;
|
||||
|
||||
void destroy_element(Usb_storage_device &elem) { destroy(_alloc, &elem); }
|
||||
|
||||
Usb_storage_device &create_element(Xml_node node)
|
||||
{
|
||||
return *new (_alloc)
|
||||
Usb_storage_device(_env, _alloc, _sigh,
|
||||
node.attribute_value("label_suffix", Label()));
|
||||
}
|
||||
|
||||
void update_element(Usb_storage_device &, Xml_node) { }
|
||||
|
||||
static bool node_is_element(Xml_node node)
|
||||
{
|
||||
return node.attribute_value("class", String<32>()) == "storage";
|
||||
};
|
||||
|
||||
static bool element_matches_xml_node(Usb_storage_device const &elem, Xml_node node)
|
||||
{
|
||||
return node.attribute_value("label_suffix", Label()) == elem.label;
|
||||
}
|
||||
};
|
||||
|
||||
#endif /* _MODEL__BLOCK_DEVICE_H_ */
|
60
repos/gems/src/app/sculpt_manager/model/wifi_connection.h
Normal file
60
repos/gems/src/app/sculpt_manager/model/wifi_connection.h
Normal file
@ -0,0 +1,60 @@
|
||||
/*
|
||||
* \brief Connection state of the wireless driver
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-08
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _MODEL__WIFI_CONNECTION_H_
|
||||
#define _MODEL__WIFI_CONNECTION_H_
|
||||
|
||||
#include "access_point.h"
|
||||
|
||||
namespace Sculpt { struct Wifi_connection; }
|
||||
|
||||
|
||||
struct Sculpt::Wifi_connection
|
||||
{
|
||||
enum State { DISCONNECTED, CONNECTING, CONNECTED };
|
||||
|
||||
State state;
|
||||
|
||||
Access_point::Bssid bssid;
|
||||
Access_point::Ssid ssid;
|
||||
|
||||
/**
|
||||
* Create 'Wifi_connection' object from 'wlan_state' report
|
||||
*/
|
||||
static Wifi_connection from_xml(Xml_node node)
|
||||
{
|
||||
bool const connected =
|
||||
node.has_sub_node("accesspoint") &&
|
||||
node.sub_node("accesspoint").attribute("state").has_value("connected");
|
||||
|
||||
if (!connected)
|
||||
return { .state = DISCONNECTED,
|
||||
.bssid = Access_point::Bssid{},
|
||||
.ssid = Access_point::Bssid{} };
|
||||
|
||||
Xml_node const ap = node.sub_node("accesspoint");
|
||||
|
||||
return { .state = CONNECTED,
|
||||
.bssid = ap.attribute_value("bssid", Access_point::Bssid()),
|
||||
.ssid = ap.attribute_value("ssid", Access_point::Ssid()) };
|
||||
}
|
||||
|
||||
static Wifi_connection disconnected_wifi_connection()
|
||||
{
|
||||
return Wifi_connection { DISCONNECTED, Access_point::Bssid{}, Access_point::Ssid{} };
|
||||
}
|
||||
|
||||
bool connected() const { return state == CONNECTED; }
|
||||
};
|
||||
|
||||
#endif /* _MODEL__WIFI_CONNECTION_H_ */
|
122
repos/gems/src/app/sculpt_manager/model/wpa_passphrase.h
Normal file
122
repos/gems/src/app/sculpt_manager/model/wpa_passphrase.h
Normal file
@ -0,0 +1,122 @@
|
||||
/*
|
||||
* \brief WPA passphrase
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-23
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _MODEL__WPA_PASSPHRASE_H_
|
||||
#define _MODEL__WPA_PASSPHRASE_H_
|
||||
|
||||
#include <base/output.h>
|
||||
#include <util/utf8.h>
|
||||
#include <types.h>
|
||||
#include <xml.h>
|
||||
|
||||
namespace Sculpt {
|
||||
struct Blind_wpa_passphrase;
|
||||
struct Wpa_passphrase;
|
||||
}
|
||||
|
||||
|
||||
struct Sculpt::Blind_wpa_passphrase
|
||||
{
|
||||
virtual void print_bullets(Output &) const = 0;
|
||||
|
||||
virtual ~Blind_wpa_passphrase() { }
|
||||
|
||||
void print(Output &out) const { print_bullets(out); }
|
||||
|
||||
virtual bool suitable_for_connect() const = 0;
|
||||
};
|
||||
|
||||
|
||||
struct Sculpt::Wpa_passphrase : Blind_wpa_passphrase
|
||||
{
|
||||
private:
|
||||
|
||||
enum { CAPACITY = 64 };
|
||||
Codepoint _characters[CAPACITY] { };
|
||||
|
||||
unsigned _length = 0;
|
||||
|
||||
public:
|
||||
|
||||
/**
|
||||
* Print PSK as UTF-8 string
|
||||
*/
|
||||
void print(Output &out) const
|
||||
{
|
||||
/*
|
||||
* XXX duplicated from gems/src/server/terminal/main.cc
|
||||
*/
|
||||
struct Utf8 { char b0, b1, b2, b3, b4; };
|
||||
|
||||
auto utf8_from_codepoint = [] (unsigned c) {
|
||||
|
||||
/* extract 'n' bits 'at' bit position of value 'c' */
|
||||
auto bits = [c] (unsigned at, unsigned n) {
|
||||
return (c >> at) & ((1 << n) - 1); };
|
||||
|
||||
return (c < 2<<7) ? Utf8 { char(bits( 0, 7)), 0, 0, 0, 0 }
|
||||
: (c < 2<<11) ? Utf8 { char(bits( 6, 5) | 0xc0),
|
||||
char(bits( 0, 6) | 0x80), 0, 0, 0 }
|
||||
: (c < 2<<16) ? Utf8 { char(bits(12, 4) | 0xe0),
|
||||
char(bits( 6, 6) | 0x80),
|
||||
char(bits( 0, 6) | 0x80), 0, 0 }
|
||||
: (c < 2<<21) ? Utf8 { char(bits(18, 3) | 0xf0),
|
||||
char(bits(12, 6) | 0x80),
|
||||
char(bits( 6, 6) | 0x80),
|
||||
char(bits( 0, 6) | 0x80), 0 }
|
||||
: Utf8 { };
|
||||
};
|
||||
|
||||
for (unsigned i = 0; i < _length; i++) {
|
||||
|
||||
Utf8 const utf8 = utf8_from_codepoint(_characters[i].value);
|
||||
|
||||
auto _print = [&] (char c) {
|
||||
if (c)
|
||||
Genode::print(out, Char(c)); };
|
||||
|
||||
_print(utf8.b0); _print(utf8.b1); _print(utf8.b2);
|
||||
_print(utf8.b3); _print(utf8.b4);
|
||||
}
|
||||
}
|
||||
|
||||
void append_character(Codepoint c)
|
||||
{
|
||||
if (_length < CAPACITY) {
|
||||
_characters[_length] = c;
|
||||
_length++;
|
||||
}
|
||||
}
|
||||
|
||||
void remove_last_character()
|
||||
{
|
||||
if (_length > 0) {
|
||||
_length--;
|
||||
_characters[_length].value = 0;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Print passphrase as a number of bullets
|
||||
*/
|
||||
void print_bullets(Output &out) const override
|
||||
{
|
||||
char const bullet_utf8[4] = { (char)0xe2, (char)0x80, (char)0xa2, 0 };
|
||||
for (unsigned i = 0; i < _length; i++)
|
||||
Genode::print(out, bullet_utf8);
|
||||
}
|
||||
|
||||
bool suitable_for_connect() const override { return _length >= 8; }
|
||||
};
|
||||
|
||||
#endif /* _MODEL__WPA_PASSPHRASE_H_ */
|
202
repos/gems/src/app/sculpt_manager/network.cc
Normal file
202
repos/gems/src/app/sculpt_manager/network.cc
Normal file
@ -0,0 +1,202 @@
|
||||
/*
|
||||
* \brief Sculpt network management
|
||||
* \author Norman Feske
|
||||
* \date 2018-04-30
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
/* local includes */
|
||||
#include <network.h>
|
||||
|
||||
|
||||
void Sculpt::Network::handle_key_press(Codepoint code)
|
||||
{
|
||||
enum { BACKSPACE = 8, ENTER = 10 };
|
||||
if (code.value == BACKSPACE)
|
||||
wpa_passphrase.remove_last_character();
|
||||
else if (code.value == ENTER)
|
||||
wifi_connect(dialog.selected_ap());
|
||||
else if (code.value != 0)
|
||||
wpa_passphrase.append_character(code);
|
||||
|
||||
/*
|
||||
* Keep updating the passphase when pressing keys after
|
||||
* clicking the connect button once.
|
||||
*/
|
||||
if (_wifi_connection.state == Wifi_connection::CONNECTING)
|
||||
wifi_connect(_wifi_connection.bssid);
|
||||
|
||||
_dialog_generator.generate_dialog();
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Network::_generate_nic_router_config()
|
||||
{
|
||||
if ((_nic_target.wired() && !_runtime_info.present_in_runtime("nic_drv"))
|
||||
|| (_nic_target.wifi() && !_runtime_info.present_in_runtime("wifi_drv"))) {
|
||||
|
||||
/* defer NIC router reconfiguration until the needed uplink is present */
|
||||
_nic_router_config_up_to_date = false;
|
||||
return;
|
||||
}
|
||||
|
||||
_nic_router_config_up_to_date = true;
|
||||
|
||||
if (_nic_router_config.try_generate_manually_managed())
|
||||
return;
|
||||
|
||||
if (!_nic_target.nic_router_needed()) {
|
||||
_nic_router_config.generate([&] (Xml_generator &xml) {
|
||||
xml.attribute("verbose_domain_state", "yes"); });
|
||||
return;
|
||||
}
|
||||
|
||||
_nic_router_config.generate([&] (Xml_generator &xml) {
|
||||
xml.attribute("verbose_domain_state", "yes");
|
||||
|
||||
xml.node("report", [&] () {
|
||||
xml.attribute("interval_sec", "5");
|
||||
xml.attribute("bytes", "yes");
|
||||
xml.attribute("config", "yes");
|
||||
xml.attribute("config_triggers", "yes");
|
||||
});
|
||||
|
||||
xml.node("default-policy", [&] () {
|
||||
xml.attribute("domain", "default"); });
|
||||
|
||||
if (_nic_target.type != Nic_target::LOCAL) {
|
||||
gen_named_node(xml, "domain", "uplink", [&] () {
|
||||
switch (_nic_target.type) {
|
||||
case Nic_target::WIRED: xml.attribute("label", "wired"); break;
|
||||
case Nic_target::WIFI: xml.attribute("label", "wifi"); break;
|
||||
default: break;
|
||||
}
|
||||
xml.node("nat", [&] () {
|
||||
xml.attribute("domain", "default");
|
||||
xml.attribute("tcp-ports", "1000");
|
||||
xml.attribute("udp-ports", "1000");
|
||||
xml.attribute("icmp-ids", "1000");
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
gen_named_node(xml, "domain", "default", [&] () {
|
||||
xml.attribute("interface", "10.0.1.1/24");
|
||||
|
||||
xml.node("dhcp-server", [&] () {
|
||||
xml.attribute("ip_first", "10.0.1.2");
|
||||
xml.attribute("ip_last", "10.0.1.200");
|
||||
if (_nic_target.type != Nic_target::LOCAL) {
|
||||
xml.attribute("dns_server_from", "uplink"); }
|
||||
});
|
||||
|
||||
if (_nic_target.type != Nic_target::LOCAL) {
|
||||
xml.node("tcp", [&] () {
|
||||
xml.attribute("dst", "0.0.0.0/0");
|
||||
xml.node("permit-any", [&] () {
|
||||
xml.attribute("domain", "uplink"); }); });
|
||||
|
||||
xml.node("udp", [&] () {
|
||||
xml.attribute("dst", "0.0.0.0/0");
|
||||
xml.node("permit-any", [&] () {
|
||||
xml.attribute("domain", "uplink"); }); });
|
||||
|
||||
xml.node("icmp", [&] () {
|
||||
xml.attribute("dst", "0.0.0.0/0");
|
||||
xml.attribute("domain", "uplink"); });
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Network::_handle_wlan_accesspoints()
|
||||
{
|
||||
bool const initial_scan = !_wlan_accesspoints_rom.xml().has_sub_node("accesspoint");
|
||||
|
||||
_wlan_accesspoints_rom.update();
|
||||
|
||||
/* suppress updating the list while the access-point list is hovered */
|
||||
if (!initial_scan && dialog.ap_list_hovered())
|
||||
return;
|
||||
|
||||
Access_point_update_policy policy(_alloc);
|
||||
_access_points.update_from_xml(policy, _wlan_accesspoints_rom.xml());
|
||||
_dialog_generator.generate_dialog();
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Network::_handle_wlan_state()
|
||||
{
|
||||
_wlan_state_rom.update();
|
||||
_wifi_connection = Wifi_connection::from_xml(_wlan_state_rom.xml());
|
||||
_dialog_generator.generate_dialog();
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Network::_handle_nic_router_state()
|
||||
{
|
||||
_nic_router_state_rom.update();
|
||||
|
||||
Nic_state const old_nic_state = _nic_state;
|
||||
_nic_state = Nic_state::from_xml(_nic_router_state_rom.xml());
|
||||
|
||||
if (_nic_state.ipv4 != old_nic_state.ipv4)
|
||||
_dialog_generator.generate_dialog();
|
||||
|
||||
/* if the nic state becomes ready, consider spawning the update subsystem */
|
||||
if (old_nic_state.ready() != _nic_state.ready())
|
||||
_runtime_config_generator.generate_runtime_config();
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Network::_handle_nic_router_config(Xml_node config)
|
||||
{
|
||||
_nic_target.policy = config.has_type("empty")
|
||||
? Nic_target::MANAGED : Nic_target::MANUAL;
|
||||
|
||||
/* obtain uplink information from configuration */
|
||||
Nic_target::Type target = Nic_target::LOCAL;
|
||||
target = Nic_target::LOCAL;
|
||||
|
||||
if (!config.has_sub_node("domain"))
|
||||
target = Nic_target::OFF;
|
||||
|
||||
config.for_each_sub_node("domain", [&] (Xml_node domain) {
|
||||
|
||||
/* skip non-uplink domains */
|
||||
if (domain.attribute_value("name", String<16>()) != "uplink")
|
||||
return;
|
||||
|
||||
if (domain.attribute_value("label", String<16>()) == "wired")
|
||||
target = Nic_target::WIRED;
|
||||
|
||||
if (domain.attribute_value("label", String<16>()) == "wifi")
|
||||
target = Nic_target::WIFI;
|
||||
});
|
||||
|
||||
nic_target(target);
|
||||
_generate_nic_router_config();
|
||||
_runtime_config_generator.generate_runtime_config();
|
||||
_dialog_generator.generate_dialog();
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Network::gen_runtime_start_nodes(Xml_generator &xml) const
|
||||
{
|
||||
if (_use_nic_drv)
|
||||
xml.node("start", [&] () { gen_nic_drv_start_content(xml); });
|
||||
|
||||
if (_use_wifi_drv)
|
||||
xml.node("start", [&] () { gen_wifi_drv_start_content(xml); });
|
||||
|
||||
if (_nic_target.type != Nic_target::OFF)
|
||||
xml.node("start", [&] () {
|
||||
gen_nic_router_start_content(xml); });
|
||||
}
|
203
repos/gems/src/app/sculpt_manager/network.h
Normal file
203
repos/gems/src/app/sculpt_manager/network.h
Normal file
@ -0,0 +1,203 @@
|
||||
/*
|
||||
* \brief Sculpt network management
|
||||
* \author Norman Feske
|
||||
* \date 2018-04-30
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _NETWORK_H_
|
||||
#define _NETWORK_H_
|
||||
|
||||
/* Genode includes */
|
||||
#include <base/attached_rom_dataspace.h>
|
||||
#include <os/reporter.h>
|
||||
|
||||
/* local includes */
|
||||
#include <model/child_exit_state.h>
|
||||
#include <view/network_dialog.h>
|
||||
#include <gui.h>
|
||||
#include <runtime.h>
|
||||
#include <keyboard_focus.h>
|
||||
#include <managed_config.h>
|
||||
|
||||
namespace Sculpt { struct Network; }
|
||||
|
||||
|
||||
struct Sculpt::Network : Network_dialog::Action
|
||||
{
|
||||
Env &_env;
|
||||
|
||||
Allocator &_alloc;
|
||||
|
||||
Dialog::Generator &_dialog_generator;
|
||||
|
||||
Runtime_config_generator &_runtime_config_generator;
|
||||
|
||||
Runtime_info const &_runtime_info;
|
||||
|
||||
Nic_target _nic_target { };
|
||||
Nic_state _nic_state { };
|
||||
|
||||
bool _nic_router_config_up_to_date = false;
|
||||
|
||||
Wpa_passphrase wpa_passphrase { };
|
||||
|
||||
bool _use_nic_drv = false;
|
||||
bool _use_wifi_drv = false;
|
||||
|
||||
Attached_rom_dataspace _wlan_accesspoints_rom {
|
||||
_env, "report -> runtime/wifi_drv/wlan_accesspoints" };
|
||||
|
||||
Attached_rom_dataspace _wlan_state_rom {
|
||||
_env, "report -> runtime/wifi_drv/wlan_state" };
|
||||
|
||||
Attached_rom_dataspace _nic_router_state_rom {
|
||||
_env, "report -> runtime/nic_router/state" };
|
||||
|
||||
void _generate_nic_router_config();
|
||||
|
||||
Access_points _access_points { };
|
||||
|
||||
Wifi_connection _wifi_connection = Wifi_connection::disconnected_wifi_connection();
|
||||
|
||||
void gen_runtime_start_nodes(Xml_generator &xml) const;
|
||||
|
||||
bool ready() const { return _nic_target.ready() && _nic_state.ready(); }
|
||||
|
||||
void handle_key_press(Codepoint);
|
||||
|
||||
void _handle_wlan_accesspoints();
|
||||
void _handle_wlan_state();
|
||||
void _handle_nic_router_state();
|
||||
void _handle_nic_router_config(Xml_node);
|
||||
|
||||
Managed_config<Network> _nic_router_config {
|
||||
_env, "config", "nic_router", *this, &Network::_handle_nic_router_config };
|
||||
|
||||
Signal_handler<Network> _wlan_accesspoints_handler {
|
||||
_env.ep(), *this, &Network::_handle_wlan_accesspoints };
|
||||
|
||||
Signal_handler<Network> _wlan_state_handler {
|
||||
_env.ep(), *this, &Network::_handle_wlan_state };
|
||||
|
||||
Signal_handler<Network> _nic_router_state_handler {
|
||||
_env.ep(), *this, &Network::_handle_nic_router_state };
|
||||
|
||||
Network_dialog::Wlan_config_policy _wlan_config_policy =
|
||||
Network_dialog::WLAN_CONFIG_MANAGED;
|
||||
|
||||
Network_dialog dialog {
|
||||
_env, _dialog_generator, _nic_target, _access_points,
|
||||
_wifi_connection, _nic_state, wpa_passphrase, _wlan_config_policy };
|
||||
|
||||
Managed_config<Network> _wlan_config {
|
||||
_env, "selected_network", "wlan", *this, &Network::_handle_wlan_config };
|
||||
|
||||
void _handle_wlan_config(Xml_node)
|
||||
{
|
||||
if (_wlan_config.try_generate_manually_managed()) {
|
||||
_wlan_config_policy = Network_dialog::WLAN_CONFIG_MANUAL;
|
||||
_dialog_generator.generate_dialog();
|
||||
return;
|
||||
}
|
||||
|
||||
_wlan_config_policy = Network_dialog::WLAN_CONFIG_MANAGED;;
|
||||
|
||||
if (_wifi_connection.connected())
|
||||
wifi_connect(_wifi_connection.bssid);
|
||||
else
|
||||
wifi_disconnect();
|
||||
}
|
||||
|
||||
void reattempt_nic_router_config()
|
||||
{
|
||||
if (_nic_target.nic_router_needed() && !_nic_router_config_up_to_date)
|
||||
_generate_nic_router_config();
|
||||
}
|
||||
|
||||
/**
|
||||
* Network_dialog::Action interface
|
||||
*/
|
||||
void nic_target(Nic_target::Type const type) override
|
||||
{
|
||||
/*
|
||||
* Start drivers on first use but never remove them to avoid
|
||||
* driver-restarting issues.
|
||||
*/
|
||||
if (type == Nic_target::WIFI) _use_wifi_drv = true;
|
||||
if (type == Nic_target::WIRED) _use_nic_drv = true;
|
||||
|
||||
if (type != _nic_target.type) {
|
||||
_nic_target.type = type;
|
||||
_generate_nic_router_config();
|
||||
_runtime_config_generator.generate_runtime_config();
|
||||
_dialog_generator.generate_dialog();
|
||||
}
|
||||
}
|
||||
|
||||
void wifi_connect(Access_point::Bssid bssid) override
|
||||
{
|
||||
_access_points.for_each([&] (Access_point const &ap) {
|
||||
if (ap.bssid != bssid)
|
||||
return;
|
||||
|
||||
_wifi_connection.ssid = ap.ssid;
|
||||
_wifi_connection.bssid = ap.bssid;
|
||||
_wifi_connection.state = Wifi_connection::CONNECTING;
|
||||
|
||||
_wlan_config.generate([&] (Xml_generator &xml) {
|
||||
xml.attribute("ssid", ap.ssid);
|
||||
if (ap.protection == Access_point::WPA_PSK) {
|
||||
xml.attribute("protection", "WPA-PSK");
|
||||
String<128> const psk(wpa_passphrase);
|
||||
xml.attribute("psk", psk);
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
void wifi_disconnect() override
|
||||
{
|
||||
/*
|
||||
* Reflect state change immediately to the user interface even
|
||||
* if the wifi driver will take a while to perform the disconnect.
|
||||
*/
|
||||
_wifi_connection = Wifi_connection::disconnected_wifi_connection();
|
||||
|
||||
_wlan_config.generate([&] (Xml_generator &xml) {
|
||||
|
||||
/* generate attributes to ease subsequent manual tweaking */
|
||||
xml.attribute("ssid", "");
|
||||
xml.attribute("protection", "WPA-PSK");
|
||||
xml.attribute("psk", "");
|
||||
});
|
||||
|
||||
_runtime_config_generator.generate_runtime_config();
|
||||
}
|
||||
|
||||
Network(Env &env, Allocator &alloc, Dialog::Generator &dialog_generator,
|
||||
Runtime_config_generator &runtime_config_generator,
|
||||
Runtime_info const &runtime_info)
|
||||
:
|
||||
_env(env), _alloc(alloc), _dialog_generator(dialog_generator),
|
||||
_runtime_config_generator(runtime_config_generator),
|
||||
_runtime_info(runtime_info)
|
||||
{
|
||||
_generate_nic_router_config();
|
||||
|
||||
/*
|
||||
* Subscribe to reports
|
||||
*/
|
||||
_wlan_accesspoints_rom.sigh(_wlan_accesspoints_handler);
|
||||
_wlan_state_rom .sigh(_wlan_state_handler);
|
||||
_nic_router_state_rom .sigh(_nic_router_state_handler);
|
||||
}
|
||||
};
|
||||
|
||||
#endif /* _NETWORK_H_ */
|
131
repos/gems/src/app/sculpt_manager/nitpicker.cc
Normal file
131
repos/gems/src/app/sculpt_manager/nitpicker.cc
Normal file
@ -0,0 +1,131 @@
|
||||
/*
|
||||
* \brief Nitpicker wrapper for monitoring the user input of GUI components
|
||||
* \author Norman Feske
|
||||
* \date 2018-04-30
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#include "nitpicker.h"
|
||||
|
||||
/* Genode includes */
|
||||
#include <input/component.h>
|
||||
#include <nitpicker_session/connection.h>
|
||||
#include <base/heap.h>
|
||||
|
||||
struct Nitpicker::Session_component : Rpc_object<Nitpicker::Session>
|
||||
{
|
||||
Env &_env;
|
||||
|
||||
Input_event_handler &_event_handler;
|
||||
|
||||
Nitpicker::Connection _connection;
|
||||
|
||||
Input::Session_component _input_component { _env, _env.ram() };
|
||||
|
||||
Signal_handler<Session_component> _input_handler {
|
||||
_env.ep(), *this, &Session_component::_handle_input };
|
||||
|
||||
void _handle_input()
|
||||
{
|
||||
_connection.input()->for_each_event([&] (Input::Event ev) {
|
||||
|
||||
/* handle event locally within the sculpt manager */
|
||||
_event_handler.handle_input_event(ev);
|
||||
|
||||
_input_component.submit(ev);
|
||||
});
|
||||
}
|
||||
|
||||
Session_component(Env &env, char const *args, Input_event_handler &event_handler)
|
||||
:
|
||||
_env(env), _event_handler(event_handler),
|
||||
_connection(env, session_label_from_args(args).string())
|
||||
{
|
||||
_connection.input()->sigh(_input_handler);
|
||||
_env.ep().manage(_input_component);
|
||||
_input_component.event_queue().enabled(true);
|
||||
}
|
||||
|
||||
~Session_component() { _env.ep().dissolve(_input_component); }
|
||||
|
||||
void upgrade(Session::Resources const &resources)
|
||||
{
|
||||
_connection.upgrade(resources);
|
||||
}
|
||||
|
||||
Framebuffer::Session_capability framebuffer_session() override {
|
||||
return _connection.framebuffer_session(); }
|
||||
|
||||
Input::Session_capability input_session() override {
|
||||
return _input_component.cap(); }
|
||||
|
||||
View_handle create_view(View_handle parent) override {
|
||||
return _connection.create_view(parent); }
|
||||
|
||||
void destroy_view(View_handle view) override {
|
||||
_connection.destroy_view(view); }
|
||||
|
||||
View_handle view_handle(View_capability view_cap, View_handle handle) override {
|
||||
return _connection.view_handle(view_cap, handle); }
|
||||
|
||||
View_capability view_capability(View_handle view) override {
|
||||
return _connection.view_capability(view); }
|
||||
|
||||
void release_view_handle(View_handle view) override {
|
||||
_connection.release_view_handle(view); }
|
||||
|
||||
Dataspace_capability command_dataspace() override {
|
||||
return _connection.command_dataspace(); }
|
||||
|
||||
void execute() override {
|
||||
_connection.execute(); }
|
||||
|
||||
Framebuffer::Mode mode() override {
|
||||
return _connection.mode(); }
|
||||
|
||||
void mode_sigh(Signal_context_capability sigh) override {
|
||||
_connection.mode_sigh(sigh); }
|
||||
|
||||
void buffer(Framebuffer::Mode mode, bool use_alpha) override {
|
||||
_connection.buffer(mode, use_alpha); }
|
||||
|
||||
void focus(Capability<Nitpicker::Session> session) override {
|
||||
_connection.focus(session); }
|
||||
};
|
||||
|
||||
|
||||
Nitpicker::Session_component *Nitpicker::Root::_create_session(const char *args)
|
||||
{
|
||||
return new (md_alloc()) Session_component(_env, args, _event_handler);
|
||||
}
|
||||
|
||||
|
||||
void Nitpicker::Root::_upgrade_session(Session_component *session, const char *args)
|
||||
{
|
||||
session->upgrade(session_resources_from_args(args));
|
||||
}
|
||||
|
||||
|
||||
void Nitpicker::Root::_destroy_session(Session_component *session)
|
||||
{
|
||||
Genode::destroy(md_alloc(), session);
|
||||
}
|
||||
|
||||
|
||||
Nitpicker::Root::Root(Env &env, Allocator &md_alloc, Input_event_handler &event_handler)
|
||||
:
|
||||
Root_component<Session_component>(env.ep(), md_alloc),
|
||||
_env(env), _event_handler(event_handler)
|
||||
{
|
||||
env.parent().announce(env.ep().manage(*this));
|
||||
}
|
||||
|
||||
|
||||
Nitpicker::Root::~Root() { _env.ep().dissolve(*this); }
|
||||
|
49
repos/gems/src/app/sculpt_manager/nitpicker.h
Normal file
49
repos/gems/src/app/sculpt_manager/nitpicker.h
Normal file
@ -0,0 +1,49 @@
|
||||
/*
|
||||
* \brief Nitpicker wrapper for monitoring the user input of GUI components
|
||||
* \author Norman Feske
|
||||
* \date 2018-04-30
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _NITPICKER_H_
|
||||
#define _NITPICKER_H_
|
||||
|
||||
/* Genode includes */
|
||||
#include <root/component.h>
|
||||
#include <nitpicker_session/nitpicker_session.h>
|
||||
#include <base/component.h>
|
||||
|
||||
/* local includes */
|
||||
#include "input_event_handler.h"
|
||||
|
||||
namespace Nitpicker {
|
||||
|
||||
using namespace Genode;
|
||||
using Sculpt::Input_event_handler;
|
||||
|
||||
struct Session_component;
|
||||
struct Root;
|
||||
}
|
||||
|
||||
|
||||
struct Nitpicker::Root : Genode::Root_component<Session_component>
|
||||
{
|
||||
Env &_env;
|
||||
Input_event_handler &_event_handler;
|
||||
|
||||
Session_component *_create_session(const char *) override;
|
||||
void _upgrade_session(Session_component *, const char *) override;
|
||||
void _destroy_session(Session_component *) override;
|
||||
|
||||
Root(Env &, Allocator &, Input_event_handler &);
|
||||
|
||||
~Root();
|
||||
};
|
||||
|
||||
#endif /* _NITPICKER_H_ */
|
73
repos/gems/src/app/sculpt_manager/runtime.h
Normal file
73
repos/gems/src/app/sculpt_manager/runtime.h
Normal file
@ -0,0 +1,73 @@
|
||||
/*
|
||||
* \brief Utilities for generating runtime configurations
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-18
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _RUNTIME_H_
|
||||
#define _RUNTIME_H_
|
||||
|
||||
#include <xml.h>
|
||||
#include <model/ram_fs_state.h>
|
||||
#include <model/storage_devices.h>
|
||||
#include <model/storage_target.h>
|
||||
#include <model/nic_target.h>
|
||||
|
||||
namespace Sculpt {
|
||||
|
||||
struct Runtime_config_generator : Interface
|
||||
{
|
||||
virtual void generate_runtime_config() = 0;
|
||||
};
|
||||
|
||||
struct Runtime_info : Interface
|
||||
{
|
||||
/**
|
||||
* Return true if specified child is present in the runtime subsystem
|
||||
*/
|
||||
virtual bool present_in_runtime(Start_name const &) const = 0;
|
||||
};
|
||||
|
||||
void gen_chroot_start_content(Xml_generator &, Start_name const &,
|
||||
Path const &, Writeable);
|
||||
|
||||
void gen_depot_query_start_content(Xml_generator &);
|
||||
|
||||
struct File_browser_version { unsigned value; };
|
||||
void gen_file_browser(Xml_generator &, Storage_devices const &,
|
||||
Ram_fs_state const &, File_browser_version);
|
||||
|
||||
void gen_fs_start_content(Xml_generator &, Storage_target const &,
|
||||
File_system::Type);
|
||||
|
||||
void gen_fs_rom_start_content(Xml_generator &, Start_name const &, Start_name const &, Ram_quota);
|
||||
|
||||
void gen_gpt_relabel_start_content(Xml_generator &, Storage_device const &);
|
||||
void gen_gpt_expand_start_content (Xml_generator &, Storage_device const &);
|
||||
|
||||
void gen_nic_drv_start_content(Xml_generator &);
|
||||
void gen_wifi_drv_start_content(Xml_generator &);
|
||||
|
||||
void gen_nic_router_start_content(Xml_generator &);
|
||||
void gen_nic_router_uplink(Xml_generator &, char const *);
|
||||
|
||||
struct Prepare_version { unsigned value; };
|
||||
void gen_prepare_start_content(Xml_generator &, Prepare_version);
|
||||
|
||||
void gen_ram_fs_start_content(Xml_generator &, Ram_fs_state const &);
|
||||
|
||||
void gen_update_start_content(Xml_generator &);
|
||||
|
||||
void gen_fsck_ext2_start_content(Xml_generator &, Storage_target const &);
|
||||
void gen_mkfs_ext2_start_content(Xml_generator &, Storage_target const &);
|
||||
void gen_resize2fs_start_content(Xml_generator &, Storage_target const &);
|
||||
}
|
||||
|
||||
#endif /* _RUNTIME_H_ */
|
44
repos/gems/src/app/sculpt_manager/runtime/chroot.cc
Normal file
44
repos/gems/src/app/sculpt_manager/runtime/chroot.cc
Normal file
@ -0,0 +1,44 @@
|
||||
/*
|
||||
* \brief XML configuration for the chroot component
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-18
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#include <runtime.h>
|
||||
|
||||
void Sculpt::gen_chroot_start_content(Xml_generator &xml, Start_name const &name,
|
||||
Path const &path, Writeable writable)
|
||||
{
|
||||
gen_common_start_content(xml, name, Cap_quota{100}, Ram_quota{2*1024*1024});
|
||||
|
||||
gen_named_node(xml, "binary", "chroot");
|
||||
|
||||
xml.node("config", [&] () {
|
||||
xml.node("default-policy", [&] () {
|
||||
xml.attribute("path", path);
|
||||
if (writable == WRITEABLE)
|
||||
xml.attribute("writeable", "yes");
|
||||
});
|
||||
});
|
||||
|
||||
gen_provides<::File_system::Session>(xml);
|
||||
|
||||
xml.node("route", [&] () {
|
||||
|
||||
gen_service_node<::File_system::Session>(xml, [&] () {
|
||||
gen_named_node(xml, "child", "default_fs_rw"); });
|
||||
|
||||
gen_parent_rom_route(xml, "chroot");
|
||||
gen_parent_rom_route(xml, "ld.lib.so");
|
||||
gen_parent_route<Cpu_session>(xml);
|
||||
gen_parent_route<Pd_session> (xml);
|
||||
gen_parent_route<Log_session>(xml);
|
||||
});
|
||||
}
|
43
repos/gems/src/app/sculpt_manager/runtime/depot_query.cc
Normal file
43
repos/gems/src/app/sculpt_manager/runtime/depot_query.cc
Normal file
@ -0,0 +1,43 @@
|
||||
/*
|
||||
* \brief XML configuration for the depot-query tool
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-09
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#include <runtime.h>
|
||||
|
||||
void Sculpt::gen_depot_query_start_content(Xml_generator &xml)
|
||||
{
|
||||
gen_common_start_content(xml, "depot_query",
|
||||
Cap_quota{200}, Ram_quota{2*1024*1024});
|
||||
|
||||
gen_named_node(xml, "binary", "depot_query");
|
||||
|
||||
xml.node("config", [&] () {
|
||||
xml.attribute("query", "rom");
|
||||
xml.node("vfs", [&] () {
|
||||
gen_named_node(xml, "dir", "depot", [&] () {
|
||||
xml.node("fs", [&] () {}); }); }); });
|
||||
|
||||
xml.node("route", [&] () {
|
||||
gen_parent_rom_route(xml, "depot_query");
|
||||
gen_parent_rom_route(xml, "ld.lib.so");
|
||||
gen_parent_rom_route(xml, "vfs.lib.so");
|
||||
gen_parent_rom_route(xml, "query", "config -> managed/depot_query");
|
||||
|
||||
gen_parent_route<Cpu_session> (xml);
|
||||
gen_parent_route<Pd_session> (xml);
|
||||
gen_parent_route<Log_session> (xml);
|
||||
gen_parent_route<Report::Session> (xml);
|
||||
|
||||
gen_service_node<::File_system::Session>(xml, [&] () {
|
||||
gen_named_node(xml, "child", "depot"); });
|
||||
});
|
||||
}
|
107
repos/gems/src/app/sculpt_manager/runtime/e2fs.cc
Normal file
107
repos/gems/src/app/sculpt_manager/runtime/e2fs.cc
Normal file
@ -0,0 +1,107 @@
|
||||
/*
|
||||
* \brief XML configuration for invoking e2fstools
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-02
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#include <runtime.h>
|
||||
|
||||
namespace Sculpt {
|
||||
|
||||
template <typename GEN_ARGS_FN>
|
||||
void gen_e2fs_start_content(Xml_generator &, Storage_target const &,
|
||||
Rom_name const &, GEN_ARGS_FN const &);
|
||||
|
||||
}
|
||||
|
||||
|
||||
template <typename GEN_ARGS_FN>
|
||||
void Sculpt::gen_e2fs_start_content(Xml_generator &xml,
|
||||
Storage_target const &target,
|
||||
Rom_name const &tool,
|
||||
GEN_ARGS_FN const &gen_args_fn)
|
||||
{
|
||||
gen_common_start_content(xml, String<64>(target.label(), ".", tool),
|
||||
Cap_quota{500}, Ram_quota{100*1024*1024});
|
||||
|
||||
gen_named_node(xml, "binary", "noux");
|
||||
|
||||
xml.node("config", [&] () {
|
||||
xml.attribute("stdout", "/dev/log");
|
||||
xml.attribute("stderr", "/dev/log");
|
||||
xml.attribute("stdin", "/dev/null");
|
||||
xml.node("fstab", [&] () {
|
||||
gen_named_node(xml, "tar", "e2fsprogs-minimal.tar");
|
||||
gen_named_node(xml, "dir", "dev", [&] () {
|
||||
gen_named_node(xml, "block", "block", [&] () {
|
||||
xml.attribute("label", "default");
|
||||
xml.attribute("block_buffer_count", 128);
|
||||
});
|
||||
xml.node("null", [&] () {});
|
||||
xml.node("log", [&] () {});
|
||||
});
|
||||
});
|
||||
gen_named_node(xml, "start", Rom_name("/bin/", tool), [&] () {
|
||||
gen_args_fn(xml); });
|
||||
});
|
||||
|
||||
xml.node("route", [&] () {
|
||||
gen_parent_rom_route(xml, "noux");
|
||||
gen_parent_rom_route(xml, "ld.lib.so");
|
||||
gen_parent_route<Cpu_session> (xml);
|
||||
gen_parent_route<Pd_session> (xml);
|
||||
gen_parent_route<Log_session> (xml);
|
||||
gen_parent_route<Rom_session> (xml);
|
||||
gen_parent_route<Timer::Session> (xml);
|
||||
|
||||
target.gen_block_session_route(xml);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::gen_fsck_ext2_start_content(Xml_generator &xml,
|
||||
Storage_target const &target)
|
||||
{
|
||||
auto gen_args = [&] (Xml_generator &xml) {
|
||||
xml.node("arg", [&] () { xml.attribute("value", "-yv"); });
|
||||
xml.node("arg", [&] () { xml.attribute("value", "/dev/block"); });
|
||||
};
|
||||
|
||||
gen_e2fs_start_content(xml, target, "fsck.ext2", gen_args);
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::gen_mkfs_ext2_start_content(Xml_generator &xml,
|
||||
Storage_target const &target)
|
||||
{
|
||||
auto gen_args = [&] (Xml_generator &xml) {
|
||||
xml.node("arg", [&] () {
|
||||
xml.attribute("value", "/dev/block"); }); };
|
||||
|
||||
gen_e2fs_start_content(xml, target, "mkfs.ext2", gen_args);
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::gen_resize2fs_start_content(Xml_generator &xml,
|
||||
Storage_target const &target)
|
||||
{
|
||||
auto gen_args = [&] (Xml_generator &xml) {
|
||||
|
||||
auto gen_arg = [&] (char const *arg) {
|
||||
xml.node("arg", [&] () {
|
||||
xml.attribute("value", arg); }); };
|
||||
|
||||
gen_arg("-f");
|
||||
gen_arg("-p");
|
||||
gen_arg("/dev/block");
|
||||
};
|
||||
|
||||
gen_e2fs_start_content(xml, target, "resize2fs", gen_args);
|
||||
}
|
227
repos/gems/src/app/sculpt_manager/runtime/file_browser.cc
Normal file
227
repos/gems/src/app/sculpt_manager/runtime/file_browser.cc
Normal file
@ -0,0 +1,227 @@
|
||||
/*
|
||||
* \brief XML configuration for file-browser subsystem
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-02
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#include <runtime.h>
|
||||
|
||||
namespace Sculpt {
|
||||
|
||||
template <typename FN>
|
||||
void for_each_inspected_storage_target(Storage_devices const &devices, FN const &fn)
|
||||
{
|
||||
devices.for_each([&] (Storage_device const &device) {
|
||||
device.for_each_partition([&] (Partition const &partition) {
|
||||
if (partition.file_system_inspected)
|
||||
fn(Storage_target { device.label, partition.number }); }); });
|
||||
}
|
||||
|
||||
void gen_nit_fb_start(Xml_generator &, Rom_name const &);
|
||||
void gen_terminal_start(Xml_generator &, Rom_name const &, Rom_name const &,
|
||||
File_browser_version);
|
||||
void gen_noux_start(Xml_generator &, Rom_name const &, Rom_name const &,
|
||||
Storage_devices const &, Ram_fs_state const &, File_browser_version);
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::gen_nit_fb_start(Xml_generator &xml, Rom_name const &name)
|
||||
{
|
||||
gen_common_start_content(xml, name, Cap_quota{100}, Ram_quota{4*1024*1024});
|
||||
|
||||
gen_named_node(xml, "binary", "nit_fb");
|
||||
|
||||
xml.node("provides", [&] () {
|
||||
gen_service_node<Framebuffer::Session>(xml, [&] () {});
|
||||
gen_service_node<Input::Session>(xml, [&] () {});
|
||||
});
|
||||
|
||||
xml.node("config", [&] () {
|
||||
xml.attribute("initial_width", "600");
|
||||
xml.attribute("initial_height", "500");
|
||||
});
|
||||
|
||||
xml.node("route", [&] () {
|
||||
gen_parent_rom_route(xml, "nit_fb");
|
||||
gen_parent_rom_route(xml, "ld.lib.so");
|
||||
gen_parent_route<Cpu_session> (xml);
|
||||
gen_parent_route<Pd_session> (xml);
|
||||
gen_parent_route<Log_session> (xml);
|
||||
|
||||
gen_service_node<Nitpicker::Session>(xml, [&] () {
|
||||
xml.node("parent", [&] () {
|
||||
xml.attribute("label", String<64>("leitzentrale -> ", name)); }); });
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::gen_terminal_start(Xml_generator &xml, Rom_name const &name,
|
||||
Rom_name const &nit_fb_name,
|
||||
File_browser_version version)
|
||||
{
|
||||
xml.attribute("version", version.value);
|
||||
|
||||
gen_common_start_content(xml, name, Cap_quota{100}, Ram_quota{4*1024*1024});
|
||||
|
||||
gen_named_node(xml, "binary", "terminal");
|
||||
|
||||
gen_provides<Terminal::Session>(xml);
|
||||
|
||||
xml.node("route", [&] () {
|
||||
gen_parent_rom_route(xml, "terminal");
|
||||
gen_parent_rom_route(xml, "ld.lib.so");
|
||||
gen_parent_rom_route(xml, "vfs.lib.so");
|
||||
gen_parent_rom_route(xml, "vfs_ttf.lib.so");
|
||||
gen_parent_rom_route(xml, "Vera.ttf");
|
||||
gen_parent_rom_route(xml, "VeraMono.ttf");
|
||||
gen_parent_rom_route(xml, "libc.lib.so");
|
||||
gen_parent_rom_route(xml, "libm.lib.so");
|
||||
gen_parent_route<Cpu_session> (xml);
|
||||
gen_parent_route<Pd_session> (xml);
|
||||
gen_parent_route<Log_session> (xml);
|
||||
gen_parent_route<Timer::Session> (xml);
|
||||
|
||||
gen_named_node(xml, "service", Rom_session::service_name(), [&] () {
|
||||
xml.attribute("label", "config");
|
||||
xml.node("parent", [&] () {
|
||||
xml.attribute("label", "config -> managed/fonts"); }); });
|
||||
|
||||
gen_service_node<Framebuffer::Session>(xml, [&] () {
|
||||
gen_named_node(xml, "child", nit_fb_name); });
|
||||
|
||||
gen_service_node<Input::Session>(xml, [&] () {
|
||||
gen_named_node(xml, "child", nit_fb_name); });
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::gen_noux_start(Xml_generator &xml, Rom_name const &name,
|
||||
Rom_name const &terminal_name,
|
||||
Storage_devices const &devices,
|
||||
Ram_fs_state const &ram_fs_state,
|
||||
File_browser_version version)
|
||||
{
|
||||
xml.attribute("version", version.value);
|
||||
|
||||
gen_common_start_content(xml, name, Cap_quota{500}, Ram_quota{64*1024*1024});
|
||||
|
||||
gen_named_node(xml, "binary", "noux");
|
||||
|
||||
xml.node("config", [&] () {
|
||||
xml.node("fstab", [&] () {
|
||||
gen_named_node(xml, "tar", "bash-minimal.tar");
|
||||
gen_named_node(xml, "tar", "coreutils-minimal.tar");
|
||||
gen_named_node(xml, "tar", "vim-minimal.tar");
|
||||
gen_named_node(xml, "dir", "dev", [&] () {
|
||||
xml.node("null", [&] () {});
|
||||
xml.node("zero", [&] () {});
|
||||
});
|
||||
gen_named_node(xml, "dir", "share", [&] () {
|
||||
gen_named_node(xml, "tar", "depot_users.tar"); });
|
||||
|
||||
auto fs_dir = [&] (String<64> const &label) {
|
||||
gen_named_node(xml, "dir", label, [&] () {
|
||||
xml.node("fs", [&] () { xml.attribute("label", label); }); }); };
|
||||
|
||||
fs_dir("config");
|
||||
fs_dir("report");
|
||||
|
||||
for_each_inspected_storage_target(devices, [&] (Storage_target const &target) {
|
||||
fs_dir(target.label()); });
|
||||
|
||||
if (ram_fs_state.inspected)
|
||||
fs_dir("ram");
|
||||
|
||||
gen_named_node(xml, "dir", "tmp", [&] () {
|
||||
xml.node("ram", [&] () { }); });
|
||||
|
||||
gen_named_node(xml, "dir", "share", [&] () {
|
||||
gen_named_node(xml, "dir", "vim", [&] () {
|
||||
xml.node("rom", [&] () {
|
||||
xml.attribute("name", "vimrc"); }); }); });
|
||||
|
||||
gen_named_node(xml, "rom", "VERSION");
|
||||
});
|
||||
|
||||
gen_named_node(xml, "start", "/bin/bash", [&] () {
|
||||
|
||||
gen_named_node(xml, "env", "TERM", [&] () {
|
||||
xml.attribute("value", "screen"); });
|
||||
|
||||
gen_named_node(xml, "env", "PS1", [&] () {
|
||||
xml.attribute("value", "inspect:$PWD> "); });
|
||||
});
|
||||
});
|
||||
|
||||
xml.node("route", [&] () {
|
||||
gen_parent_rom_route(xml, "noux");
|
||||
gen_parent_rom_route(xml, "ld.lib.so");
|
||||
gen_parent_rom_route(xml, "vfs.lib.so");
|
||||
gen_parent_rom_route(xml, "libc.lib.so");
|
||||
gen_parent_rom_route(xml, "libc_noux.lib.so");
|
||||
gen_parent_rom_route(xml, "libm.lib.so");
|
||||
gen_parent_rom_route(xml, "bash-minimal.tar");
|
||||
gen_parent_rom_route(xml, "coreutils-minimal.tar");
|
||||
gen_parent_rom_route(xml, "vim-minimal.tar");
|
||||
gen_parent_rom_route(xml, "ncurses.lib.so");
|
||||
gen_parent_rom_route(xml, "posix.lib.so");
|
||||
gen_parent_rom_route(xml, "depot_users.tar");
|
||||
gen_parent_rom_route(xml, "vimrc");
|
||||
gen_parent_rom_route(xml, "VERSION");
|
||||
gen_parent_route<Cpu_session> (xml);
|
||||
gen_parent_route<Pd_session> (xml);
|
||||
gen_parent_route<Log_session> (xml);
|
||||
gen_parent_route<Timer::Session> (xml);
|
||||
|
||||
gen_service_node<Terminal::Session>(xml, [&] () {
|
||||
gen_named_node(xml, "child", terminal_name); });
|
||||
|
||||
gen_service_node<::File_system::Session>(xml, [&] () {
|
||||
xml.attribute("label", "config");
|
||||
xml.node("parent", [&] () { xml.attribute("label", "config"); });
|
||||
});
|
||||
|
||||
gen_service_node<::File_system::Session>(xml, [&] () {
|
||||
xml.attribute("label", "report");
|
||||
xml.node("parent", [&] () { xml.attribute("label", "report"); });
|
||||
});
|
||||
|
||||
for_each_inspected_storage_target(devices, [&] (Storage_target const &target) {
|
||||
gen_service_node<::File_system::Session>(xml, [&] () {
|
||||
xml.attribute("label", target.label());
|
||||
gen_named_node(xml, "child", target.fs());
|
||||
});
|
||||
});
|
||||
|
||||
if (ram_fs_state.inspected)
|
||||
gen_service_node<::File_system::Session>(xml, [&] () {
|
||||
xml.attribute("label", "ram");
|
||||
gen_named_node(xml, "child", "ram_fs");
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::gen_file_browser(Xml_generator &xml,
|
||||
Storage_devices const &devices,
|
||||
Ram_fs_state const &ram_fs_state,
|
||||
File_browser_version version)
|
||||
{
|
||||
xml.node("start", [&] () {
|
||||
gen_nit_fb_start(xml, "storage browser"); });
|
||||
|
||||
xml.node("start", [&] () {
|
||||
gen_terminal_start(xml, "storage browser terminal", "storage browser",
|
||||
version); });
|
||||
|
||||
xml.node("start", [&] () {
|
||||
gen_noux_start(xml, "storage browser noux", "storage browser terminal",
|
||||
devices, ram_fs_state, version); });
|
||||
}
|
60
repos/gems/src/app/sculpt_manager/runtime/file_system.cc
Normal file
60
repos/gems/src/app/sculpt_manager/runtime/file_system.cc
Normal file
@ -0,0 +1,60 @@
|
||||
/*
|
||||
* \brief XML configuration for file-system server
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-02
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#include <runtime.h>
|
||||
|
||||
void Sculpt::gen_fs_start_content(Xml_generator &xml,
|
||||
Storage_target const &target,
|
||||
File_system::Type fs_type)
|
||||
{
|
||||
gen_common_start_content(xml, target.fs(),
|
||||
Cap_quota{400}, Ram_quota{64*1024*1024});
|
||||
|
||||
gen_named_node(xml, "binary", "vfs");
|
||||
|
||||
gen_provides<::File_system::Session>(xml);
|
||||
|
||||
xml.node("config", [&] () {
|
||||
xml.node("vfs", [&] () {
|
||||
xml.node("rump", [&] () {
|
||||
switch (fs_type) {
|
||||
case File_system::EXT2: xml.attribute("fs", "ext2fs"); break;
|
||||
case File_system::FAT32: xml.attribute("fs", "msdos"); break;
|
||||
case File_system::UNKNOWN: break;
|
||||
};
|
||||
xml.attribute("ram", "48M");
|
||||
xml.attribute("writeable", "yes");
|
||||
});
|
||||
});
|
||||
xml.node("default-policy", [&] () {
|
||||
xml.attribute("root", "/");
|
||||
xml.attribute("writeable", "yes");
|
||||
});
|
||||
});
|
||||
|
||||
xml.node("route", [&] () {
|
||||
gen_parent_rom_route(xml, "vfs");
|
||||
gen_parent_rom_route(xml, "ld.lib.so");
|
||||
gen_parent_rom_route(xml, "vfs.lib.so");
|
||||
gen_parent_rom_route(xml, "vfs_rump.lib.so");
|
||||
gen_parent_rom_route(xml, "rump.lib.so");
|
||||
gen_parent_rom_route(xml, "rump_fs.lib.so");
|
||||
gen_parent_route<Cpu_session> (xml);
|
||||
gen_parent_route<Pd_session> (xml);
|
||||
gen_parent_route<Rm_session> (xml);
|
||||
gen_parent_route<Log_session> (xml);
|
||||
gen_parent_route<Timer::Session> (xml);
|
||||
|
||||
target.gen_block_session_route(xml);
|
||||
});
|
||||
}
|
41
repos/gems/src/app/sculpt_manager/runtime/fs_rom.cc
Normal file
41
repos/gems/src/app/sculpt_manager/runtime/fs_rom.cc
Normal file
@ -0,0 +1,41 @@
|
||||
/*
|
||||
* \brief XML configuration for the fs-rom component
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-09
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#include <runtime.h>
|
||||
|
||||
void Sculpt::gen_fs_rom_start_content(Xml_generator &xml,
|
||||
Start_name const &name,
|
||||
Start_name const &server,
|
||||
Ram_quota ram_quota)
|
||||
{
|
||||
gen_common_start_content(xml, name,
|
||||
Cap_quota{200}, ram_quota);
|
||||
|
||||
gen_named_node(xml, "binary", "fs_rom");
|
||||
|
||||
xml.node("config", [&] () { });
|
||||
|
||||
gen_provides<Rom_session>(xml);
|
||||
|
||||
xml.node("route", [&] () {
|
||||
|
||||
gen_service_node<::File_system::Session>(xml, [&] () {
|
||||
gen_named_node(xml, "child", server); });
|
||||
|
||||
gen_parent_rom_route(xml, "fs_rom");
|
||||
gen_parent_rom_route(xml, "ld.lib.so");
|
||||
gen_parent_route<Cpu_session>(xml);
|
||||
gen_parent_route<Pd_session> (xml);
|
||||
gen_parent_route<Log_session>(xml);
|
||||
});
|
||||
}
|
81
repos/gems/src/app/sculpt_manager/runtime/gpt_write.cc
Normal file
81
repos/gems/src/app/sculpt_manager/runtime/gpt_write.cc
Normal file
@ -0,0 +1,81 @@
|
||||
/*
|
||||
* \brief XML configuration for invoking the gpt_write_tool
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-16
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#include <runtime.h>
|
||||
|
||||
namespace Sculpt {
|
||||
|
||||
template <typename GEN_ACTIONS_FN>
|
||||
void _gen_gpt_write_start_content(Xml_generator &, Storage_device const &,
|
||||
Start_name const &, GEN_ACTIONS_FN const &);
|
||||
}
|
||||
|
||||
|
||||
template <typename GEN_ACTIONS_FN>
|
||||
void Sculpt::_gen_gpt_write_start_content(Xml_generator &xml,
|
||||
Storage_device const &device,
|
||||
Start_name const &name,
|
||||
GEN_ACTIONS_FN const &fn)
|
||||
{
|
||||
gen_common_start_content(xml, name, Cap_quota{100}, Ram_quota{2*1024*1024});
|
||||
|
||||
gen_named_node(xml, "binary", "gpt_write");
|
||||
|
||||
xml.node("config", [&] () {
|
||||
xml.attribute("verbose", "yes");
|
||||
xml.attribute("update_geometry", "yes");
|
||||
|
||||
xml.node("actions", [&] () { fn(xml); });
|
||||
});
|
||||
|
||||
xml.node("route", [&] () {
|
||||
gen_parent_rom_route(xml, "gpt_write");
|
||||
gen_parent_rom_route(xml, "ld.lib.so");
|
||||
gen_parent_route<Cpu_session> (xml);
|
||||
gen_parent_route<Pd_session> (xml);
|
||||
gen_parent_route<Log_session> (xml);
|
||||
gen_parent_route<Rom_session> (xml);
|
||||
|
||||
Storage_target const target { device.label, Partition::Number { } };
|
||||
target.gen_block_session_route(xml);
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::gen_gpt_relabel_start_content(Xml_generator &xml,
|
||||
Storage_device const &device)
|
||||
{
|
||||
Start_name const name = device.relabel_start_name();
|
||||
_gen_gpt_write_start_content(xml, device, name, [&] (Xml_generator &xml) {
|
||||
|
||||
device.for_each_partition([&] (Partition const &partition) {
|
||||
|
||||
if (partition.number.valid() && partition.relabel_in_progress())
|
||||
xml.node("modify", [&] () {
|
||||
xml.attribute("entry", partition.number);
|
||||
xml.attribute("new_label", partition.next_label); }); }); });
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::gen_gpt_expand_start_content(Xml_generator &xml,
|
||||
Storage_device const &device)
|
||||
{
|
||||
Start_name const name = device.expand_start_name();
|
||||
_gen_gpt_write_start_content(xml, device, name, [&] (Xml_generator &xml) {
|
||||
device.for_each_partition([&] (Partition const &partition) {
|
||||
|
||||
if (partition.number.valid() && partition.gpt_expand_in_progress)
|
||||
xml.node("modify", [&] () {
|
||||
xml.attribute("entry", partition.number);
|
||||
xml.attribute("new_size", "max"); }); }); });
|
||||
}
|
37
repos/gems/src/app/sculpt_manager/runtime/nic_drv.cc
Normal file
37
repos/gems/src/app/sculpt_manager/runtime/nic_drv.cc
Normal file
@ -0,0 +1,37 @@
|
||||
/*
|
||||
* \brief XML configuration for wired NIC driver
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-02
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#include <runtime.h>
|
||||
|
||||
void Sculpt::gen_nic_drv_start_content(Xml_generator &xml)
|
||||
{
|
||||
gen_common_start_content(xml, "nic_drv", Cap_quota{300}, Ram_quota{16*1024*1024});
|
||||
|
||||
gen_provides<Nic::Session>(xml);
|
||||
|
||||
xml.node("config", [&] () { });
|
||||
|
||||
xml.node("route", [&] () {
|
||||
gen_parent_rom_route(xml, "nic_drv");
|
||||
gen_parent_rom_route(xml, "ld.lib.so");
|
||||
gen_parent_route<Cpu_session> (xml);
|
||||
gen_parent_route<Pd_session> (xml);
|
||||
gen_parent_route<Rm_session> (xml);
|
||||
gen_parent_route<Log_session> (xml);
|
||||
gen_parent_route<Timer::Session> (xml);
|
||||
|
||||
gen_service_node<Platform::Session>(xml, [&] () {
|
||||
xml.node("parent", [&] () {
|
||||
xml.attribute("label", "nic"); }); });
|
||||
});
|
||||
}
|
43
repos/gems/src/app/sculpt_manager/runtime/nic_router.cc
Normal file
43
repos/gems/src/app/sculpt_manager/runtime/nic_router.cc
Normal file
@ -0,0 +1,43 @@
|
||||
/*
|
||||
* \brief XML configuration for the NIC router
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-08
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#include <runtime.h>
|
||||
|
||||
|
||||
void Sculpt::gen_nic_router_start_content(Xml_generator &xml)
|
||||
{
|
||||
gen_common_start_content(xml, "nic_router",
|
||||
Cap_quota{300}, Ram_quota{10*1024*1024});
|
||||
|
||||
gen_provides<Nic::Session>(xml);
|
||||
|
||||
xml.node("route", [&] () {
|
||||
gen_parent_rom_route(xml, "nic_router");
|
||||
gen_parent_rom_route(xml, "ld.lib.so");
|
||||
gen_parent_rom_route(xml, "config", "config -> managed/nic_router");
|
||||
gen_parent_route<Cpu_session> (xml);
|
||||
gen_parent_route<Pd_session> (xml);
|
||||
gen_parent_route<Rm_session> (xml);
|
||||
gen_parent_route<Log_session> (xml);
|
||||
gen_parent_route<Timer::Session> (xml);
|
||||
gen_parent_route<Report::Session> (xml);
|
||||
gen_service_node<Nic::Session>(xml, [&] () {
|
||||
xml.attribute("label", "wired");
|
||||
gen_named_node(xml, "child", "nic_drv");
|
||||
});
|
||||
gen_service_node<Nic::Session>(xml, [&] () {
|
||||
xml.attribute("label", "wifi");
|
||||
gen_named_node(xml, "child", "wifi_drv");
|
||||
});
|
||||
});
|
||||
}
|
97
repos/gems/src/app/sculpt_manager/runtime/prepare.cc
Normal file
97
repos/gems/src/app/sculpt_manager/runtime/prepare.cc
Normal file
@ -0,0 +1,97 @@
|
||||
/*
|
||||
* \brief XML configuration for config loading and depot initialization
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-08
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#include <runtime.h>
|
||||
|
||||
void Sculpt::gen_prepare_start_content(Xml_generator &xml, Prepare_version version)
|
||||
{
|
||||
xml.attribute("version", version.value);
|
||||
|
||||
gen_common_start_content(xml, "prepare", Cap_quota{500}, Ram_quota{100*1024*1024});
|
||||
|
||||
gen_named_node(xml, "binary", "noux");
|
||||
|
||||
char const * const script =
|
||||
"export VERSION=`cat /VERSION`\n"
|
||||
"cp -r /rw/config/$VERSION/* /config/\n"
|
||||
"mkdir -p /rw/depot\n"
|
||||
"cp -r depot/genodelabs depot/alex-ab depot/chelmuth depot/cproc"
|
||||
" depot/cnuke depot/ehmry depot/nfeske depot/skalk"
|
||||
" /rw/depot\n";
|
||||
|
||||
xml.node("config", [&] () {
|
||||
xml.attribute("stdout", "/dev/null");
|
||||
xml.attribute("stderr", "/dev/null");
|
||||
xml.attribute("stdin", "/dev/null");
|
||||
|
||||
xml.node("fstab", [&] () {
|
||||
|
||||
gen_named_node(xml, "tar", "bash-minimal.tar");
|
||||
gen_named_node(xml, "tar", "coreutils-minimal.tar");
|
||||
gen_named_node(xml, "tar", "depot_users.tar");
|
||||
|
||||
gen_named_node(xml, "inline", ".bash_profile", [&] () {
|
||||
xml.append(script); });
|
||||
|
||||
gen_named_node(xml, "dir", "dev", [&] () {
|
||||
xml.node("null", [&] () {});
|
||||
xml.node("log", [&] () {});
|
||||
xml.node("zero", [&] () {}); });
|
||||
|
||||
gen_named_node(xml, "dir", "rw", [&] () {
|
||||
xml.node("fs", [&] () { xml.attribute("label", "target"); }); });
|
||||
|
||||
gen_named_node(xml, "dir", "config", [&] () {
|
||||
xml.node("fs", [&] () { xml.attribute("label", "config"); }); });
|
||||
|
||||
gen_named_node(xml, "rom", "VERSION");
|
||||
});
|
||||
|
||||
gen_named_node(xml, "start", "/bin/bash", [&] () {
|
||||
|
||||
gen_named_node(xml, "env", "HOME", [&] () {
|
||||
xml.attribute("value", "/"); });
|
||||
|
||||
gen_named_node(xml, "env", "TERM", [&] () {
|
||||
xml.attribute("value", "screen"); });
|
||||
|
||||
xml.node("arg", [&] () { xml.attribute("value", "--login"); });
|
||||
});
|
||||
});
|
||||
|
||||
xml.node("route", [&] () {
|
||||
gen_parent_rom_route(xml, "noux");
|
||||
gen_parent_rom_route(xml, "ld.lib.so");
|
||||
gen_parent_rom_route(xml, "bash-minimal.tar");
|
||||
gen_parent_rom_route(xml, "coreutils-minimal.tar");
|
||||
gen_parent_rom_route(xml, "depot_users.tar");
|
||||
gen_parent_rom_route(xml, "vfs.lib.so");
|
||||
gen_parent_rom_route(xml, "libc.lib.so");
|
||||
gen_parent_rom_route(xml, "libc_noux.lib.so");
|
||||
gen_parent_rom_route(xml, "libm.lib.so");
|
||||
gen_parent_rom_route(xml, "posix.lib.so");
|
||||
gen_parent_route<Cpu_session> (xml);
|
||||
gen_parent_route<Pd_session> (xml);
|
||||
gen_parent_route<Log_session> (xml);
|
||||
gen_parent_route<Rom_session> (xml);
|
||||
gen_parent_route<Timer::Session> (xml);
|
||||
|
||||
gen_service_node<::File_system::Session>(xml, [&] () {
|
||||
xml.attribute("label", "target");
|
||||
gen_named_node(xml, "child", "default_fs_rw"); });
|
||||
|
||||
gen_service_node<::File_system::Session>(xml, [&] () {
|
||||
xml.attribute("label", "config");
|
||||
xml.node("parent", [&] () { xml.attribute("label", "config"); }); });
|
||||
});
|
||||
}
|
39
repos/gems/src/app/sculpt_manager/runtime/ram_fs.cc
Normal file
39
repos/gems/src/app/sculpt_manager/runtime/ram_fs.cc
Normal file
@ -0,0 +1,39 @@
|
||||
/*
|
||||
* \brief XML configuration for RAM file system
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-15
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#include <runtime.h>
|
||||
|
||||
void Sculpt::gen_ram_fs_start_content(Xml_generator &xml,
|
||||
Ram_fs_state const &state)
|
||||
{
|
||||
xml.attribute("version", state.version.value);
|
||||
|
||||
gen_common_start_content(xml, "ram_fs", Cap_quota{300}, state.ram_quota);
|
||||
|
||||
gen_provides<::File_system::Session>(xml);
|
||||
|
||||
xml.node("config", [&] () {
|
||||
xml.node("default-policy", [&] () {
|
||||
xml.attribute("root", "/");
|
||||
xml.attribute("writeable", "yes");
|
||||
});
|
||||
});
|
||||
|
||||
xml.node("route", [&] () {
|
||||
gen_parent_rom_route(xml, "ram_fs");
|
||||
gen_parent_rom_route(xml, "ld.lib.so");
|
||||
gen_parent_route<Cpu_session> (xml);
|
||||
gen_parent_route<Pd_session> (xml);
|
||||
gen_parent_route<Log_session> (xml);
|
||||
});
|
||||
}
|
81
repos/gems/src/app/sculpt_manager/runtime/update.cc
Normal file
81
repos/gems/src/app/sculpt_manager/runtime/update.cc
Normal file
@ -0,0 +1,81 @@
|
||||
/*
|
||||
* \brief XML configuration for the depot-download subsystem
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-08
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#include <runtime.h>
|
||||
|
||||
void Sculpt::gen_update_start_content(Xml_generator &xml)
|
||||
{
|
||||
gen_common_start_content(xml, "update", Cap_quota{2000}, Ram_quota{64*1024*1024});
|
||||
|
||||
gen_named_node(xml, "binary", "init");
|
||||
|
||||
xml.node("route", [&] () {
|
||||
|
||||
gen_parent_rom_route(xml, "ld.lib.so");
|
||||
gen_parent_rom_route(xml, "vfs.lib.so");
|
||||
gen_parent_rom_route(xml, "libc.lib.so");
|
||||
gen_parent_rom_route(xml, "libm.lib.so");
|
||||
gen_parent_rom_route(xml, "extract");
|
||||
gen_parent_rom_route(xml, "verify");
|
||||
gen_parent_rom_route(xml, "fetchurl");
|
||||
gen_parent_rom_route(xml, "chroot");
|
||||
gen_parent_rom_route(xml, "curl.lib.so");
|
||||
gen_parent_rom_route(xml, "init");
|
||||
gen_parent_rom_route(xml, "depot_query");
|
||||
gen_parent_rom_route(xml, "depot_download_manager");
|
||||
gen_parent_rom_route(xml, "report_rom");
|
||||
gen_parent_rom_route(xml, "vfs");
|
||||
gen_parent_rom_route(xml, "lxip.lib.so");
|
||||
gen_parent_rom_route(xml, "vfs_lxip.lib.so");
|
||||
gen_parent_rom_route(xml, "posix.lib.so");
|
||||
gen_parent_rom_route(xml, "libssh.lib.so");
|
||||
gen_parent_rom_route(xml, "libssl.lib.so");
|
||||
gen_parent_rom_route(xml, "libcrypto.lib.so");
|
||||
gen_parent_rom_route(xml, "zlib.lib.so");
|
||||
gen_parent_rom_route(xml, "libarchive.lib.so");
|
||||
gen_parent_rom_route(xml, "liblzma.lib.so");
|
||||
gen_parent_rom_route(xml, "pthread.lib.so");
|
||||
gen_parent_rom_route(xml, "config", "depot_download.config");
|
||||
gen_parent_rom_route(xml, "installation", "config -> managed/installation");
|
||||
gen_parent_route<Cpu_session> (xml);
|
||||
gen_parent_route<Pd_session> (xml);
|
||||
gen_parent_route<Rm_session> (xml);
|
||||
gen_parent_route<Timer::Session> (xml);
|
||||
gen_parent_route<Report::Session>(xml);
|
||||
|
||||
typedef String<32> Label;
|
||||
auto gen_fs = [&] (Label const &label, Label const &server) {
|
||||
gen_service_node<::File_system::Session>(xml, [&] () {
|
||||
xml.attribute("label", label);
|
||||
gen_named_node(xml, "child", server); }); };
|
||||
|
||||
/* connect file-system sessions to chroot instances */
|
||||
gen_fs("depot", "depot_rw");
|
||||
gen_fs("public", "public_rw");
|
||||
|
||||
auto gen_relabeled_log = [&] (Label const &label, Label const &relabeled) {
|
||||
gen_service_node<Log_session>(xml, [&] () {
|
||||
xml.attribute("label", label);
|
||||
xml.node("parent", [&] () {
|
||||
xml.attribute("label", relabeled); }); }); };
|
||||
|
||||
/* shorten LOG-session labels to reduce the debug-output noise */
|
||||
gen_relabeled_log("dynamic -> fetchurl", "fetchurl");
|
||||
gen_relabeled_log("dynamic -> verify", "verify");
|
||||
gen_relabeled_log("dynamic -> extract", "extract");
|
||||
gen_parent_route<Log_session>(xml);
|
||||
|
||||
gen_service_node<Nic::Session>(xml, [&] () {
|
||||
gen_named_node(xml, "child", "nic_router"); });
|
||||
});
|
||||
}
|
84
repos/gems/src/app/sculpt_manager/runtime/wifi_drv.cc
Normal file
84
repos/gems/src/app/sculpt_manager/runtime/wifi_drv.cc
Normal file
@ -0,0 +1,84 @@
|
||||
/*
|
||||
* \brief XML configuration for wireless driver
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-02
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#include <runtime.h>
|
||||
|
||||
void Sculpt::gen_wifi_drv_start_content(Xml_generator &xml)
|
||||
{
|
||||
gen_common_start_content(xml, "wifi_drv", Cap_quota{300}, Ram_quota{54*1024*1024});
|
||||
|
||||
gen_provides<Nic::Session>(xml);
|
||||
|
||||
xml.node("config", [&] () {
|
||||
xml.attribute("connected_scan_interval", "0");
|
||||
xml.attribute("use_11n", "no");
|
||||
|
||||
xml.node("vfs", [&] () {
|
||||
gen_named_node(xml, "dir", "dev", [&] () {
|
||||
xml.node("null", [&] () {});
|
||||
xml.node("zero", [&] () {});
|
||||
xml.node("rtc", [&] () {});
|
||||
xml.node("log", [&] () {});
|
||||
gen_named_node(xml, "jitterentropy", "random");
|
||||
gen_named_node(xml, "jitterentropy", "urandom"); });
|
||||
|
||||
gen_named_node(xml, "dir", "config", [&] () {
|
||||
xml.node("ram", [&] () {}); });
|
||||
});
|
||||
|
||||
xml.node("libc", [&] () {
|
||||
xml.attribute("stdout", "/dev/null");
|
||||
xml.attribute("stderr", "/dev/log");
|
||||
xml.attribute("rtc", "/dev/rtc");
|
||||
});
|
||||
});
|
||||
|
||||
xml.node("route", [&] () {
|
||||
gen_parent_rom_route(xml, "wifi_drv");
|
||||
gen_parent_rom_route(xml, "ld.lib.so");
|
||||
gen_parent_rom_route(xml, "libcrypto.lib.so");
|
||||
gen_parent_rom_route(xml, "vfs.lib.so");
|
||||
gen_parent_rom_route(xml, "libc.lib.so");
|
||||
gen_parent_rom_route(xml, "libm.lib.so");
|
||||
gen_parent_rom_route(xml, "vfs_jitterentropy.lib.so");
|
||||
gen_parent_rom_route(xml, "libssl.lib.so");
|
||||
gen_parent_rom_route(xml, "wifi.lib.so");
|
||||
gen_parent_rom_route(xml, "wpa_driver_nl80211.lib.so");
|
||||
gen_parent_rom_route(xml, "wpa_supplicant.lib.so");
|
||||
gen_parent_rom_route(xml, "iwlwifi-1000-5.ucode");
|
||||
gen_parent_rom_route(xml, "iwlwifi-3160-16.ucode");
|
||||
gen_parent_rom_route(xml, "iwlwifi-6000-4.ucode");
|
||||
gen_parent_rom_route(xml, "iwlwifi-6000g2a-6.ucode");
|
||||
gen_parent_rom_route(xml, "iwlwifi-6000g2b-6.ucode");
|
||||
gen_parent_rom_route(xml, "iwlwifi-7260-16.ucode");
|
||||
gen_parent_rom_route(xml, "iwlwifi-7265-16.ucode");
|
||||
gen_parent_rom_route(xml, "iwlwifi-7265D-16.ucode");
|
||||
gen_parent_rom_route(xml, "iwlwifi-8000C-16.ucode");
|
||||
gen_parent_route<Cpu_session> (xml);
|
||||
gen_parent_route<Pd_session> (xml);
|
||||
gen_parent_route<Rm_session> (xml);
|
||||
gen_parent_route<Log_session> (xml);
|
||||
gen_parent_route<Timer::Session> (xml);
|
||||
gen_parent_route<Rtc::Session> (xml);
|
||||
gen_parent_route<Report::Session> (xml);
|
||||
|
||||
gen_service_node<Rom_session>(xml, [&] () {
|
||||
xml.attribute("label", "wlan_configuration");
|
||||
xml.node("parent", [&] () {
|
||||
xml.attribute("label", "config -> managed/wlan"); }); });
|
||||
|
||||
gen_service_node<Platform::Session>(xml, [&] () {
|
||||
xml.node("parent", [&] () {
|
||||
xml.attribute("label", "wifi"); }); });
|
||||
});
|
||||
}
|
156
repos/gems/src/app/sculpt_manager/storage.cc
Normal file
156
repos/gems/src/app/sculpt_manager/storage.cc
Normal file
@ -0,0 +1,156 @@
|
||||
/*
|
||||
* \brief Sculpt storage management
|
||||
* \author Norman Feske
|
||||
* \date 2018-04-30
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
/* local includes */
|
||||
#include <storage.h>
|
||||
|
||||
|
||||
void Sculpt::Storage::handle_storage_devices_update()
|
||||
{
|
||||
bool reconfigure_runtime = false;
|
||||
{
|
||||
_block_devices_rom.update();
|
||||
Block_device_update_policy policy(_env, _alloc, _storage_device_update_handler);
|
||||
_storage_devices.update_block_devices_from_xml(policy, _block_devices_rom.xml());
|
||||
|
||||
_storage_devices.block_devices.for_each([&] (Block_device &dev) {
|
||||
|
||||
dev.process_part_blk_report();
|
||||
|
||||
if (dev.state == Storage_device::UNKNOWN) {
|
||||
reconfigure_runtime = true; };
|
||||
});
|
||||
}
|
||||
|
||||
{
|
||||
_usb_active_config_rom.update();
|
||||
Usb_storage_device_update_policy policy(_env, _alloc, _storage_device_update_handler);
|
||||
Xml_node const config = _usb_active_config_rom.xml();
|
||||
Xml_node const raw = config.has_sub_node("raw")
|
||||
? config.sub_node("raw") : Xml_node("<raw/>");
|
||||
|
||||
_storage_devices.update_usb_storage_devices_from_xml(policy, raw);
|
||||
|
||||
_storage_devices.usb_storage_devices.for_each([&] (Usb_storage_device &dev) {
|
||||
|
||||
dev.process_driver_report();
|
||||
dev.process_part_blk_report();
|
||||
|
||||
if (dev.state == Storage_device::UNKNOWN) {
|
||||
reconfigure_runtime = true; };
|
||||
});
|
||||
}
|
||||
|
||||
if (!_sculpt_partition.valid()) {
|
||||
|
||||
Storage_target const default_target =
|
||||
_discovery_state.detect_default_target(_storage_devices);
|
||||
|
||||
if (default_target.valid())
|
||||
use(default_target);
|
||||
}
|
||||
|
||||
_dialog_generator.generate_dialog();
|
||||
|
||||
if (reconfigure_runtime)
|
||||
_runtime_config_generator.generate_runtime_config();
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Storage::gen_runtime_start_nodes(Xml_generator &xml) const
|
||||
{
|
||||
xml.node("start", [&] () {
|
||||
gen_ram_fs_start_content(xml, _ram_fs_state); });
|
||||
|
||||
auto part_blk_needed_for_use = [&] (Storage_device const &dev) {
|
||||
return (_sculpt_partition.device == dev.label)
|
||||
&& _sculpt_partition.partition.valid(); };
|
||||
|
||||
_storage_devices.block_devices.for_each([&] (Block_device const &dev) {
|
||||
|
||||
if (dev.part_blk_needed_for_discovery()
|
||||
|| dev.part_blk_needed_for_access()
|
||||
|| part_blk_needed_for_use(dev))
|
||||
|
||||
xml.node("start", [&] () {
|
||||
Storage_device::Label const parent { };
|
||||
dev.gen_part_blk_start_content(xml, parent); }); });
|
||||
|
||||
_storage_devices.usb_storage_devices.for_each([&] (Usb_storage_device const &dev) {
|
||||
|
||||
if (dev.usb_block_drv_needed() || _sculpt_partition.device == dev.label)
|
||||
xml.node("start", [&] () {
|
||||
dev.gen_usb_block_drv_start_content(xml); });
|
||||
|
||||
if (dev.part_blk_needed_for_discovery()
|
||||
|| dev.part_blk_needed_for_access()
|
||||
|| part_blk_needed_for_use(dev))
|
||||
|
||||
xml.node("start", [&] () {
|
||||
Storage_device::Label const driver = dev.usb_block_drv_name();
|
||||
dev.gen_part_blk_start_content(xml, driver);
|
||||
});
|
||||
});
|
||||
|
||||
_storage_devices.for_each([&] (Storage_device const &device) {
|
||||
|
||||
device.for_each_partition([&] (Partition const &partition) {
|
||||
|
||||
Storage_target const target { device.label, partition.number };
|
||||
|
||||
if (partition.check_in_progress) {
|
||||
xml.node("start", [&] () {
|
||||
gen_fsck_ext2_start_content(xml, target); }); }
|
||||
|
||||
if (partition.format_in_progress) {
|
||||
xml.node("start", [&] () {
|
||||
gen_mkfs_ext2_start_content(xml, target); }); }
|
||||
|
||||
if (partition.fs_resize_in_progress) {
|
||||
xml.node("start", [&] () {
|
||||
gen_resize2fs_start_content(xml, target); }); }
|
||||
|
||||
if (partition.file_system.type != File_system::UNKNOWN) {
|
||||
if (partition.file_system_inspected || target == _sculpt_partition)
|
||||
xml.node("start", [&] () {
|
||||
gen_fs_start_content(xml, target, partition.file_system.type); });
|
||||
|
||||
/*
|
||||
* Create alias so that the default file system can be referred
|
||||
* to as "default_fs_rw" without the need to know the name of the
|
||||
* underlying storage target.
|
||||
*/
|
||||
if (target == _sculpt_partition)
|
||||
gen_named_node(xml, "alias", "default_fs_rw", [&] () {
|
||||
xml.attribute("child", target.fs()); });
|
||||
}
|
||||
|
||||
}); /* for each partition */
|
||||
|
||||
/* relabel partitions if needed */
|
||||
if (device.relabel_in_progress())
|
||||
xml.node("start", [&] () {
|
||||
gen_gpt_relabel_start_content(xml, device); });
|
||||
|
||||
/* expand partitions if needed */
|
||||
if (device.expand_in_progress())
|
||||
xml.node("start", [&] () {
|
||||
gen_gpt_expand_start_content(xml, device); });
|
||||
|
||||
}); /* for each device */
|
||||
|
||||
if (_sculpt_partition.ram_fs())
|
||||
gen_named_node(xml, "alias", "default_fs_rw", [&] () {
|
||||
xml.attribute("child", "ram_fs"); });
|
||||
}
|
||||
|
207
repos/gems/src/app/sculpt_manager/storage.h
Normal file
207
repos/gems/src/app/sculpt_manager/storage.h
Normal file
@ -0,0 +1,207 @@
|
||||
/*
|
||||
* \brief Sculpt storage management
|
||||
* \author Norman Feske
|
||||
* \date 2018-04-30
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _STORAGE_H_
|
||||
#define _STORAGE_H_
|
||||
|
||||
/* Genode includes */
|
||||
#include <base/attached_rom_dataspace.h>
|
||||
#include <os/reporter.h>
|
||||
|
||||
/* local includes */
|
||||
#include <model/discovery_state.h>
|
||||
#include <view/storage_dialog.h>
|
||||
#include <runtime.h>
|
||||
|
||||
namespace Sculpt { struct Storage; }
|
||||
|
||||
|
||||
struct Sculpt::Storage : Storage_dialog::Action
|
||||
{
|
||||
Env &_env;
|
||||
|
||||
Allocator &_alloc;
|
||||
|
||||
Dialog::Generator &_dialog_generator;
|
||||
|
||||
Runtime_config_generator &_runtime_config_generator;
|
||||
|
||||
struct Target_user : Interface
|
||||
{
|
||||
virtual void use_storage_target(Storage_target const &) = 0;
|
||||
};
|
||||
|
||||
Target_user &_target_user;
|
||||
|
||||
Attached_rom_dataspace _block_devices_rom { _env, "report -> drivers/block_devices" };
|
||||
|
||||
Attached_rom_dataspace _usb_active_config_rom { _env, "report -> drivers/usb_active_config" };
|
||||
|
||||
Storage_devices _storage_devices { };
|
||||
|
||||
Ram_fs_state _ram_fs_state { };
|
||||
|
||||
Storage_target _sculpt_partition { };
|
||||
|
||||
Discovery_state _discovery_state { };
|
||||
|
||||
File_browser_version _file_browser_version { 0 };
|
||||
|
||||
Storage_dialog dialog {
|
||||
_env, _dialog_generator, _storage_devices, _ram_fs_state, _sculpt_partition };
|
||||
|
||||
void handle_storage_devices_update();
|
||||
|
||||
Signal_handler<Storage> _storage_device_update_handler {
|
||||
_env.ep(), *this, &Storage::handle_storage_devices_update };
|
||||
|
||||
/*
|
||||
* Determine whether showing the file-system browser or not
|
||||
*/
|
||||
bool any_file_system_inspected() const
|
||||
{
|
||||
bool result = _ram_fs_state.inspected;
|
||||
_storage_devices.for_each([&] (Storage_device const &device) {
|
||||
device.for_each_partition([&] (Partition const &partition) {
|
||||
result |= partition.file_system_inspected; }); });
|
||||
return result;
|
||||
}
|
||||
|
||||
void gen_runtime_start_nodes(Xml_generator &) const;
|
||||
|
||||
template <typename FN>
|
||||
void _apply_partition(Storage_target const &target, FN const &fn)
|
||||
{
|
||||
_storage_devices.for_each([&] (Storage_device &device) {
|
||||
|
||||
if (target.device != device.label)
|
||||
return;
|
||||
|
||||
device.for_each_partition([&] (Partition &partition) {
|
||||
|
||||
bool const whole_device = !target.partition.valid()
|
||||
&& !partition.number.valid();
|
||||
|
||||
bool const partition_matches = (device.label == target.device)
|
||||
&& (partition.number == target.partition);
|
||||
|
||||
if (whole_device || partition_matches) {
|
||||
fn(partition);
|
||||
_runtime_config_generator.generate_runtime_config();
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
/**
|
||||
* Storage_dialog::Action interface
|
||||
*/
|
||||
void format(Storage_target const &target) override
|
||||
{
|
||||
_apply_partition(target, [&] (Partition &partition) {
|
||||
partition.format_in_progress = true; });
|
||||
}
|
||||
|
||||
void cancel_format(Storage_target const &target) override
|
||||
{
|
||||
_apply_partition(target, [&] (Partition &partition) {
|
||||
|
||||
if (partition.format_in_progress) {
|
||||
partition.file_system.type = File_system::UNKNOWN;
|
||||
partition.format_in_progress = false;
|
||||
}
|
||||
dialog.reset_operation();
|
||||
});
|
||||
}
|
||||
|
||||
void expand(Storage_target const &target) override
|
||||
{
|
||||
_apply_partition(target, [&] (Partition &partition) {
|
||||
partition.gpt_expand_in_progress = true; });
|
||||
}
|
||||
|
||||
void cancel_expand(Storage_target const &target) override
|
||||
{
|
||||
_apply_partition(target, [&] (Partition &partition) {
|
||||
|
||||
if (partition.expand_in_progress()) {
|
||||
partition.file_system.type = File_system::UNKNOWN;
|
||||
partition.gpt_expand_in_progress = false;
|
||||
partition.fs_resize_in_progress = false;
|
||||
}
|
||||
dialog.reset_operation();
|
||||
});
|
||||
}
|
||||
|
||||
void check(Storage_target const &target) override
|
||||
{
|
||||
_apply_partition(target, [&] (Partition &partition) {
|
||||
partition.check_in_progress = true; });
|
||||
}
|
||||
|
||||
void toggle_file_browser(Storage_target const &target) override
|
||||
{
|
||||
File_browser_version const orig_version = _file_browser_version;
|
||||
|
||||
if (target.ram_fs()) {
|
||||
_ram_fs_state.inspected = !_ram_fs_state.inspected;
|
||||
_file_browser_version.value++;
|
||||
}
|
||||
|
||||
_apply_partition(target, [&] (Partition &partition) {
|
||||
partition.file_system_inspected = !partition.file_system_inspected;
|
||||
_file_browser_version.value++;
|
||||
});
|
||||
|
||||
if (orig_version.value == _file_browser_version.value)
|
||||
return;
|
||||
|
||||
_runtime_config_generator.generate_runtime_config();
|
||||
}
|
||||
|
||||
void toggle_default_storage_target(Storage_target const &target) override
|
||||
{
|
||||
_apply_partition(target, [&] (Partition &partition) {
|
||||
partition.toggle_default_label(); });
|
||||
}
|
||||
|
||||
void use(Storage_target const &target) override
|
||||
{
|
||||
_target_user.use_storage_target(target);
|
||||
}
|
||||
|
||||
void reset_ram_fs() override
|
||||
{
|
||||
_ram_fs_state.ram_quota = Ram_fs_state::initial_ram();
|
||||
_ram_fs_state.version.value++;
|
||||
|
||||
dialog.reset_operation();
|
||||
_runtime_config_generator.generate_runtime_config();
|
||||
}
|
||||
|
||||
|
||||
Storage(Env &env, Allocator &alloc, Dialog::Generator &dialog_generator,
|
||||
Runtime_config_generator &runtime_config_generator,
|
||||
Target_user &target_user)
|
||||
:
|
||||
_env(env), _alloc(alloc),
|
||||
_dialog_generator(dialog_generator),
|
||||
_runtime_config_generator(runtime_config_generator),
|
||||
_target_user(target_user)
|
||||
{
|
||||
_block_devices_rom .sigh(_storage_device_update_handler);
|
||||
_usb_active_config_rom.sigh(_storage_device_update_handler);
|
||||
}
|
||||
};
|
||||
|
||||
#endif /* _STORAGE_H_ */
|
7
repos/gems/src/app/sculpt_manager/target.mk
Normal file
7
repos/gems/src/app/sculpt_manager/target.mk
Normal file
@ -0,0 +1,7 @@
|
||||
TARGET := sculpt_manager
|
||||
SRC_CC := $(notdir $(wildcard $(PRG_DIR)/*.cc))
|
||||
SRC_CC += $(addprefix runtime/,$(notdir $(wildcard $(PRG_DIR)/runtime/*.cc)))
|
||||
SRC_CC += $(addprefix view/, $(notdir $(wildcard $(PRG_DIR)/view/*.cc)))
|
||||
SRC_CC += $(addprefix model/, $(notdir $(wildcard $(PRG_DIR)/model/*.cc)))
|
||||
LIBS += base
|
||||
INC_DIR += $(PRG_DIR) $(REP_DIR)/src/app/depot_deploy
|
49
repos/gems/src/app/sculpt_manager/types.h
Normal file
49
repos/gems/src/app/sculpt_manager/types.h
Normal file
@ -0,0 +1,49 @@
|
||||
/*
|
||||
* \brief Common types used within the Sculpt manager
|
||||
* \author Norman Feske
|
||||
* \date 2018-04-30
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _TYPES_H_
|
||||
#define _TYPES_H_
|
||||
|
||||
#include <util/list_model.h>
|
||||
#include <base/env.h>
|
||||
#include <base/attached_rom_dataspace.h>
|
||||
#include <platform_session/platform_session.h>
|
||||
#include <nitpicker_session/nitpicker_session.h>
|
||||
#include <usb_session/usb_session.h>
|
||||
#include <log_session/log_session.h>
|
||||
#include <timer_session/timer_session.h>
|
||||
#include <file_system_session/file_system_session.h>
|
||||
#include <report_session/report_session.h>
|
||||
#include <block_session/block_session.h>
|
||||
#include <terminal_session/terminal_session.h>
|
||||
#include <rom_session/rom_session.h>
|
||||
#include <rm_session/rm_session.h>
|
||||
#include <nic_session/nic_session.h>
|
||||
#include <rtc_session/rtc_session.h>
|
||||
#include <trace_session/trace_session.h>
|
||||
|
||||
namespace Sculpt {
|
||||
|
||||
using namespace Genode;
|
||||
|
||||
typedef String<32> Rom_name;
|
||||
typedef String<128> Path;
|
||||
typedef String<36> Start_name;
|
||||
typedef String<64> Label;
|
||||
|
||||
typedef Nitpicker::Point Point;
|
||||
|
||||
enum Writeable { WRITEABLE, READ_ONLY };
|
||||
}
|
||||
|
||||
#endif /* _TYPES_H_ */
|
65
repos/gems/src/app/sculpt_manager/view/activatable_item.h
Normal file
65
repos/gems/src/app/sculpt_manager/view/activatable_item.h
Normal file
@ -0,0 +1,65 @@
|
||||
/*
|
||||
* \brief GUI element that can be activated on clack
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-03
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _VIEW__ACTIVATABLE_ITEM_H_
|
||||
#define _VIEW__ACTIVATABLE_ITEM_H_
|
||||
|
||||
#include "hoverable_item.h"
|
||||
|
||||
namespace Sculpt { struct Activatable_item; }
|
||||
|
||||
|
||||
struct Sculpt::Activatable_item : Hoverable_item
|
||||
{
|
||||
typedef Hoverable_item::Id Id;
|
||||
|
||||
Id _selected { };
|
||||
Id _activated { };
|
||||
|
||||
/**
|
||||
* Apply click - if item is hovered, the click selects the item but
|
||||
* does not activate it yet
|
||||
*/
|
||||
void propose_activation_on_click()
|
||||
{
|
||||
_selected = _hovered;
|
||||
}
|
||||
|
||||
void confirm_activation_on_clack()
|
||||
{
|
||||
if (_hovered.valid() && (_hovered == _selected))
|
||||
_activated = _selected;
|
||||
}
|
||||
|
||||
void reset() { _selected = Id{}, _activated = Id{}; }
|
||||
|
||||
/**
|
||||
* Return true if item is currently activated
|
||||
*/
|
||||
bool activated(Id const &id) const { return id == _activated; }
|
||||
|
||||
/**
|
||||
* Generate button attributes depending on the item state
|
||||
*/
|
||||
void gen_button_attr(Xml_generator &xml, Id const &id) const
|
||||
{
|
||||
/* hover only as long as the button is not activated */
|
||||
if (!_selected.valid() || !_activated.valid())
|
||||
Hoverable_item::gen_button_attr(xml, id);
|
||||
|
||||
if (_selected.valid() && _selected == _hovered)
|
||||
xml.attribute("selected", "yes");
|
||||
}
|
||||
};
|
||||
|
||||
#endif /* _VIEW__ACTIVATABLE_ITEM_H_ */
|
39
repos/gems/src/app/sculpt_manager/view/dialog.h
Normal file
39
repos/gems/src/app/sculpt_manager/view/dialog.h
Normal file
@ -0,0 +1,39 @@
|
||||
/*
|
||||
* \brief Menu-view dialog handling
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-18
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _VIEW__DIALOG_H_
|
||||
#define _VIEW__DIALOG_H_
|
||||
|
||||
/* Genode includes */
|
||||
#include <input/event.h>
|
||||
|
||||
/* local includes */
|
||||
#include "types.h"
|
||||
|
||||
namespace Sculpt { struct Dialog; }
|
||||
|
||||
|
||||
struct Sculpt::Dialog : Interface
|
||||
{
|
||||
/**
|
||||
* Interface for triggering the (re-)generation of a menu-view dialog
|
||||
*
|
||||
* This interface ls implemented by a top-level dialog and called by a sub
|
||||
* dialog.
|
||||
*/
|
||||
struct Generator : Interface { virtual void generate_dialog() = 0; };
|
||||
|
||||
virtual void hover(Xml_node hover) = 0;
|
||||
};
|
||||
|
||||
#endif /* _VIEW__DIALOG_H_ */
|
69
repos/gems/src/app/sculpt_manager/view/download_status.h
Normal file
69
repos/gems/src/app/sculpt_manager/view/download_status.h
Normal file
@ -0,0 +1,69 @@
|
||||
/*
|
||||
* \brief Generate download-status view
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-18
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _VIEW__DOWNLOAD_STATUS_H_
|
||||
#define _VIEW__DOWNLOAD_STATUS_H_
|
||||
|
||||
/* local includes */
|
||||
#include <xml.h>
|
||||
|
||||
namespace Sculpt { static void gen_download_status(Xml_generator &, Xml_node); }
|
||||
|
||||
|
||||
void Sculpt::gen_download_status(Xml_generator &xml, Xml_node state)
|
||||
{
|
||||
gen_named_node(xml, "frame", "downloads", [&] () {
|
||||
xml.node("vbox", [&] () {
|
||||
|
||||
xml.node("label", [&] () {
|
||||
xml.attribute("text", "Download"); });
|
||||
|
||||
unsigned count = 0;
|
||||
state.for_each_sub_node("archive", [&] (Xml_node archive) {
|
||||
gen_named_node(xml, "hbox", String<10>(count++), [&] () {
|
||||
gen_named_node(xml, "float", "left", [&] () {
|
||||
xml.attribute("west", "yes");
|
||||
typedef String<40> Path;
|
||||
xml.node("label", [&] () {
|
||||
xml.attribute("text", archive.attribute_value("path", Path()));
|
||||
xml.attribute("font", "annotation/regular");
|
||||
});
|
||||
});
|
||||
|
||||
typedef String<16> Info;
|
||||
|
||||
Info info = archive.attribute_value("state", Info());
|
||||
float const total = archive.attribute_value("total", 0.0);
|
||||
float const now = archive.attribute_value("now", 0.0);
|
||||
|
||||
if (info == "download") {
|
||||
if (total > 0.0)
|
||||
info = Info((unsigned)((100*now)/total), "%");
|
||||
else
|
||||
info = Info("fetch");
|
||||
}
|
||||
|
||||
gen_named_node(xml, "float", "right", [&] () {
|
||||
xml.attribute("east", "yes");
|
||||
xml.node("label", [&] () {
|
||||
xml.attribute("text", info);
|
||||
xml.attribute("font", "annotation/regular");
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
#endif /* _VIEW__DOWNLOAD_STATUS_H_ */
|
58
repos/gems/src/app/sculpt_manager/view/hoverable_item.h
Normal file
58
repos/gems/src/app/sculpt_manager/view/hoverable_item.h
Normal file
@ -0,0 +1,58 @@
|
||||
/*
|
||||
* \brief GUI element that shows hovering feedback
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-03
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _VIEW__HOVERABLE_ITEM_H_
|
||||
#define _VIEW__HOVERABLE_ITEM_H_
|
||||
|
||||
#include "types.h"
|
||||
#include "xml.h"
|
||||
|
||||
namespace Sculpt { struct Hoverable_item; }
|
||||
|
||||
|
||||
struct Sculpt::Hoverable_item
|
||||
{
|
||||
typedef String<64> Id;
|
||||
|
||||
Id _hovered { };
|
||||
|
||||
/**
|
||||
* Set ID to matching hover sub node name
|
||||
*
|
||||
* \return true if hovering changed
|
||||
*/
|
||||
template <typename... ARGS>
|
||||
bool match(Xml_node hover, ARGS &&... args)
|
||||
{
|
||||
Id const orig = _hovered;
|
||||
_hovered = query_attribute<Id>(hover, args...);
|
||||
return _hovered != orig;
|
||||
}
|
||||
|
||||
/**
|
||||
* Return true if item is currently hovered
|
||||
*/
|
||||
bool hovered(Id const &id) const { return id == _hovered; }
|
||||
|
||||
/**
|
||||
* Generate button attributes depending on the item state
|
||||
*/
|
||||
void gen_button_attr(Xml_generator &xml, Id const &id) const
|
||||
{
|
||||
xml.attribute("name", id);
|
||||
|
||||
if (hovered(id)) xml.attribute("hovered", "yes");
|
||||
}
|
||||
};
|
||||
|
||||
#endif /* _VIEW__HOVERABLE_ITEM_H_ */
|
295
repos/gems/src/app/sculpt_manager/view/network_dialog.cc
Normal file
295
repos/gems/src/app/sculpt_manager/view/network_dialog.cc
Normal file
@ -0,0 +1,295 @@
|
||||
/*
|
||||
* \brief Network management dialog
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-07
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
/* Genode includes */
|
||||
#include <base/log.h>
|
||||
|
||||
/* local includes */
|
||||
#include "network_dialog.h"
|
||||
|
||||
void Sculpt::Network_dialog::_gen_access_point(Xml_generator &xml,
|
||||
Access_point const &ap) const
|
||||
{
|
||||
gen_named_node(xml, "hbox", ap.bssid, [&] () {
|
||||
|
||||
gen_named_node(xml, "float", "left", [&] () {
|
||||
xml.attribute("west", "yes");
|
||||
|
||||
xml.node("hbox", [&] () {
|
||||
gen_named_node(xml, "button", "button", [&] () {
|
||||
|
||||
if (_wifi_connection.connected())
|
||||
xml.attribute("selected", "yes");
|
||||
else
|
||||
_ap_item.gen_button_attr(xml, ap.bssid);
|
||||
|
||||
xml.node("label", [&] () {
|
||||
xml.attribute("text", " "); }); });
|
||||
|
||||
gen_named_node(xml, "label", "ssid", [&] () {
|
||||
xml.attribute("text", String<20>(" ", ap.ssid)); });
|
||||
|
||||
gen_named_node(xml, "label", "protection", [&] () {
|
||||
xml.attribute("font", "annotation/regular");
|
||||
if (ap.protection == Access_point::WPA_PSK)
|
||||
xml.attribute("text", " (WPA) ");
|
||||
else
|
||||
xml.attribute("text", " ");
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
gen_named_node(xml, "float", "right", [&] () {
|
||||
xml.attribute("east", "yes");
|
||||
xml.node("label", [&] () {
|
||||
xml.attribute("text", String<8>(ap.quality, "%")); });
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
bool Sculpt::Network_dialog::_selected_ap_visible() const
|
||||
{
|
||||
unsigned cnt = 0;
|
||||
return _for_each_ap([&] (Access_point const &ap) {
|
||||
return (cnt++ < _max_visible_aps) && _ap_item.selected(ap.bssid); });
|
||||
}
|
||||
|
||||
|
||||
bool Sculpt::Network_dialog::_selected_ap_unprotected() const
|
||||
{
|
||||
return _for_each_ap([&] (Access_point const &ap) {
|
||||
return _ap_item.selected(ap.bssid) && ap.unprotected(); });
|
||||
}
|
||||
|
||||
|
||||
bool Sculpt::Network_dialog::need_keyboard_focus_for_passphrase() const
|
||||
{
|
||||
if (_wifi_connection.state == Wifi_connection::CONNECTED)
|
||||
return false;
|
||||
|
||||
return _for_each_ap([&] (Access_point const &ap) {
|
||||
return _ap_item.selected(ap.bssid) && ap.wpa_protected(); });
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Network_dialog::_gen_access_point_list(Xml_generator &xml) const
|
||||
{
|
||||
if (_wlan_config_policy == WLAN_CONFIG_MANUAL)
|
||||
return;
|
||||
|
||||
bool const selected_ap_visible = _selected_ap_visible();
|
||||
|
||||
unsigned cnt = 0;
|
||||
_access_points.for_each([&] (Access_point const &ap) {
|
||||
|
||||
if (cnt++ >= _max_visible_aps)
|
||||
return;
|
||||
|
||||
/*
|
||||
* Whenever the user has selected an access point, hide all others.
|
||||
* Should the selected AP disappear from the list, show all others.
|
||||
*/
|
||||
bool const selected = _ap_item.selected(ap.bssid);
|
||||
if (selected_ap_visible && !selected)
|
||||
return;
|
||||
|
||||
_gen_access_point(xml, ap);
|
||||
|
||||
if (!selected)
|
||||
return;
|
||||
|
||||
bool const connected_to_selected_ap =
|
||||
(selected && _wifi_connection.bssid == ap.bssid)
|
||||
&& _wifi_connection.state == Wifi_connection::CONNECTED;
|
||||
|
||||
if (connected_to_selected_ap)
|
||||
return;
|
||||
|
||||
if (ap.protection == Access_point::WPA_PSK) {
|
||||
gen_named_node(xml, "label", "passphrase msg", [&] () {
|
||||
xml.attribute("text", "Enter passphrase:"); });
|
||||
|
||||
gen_named_node(xml, "frame", "passphrase", [&] () {
|
||||
xml.node("float", [&] () {
|
||||
xml.attribute("west", "yes");
|
||||
xml.node("label", [&] () {
|
||||
xml.attribute("font", "title/regular");
|
||||
xml.attribute("text", String<3*64>(" ", _wpa_passphrase));
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
if (_wpa_passphrase.suitable_for_connect()) {
|
||||
xml.node("button", [&] () {
|
||||
|
||||
if (_wifi_connection.state == Wifi_connection::CONNECTING)
|
||||
xml.attribute("selected", "yes");
|
||||
|
||||
/* suppress hover while connecting */
|
||||
else
|
||||
_connect_item.gen_button_attr(xml, "connect");
|
||||
|
||||
xml.node("label", [&] () {
|
||||
xml.attribute("text", "Connect"); });
|
||||
});
|
||||
}
|
||||
}
|
||||
});
|
||||
|
||||
/*
|
||||
* Present motivational message until we get the first 'wlan_accesspoints'
|
||||
* report.
|
||||
*/
|
||||
if (cnt == 0)
|
||||
xml.node("label", [&] () {
|
||||
xml.attribute("text", "Scanning..."); });
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Network_dialog::_gen_connected_ap(Xml_generator &xml) const
|
||||
{
|
||||
bool done = false;
|
||||
|
||||
/*
|
||||
* Try to present complete info including the quality from access-point
|
||||
* list.
|
||||
*/
|
||||
_access_points.for_each([&] (Access_point const &ap) {
|
||||
if (!done && _wifi_connection.bssid == ap.bssid) {
|
||||
_gen_access_point(xml, ap);
|
||||
done = true;
|
||||
}
|
||||
});
|
||||
|
||||
/*
|
||||
* If access point is not present in the list, fall back to the information
|
||||
* given in the 'wlan_state' report.
|
||||
*/
|
||||
if (!done)
|
||||
_gen_access_point(xml, Access_point { _wifi_connection.bssid,
|
||||
_wifi_connection.ssid,
|
||||
Access_point::UNKNOWN });
|
||||
|
||||
gen_named_node(xml, "label", "associated", [&] () {
|
||||
xml.attribute("text", "associated"); });
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Network_dialog::generate(Xml_generator &xml) const
|
||||
{
|
||||
gen_named_node(xml, "frame", "network", [&] () {
|
||||
xml.node("vbox", [&] () {
|
||||
gen_named_node(xml, "label", "title", [&] () {
|
||||
xml.attribute("text", "Network");
|
||||
xml.attribute("font", "title/regular");
|
||||
});
|
||||
|
||||
gen_named_node(xml, "hbox", "type", [&] () {
|
||||
|
||||
auto gen_nic_button = [&] (Hoverable_item::Id const &id,
|
||||
Nic_target::Type const type,
|
||||
String<10> const &label) {
|
||||
gen_named_node(xml, "button", id, [&] () {
|
||||
|
||||
_nic_item.gen_button_attr(xml, id);
|
||||
|
||||
if (_nic_target.type == type)
|
||||
xml.attribute("selected", "yes");
|
||||
|
||||
xml.node("label", [&] () { xml.attribute("text", label); });
|
||||
});
|
||||
};
|
||||
|
||||
gen_nic_button("off", Nic_target::OFF, "Off");
|
||||
|
||||
/*
|
||||
* Allow interactive selection only if NIC-router configuration
|
||||
* is not manually maintained.
|
||||
*/
|
||||
if (_nic_target.managed() || _nic_target.local())
|
||||
gen_nic_button("local", Nic_target::LOCAL, "Local");
|
||||
|
||||
if (_nic_target.managed() || _nic_target.wired())
|
||||
gen_nic_button("wired", Nic_target::WIRED, "Wired");
|
||||
|
||||
if (_nic_target.managed() || _nic_target.wifi())
|
||||
gen_nic_button("wifi", Nic_target::WIFI, "Wifi");
|
||||
});
|
||||
|
||||
if (_nic_target.type == Nic_target::WIFI || _nic_target.type == Nic_target::WIRED) {
|
||||
gen_named_node(xml, "frame", "nic_info", [&] () {
|
||||
xml.node("vbox", [&] () {
|
||||
|
||||
/*
|
||||
* If connected via Wifi, show the information of the
|
||||
* connected access point. If not connected, present
|
||||
* the complete list of access points with the option
|
||||
* to select one.
|
||||
*/
|
||||
if (_nic_target.type == Nic_target::WIFI) {
|
||||
if (_wifi_connection.connected())
|
||||
_gen_connected_ap(xml);
|
||||
else
|
||||
_gen_access_point_list(xml);
|
||||
}
|
||||
|
||||
/* append display of uplink IP address */
|
||||
if (_nic_state.ready())
|
||||
gen_named_node(xml, "label", "ip", [&] () {
|
||||
xml.attribute("text", _nic_state.ipv4); });
|
||||
});
|
||||
});
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Network_dialog::hover(Xml_node hover)
|
||||
{
|
||||
bool const changed =
|
||||
_nic_item .match(hover, "vbox", "hbox", "button", "name") |
|
||||
_ap_item .match(hover, "vbox", "frame", "vbox", "hbox", "name") |
|
||||
_connect_item.match(hover, "vbox", "frame", "vbox", "button", "name");
|
||||
|
||||
_nic_info.match(hover, "vbox", "frame", "name");
|
||||
|
||||
if (changed)
|
||||
_dialog_generator.generate_dialog();
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Network_dialog::click(Action &action)
|
||||
{
|
||||
if (_nic_item.hovered("off")) action.nic_target(Nic_target::OFF);
|
||||
if (_nic_item.hovered("local")) action.nic_target(Nic_target::LOCAL);
|
||||
if (_nic_item.hovered("wired")) action.nic_target(Nic_target::WIRED);
|
||||
if (_nic_item.hovered("wifi")) action.nic_target(Nic_target::WIFI);
|
||||
|
||||
if (_wifi_connection.connected() && _ap_item.hovered(_wifi_connection.bssid)) {
|
||||
action.wifi_disconnect();
|
||||
_ap_item.reset();
|
||||
} else {
|
||||
_ap_item.toggle_selection_on_click();
|
||||
|
||||
/* immediately connect to unprotected access point when selected */
|
||||
if (_ap_item.any_selected() && _selected_ap_unprotected())
|
||||
action.wifi_connect(selected_ap());
|
||||
}
|
||||
|
||||
if (_connect_item.hovered("connect"))
|
||||
action.wifi_connect(selected_ap());
|
||||
|
||||
_dialog_generator.generate_dialog();
|
||||
}
|
113
repos/gems/src/app/sculpt_manager/view/network_dialog.h
Normal file
113
repos/gems/src/app/sculpt_manager/view/network_dialog.h
Normal file
@ -0,0 +1,113 @@
|
||||
/*
|
||||
* \brief Network management dialog
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-07
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _VIEW__NETWORK_DIALOG_H_
|
||||
#define _VIEW__NETWORK_DIALOG_H_
|
||||
|
||||
#include <types.h>
|
||||
#include <model/nic_target.h>
|
||||
#include <model/nic_state.h>
|
||||
#include <model/wifi_connection.h>
|
||||
#include <model/wpa_passphrase.h>
|
||||
#include <view/dialog.h>
|
||||
#include <view/selectable_item.h>
|
||||
|
||||
namespace Sculpt { struct Network_dialog; }
|
||||
|
||||
|
||||
struct Sculpt::Network_dialog : Dialog
|
||||
{
|
||||
Env &_env;
|
||||
|
||||
Dialog::Generator &_dialog_generator;
|
||||
|
||||
enum Wlan_config_policy { WLAN_CONFIG_MANAGED, WLAN_CONFIG_MANUAL };
|
||||
|
||||
Nic_target const &_nic_target;
|
||||
Access_points const &_access_points;
|
||||
Wifi_connection const &_wifi_connection;
|
||||
Nic_state const &_nic_state;
|
||||
Blind_wpa_passphrase const &_wpa_passphrase;
|
||||
Wlan_config_policy const &_wlan_config_policy;
|
||||
|
||||
Hoverable_item _nic_item { };
|
||||
Selectable_item _ap_item { };
|
||||
Hoverable_item _nic_info { };
|
||||
Hoverable_item _connect_item { }; /* confirm WPA passphrase */
|
||||
|
||||
bool ap_list_hovered() const { return _nic_target.type == Nic_target::WIFI
|
||||
&& _nic_info.hovered("nic_info"); }
|
||||
|
||||
/*
|
||||
* \return true if at least one access point fulfils the condition 'COND_FN'
|
||||
*/
|
||||
template <typename COND_FN>
|
||||
bool _for_each_ap(COND_FN const &cond_fn) const
|
||||
{
|
||||
bool result = false;
|
||||
_access_points.for_each([&] (Access_point const &ap) {
|
||||
result |= cond_fn(ap); });
|
||||
return result;
|
||||
}
|
||||
|
||||
Access_point::Bssid selected_ap() const { return _ap_item._selected; }
|
||||
|
||||
/* limit view to highest-quality access points */
|
||||
unsigned const _max_visible_aps = 20;
|
||||
|
||||
/* determine whether the selected AP is present in access-point list */
|
||||
bool _selected_ap_visible() const;
|
||||
|
||||
bool _selected_ap_unprotected() const;
|
||||
|
||||
void _gen_access_point(Xml_generator &, Access_point const &) const;
|
||||
void _gen_connected_ap(Xml_generator &) const;
|
||||
void _gen_access_point_list(Xml_generator &) const;
|
||||
|
||||
void generate(Xml_generator &) const;
|
||||
|
||||
bool need_keyboard_focus_for_passphrase() const;
|
||||
|
||||
/**
|
||||
* Dialog interface
|
||||
*/
|
||||
void hover(Xml_node hover) override;
|
||||
|
||||
struct Action : Interface
|
||||
{
|
||||
virtual void nic_target(Nic_target::Type) = 0;
|
||||
|
||||
virtual void wifi_connect(Access_point::Ssid) = 0;
|
||||
|
||||
virtual void wifi_disconnect() = 0;
|
||||
};
|
||||
|
||||
void click(Action &action);
|
||||
|
||||
Network_dialog(Env &env,
|
||||
Dialog::Generator &dialog_generator,
|
||||
Nic_target const &nic_target,
|
||||
Access_points const &access_points,
|
||||
Wifi_connection const &wifi_connection,
|
||||
Nic_state const &nic_state,
|
||||
Blind_wpa_passphrase const &wpa_passphrase,
|
||||
Wlan_config_policy const &wlan_config_policy)
|
||||
:
|
||||
_env(env), _dialog_generator(dialog_generator),
|
||||
_nic_target(nic_target), _access_points(access_points),
|
||||
_wifi_connection(wifi_connection), _nic_state(nic_state),
|
||||
_wpa_passphrase(wpa_passphrase), _wlan_config_policy(wlan_config_policy)
|
||||
{ }
|
||||
};
|
||||
|
||||
#endif /* _VIEW__NETWORK_DIALOG_H_ */
|
59
repos/gems/src/app/sculpt_manager/view/selectable_item.h
Normal file
59
repos/gems/src/app/sculpt_manager/view/selectable_item.h
Normal file
@ -0,0 +1,59 @@
|
||||
/*
|
||||
* \brief GUI element that has a hovered and selected state
|
||||
* \author Norman Feske
|
||||
* \date 2018-05-03
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _VIEW__SELECTABLE_ITEM_H_
|
||||
#define _VIEW__SELECTABLE_ITEM_H_
|
||||
|
||||
#include "hoverable_item.h"
|
||||
|
||||
namespace Sculpt { struct Selectable_item; }
|
||||
|
||||
|
||||
struct Sculpt::Selectable_item : Hoverable_item
|
||||
{
|
||||
typedef Hoverable_item::Id Id;
|
||||
|
||||
Id _selected { };
|
||||
|
||||
/**
|
||||
* Apply click - if item is hovered, the click toggles the selection
|
||||
*/
|
||||
void toggle_selection_on_click()
|
||||
{
|
||||
if (_hovered.valid())
|
||||
_selected = (_hovered == _selected) ? Id() : _hovered;
|
||||
}
|
||||
|
||||
void select(Id const &id) { _selected = id; }
|
||||
|
||||
void reset() { _selected = Id{}; }
|
||||
|
||||
/**
|
||||
* Return true if item is currently selected
|
||||
*/
|
||||
bool selected(Id const &id) const { return id == _selected; }
|
||||
|
||||
bool any_selected() const { return _selected.valid(); }
|
||||
|
||||
/**
|
||||
* Generate button attributes depending on the item state
|
||||
*/
|
||||
void gen_button_attr(Xml_generator &xml, Id const &id) const
|
||||
{
|
||||
Hoverable_item::gen_button_attr(xml, id);
|
||||
|
||||
if (selected(id)) xml.attribute("selected", "yes");
|
||||
}
|
||||
};
|
||||
|
||||
#endif /* _SELECTABLE_ITEM_H_ */
|
533
repos/gems/src/app/sculpt_manager/view/storage_dialog.cc
Normal file
533
repos/gems/src/app/sculpt_manager/view/storage_dialog.cc
Normal file
@ -0,0 +1,533 @@
|
||||
/*
|
||||
* \brief Storage management dialog
|
||||
* \author Norman Feske
|
||||
* \date 2018-04-30
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
/* Genode includes */
|
||||
#include <base/log.h>
|
||||
|
||||
/* local includes */
|
||||
#include "storage_dialog.h"
|
||||
|
||||
|
||||
void Sculpt::Storage_dialog::_gen_partition_operations(Xml_generator &xml,
|
||||
Storage_device const &device,
|
||||
Partition const &partition) const
|
||||
{
|
||||
Storage_target const target { device.label, partition.number };
|
||||
|
||||
String<16> const version(device.label, ".", partition.number);
|
||||
|
||||
bool const whole_device = !partition.number.valid();
|
||||
|
||||
bool const device_in_use = (_used_target.device == device.label);
|
||||
|
||||
bool const target_in_use = (_used_target == target)
|
||||
|| (whole_device && device_in_use)
|
||||
|| partition.file_system_inspected;
|
||||
|
||||
bool const relabel_in_progress = device.relabel_in_progress();
|
||||
|
||||
bool const expand_in_progress = device.expand_in_progress();
|
||||
|
||||
bool const format_selected = _operation_item.selected("format");
|
||||
|
||||
bool const expand_selected = _operation_item.selected("expand");
|
||||
|
||||
if (partition.file_system.accessible() && !format_selected
|
||||
&& !expand_selected && !expand_in_progress) {
|
||||
|
||||
if (!partition.check_in_progress && !partition.format_in_progress
|
||||
&& partition.file_system.accessible() && !relabel_in_progress) {
|
||||
|
||||
xml.node("button", [&] () {
|
||||
_inspect_item.gen_button_attr(xml, "browse");
|
||||
xml.attribute("version", version);
|
||||
|
||||
if (partition.file_system_inspected)
|
||||
xml.attribute("selected", "yes");
|
||||
|
||||
xml.node("label", [&] () { xml.attribute("text", "Inspect"); });
|
||||
});
|
||||
}
|
||||
|
||||
if ((!_used_target.valid() || _used_target == target)
|
||||
&& !partition.check_in_progress && !partition.format_in_progress
|
||||
&& !relabel_in_progress) {
|
||||
|
||||
xml.node("button", [&] () {
|
||||
xml.attribute("version", version);
|
||||
_use_item.gen_button_attr(xml, "use");
|
||||
if (_used_target == target)
|
||||
xml.attribute("selected", "yes");
|
||||
xml.node("label", [&] () { xml.attribute("text", "Use"); });
|
||||
});
|
||||
}
|
||||
|
||||
if ((device.all_partitions_idle() || partition.relabel_in_progress())
|
||||
&& partition.genode() && !device_in_use) {
|
||||
|
||||
xml.node("button", [&] () {
|
||||
|
||||
/* support hovering only if no relabeling is in progress */
|
||||
if (partition.relabel_in_progress())
|
||||
xml.attribute("name", "relabel");
|
||||
else
|
||||
_relabel_item.gen_button_attr(xml, "relabel");
|
||||
|
||||
xml.attribute("version", version);
|
||||
|
||||
if (partition.genode_default() || partition.relabel_in_progress())
|
||||
xml.attribute("selected", "yes");
|
||||
|
||||
xml.node("label", [&] () {
|
||||
xml.attribute("text", "Default"); });
|
||||
});
|
||||
if (partition.relabel_in_progress())
|
||||
xml.node("label", [&] () { xml.attribute("text", "In progress..."); });
|
||||
}
|
||||
|
||||
if (!target_in_use && !partition.format_in_progress && partition.checkable()
|
||||
&& !relabel_in_progress) {
|
||||
|
||||
xml.node("button", [&] () {
|
||||
_operation_item.gen_button_attr(xml, "check");
|
||||
xml.attribute("version", version);
|
||||
|
||||
if (partition.check_in_progress)
|
||||
xml.attribute("selected", "yes");
|
||||
|
||||
xml.node("label", [&] () { xml.attribute("text", "Check"); });
|
||||
});
|
||||
if (partition.check_in_progress)
|
||||
xml.node("label", [&] () { xml.attribute("text", "In progress..."); });
|
||||
}
|
||||
}
|
||||
|
||||
bool const whole_device_with_partition_in_use =
|
||||
whole_device && !device.all_partitions_idle();
|
||||
|
||||
bool const format_button_visible = !target_in_use
|
||||
&& !whole_device_with_partition_in_use
|
||||
&& !partition.check_in_progress
|
||||
&& !expand_in_progress
|
||||
&& !relabel_in_progress
|
||||
&& !_operation_item.selected("expand");
|
||||
|
||||
bool const expand_button_visible = !target_in_use
|
||||
&& !whole_device
|
||||
&& !partition.check_in_progress
|
||||
&& !partition.format_in_progress
|
||||
&& !relabel_in_progress
|
||||
&& partition.expandable()
|
||||
&& !_operation_item.selected("format");
|
||||
|
||||
bool const progress_msg_visible =
|
||||
(_operation_item.selected("format") && partition.format_in_progress)
|
||||
|| (_operation_item.selected("expand") && partition.expand_in_progress());
|
||||
|
||||
bool const confirm_visible =
|
||||
(_operation_item.selected("format") && !partition.format_in_progress)
|
||||
|| (_operation_item.selected("expand") && !partition.expand_in_progress());
|
||||
|
||||
if (format_button_visible) {
|
||||
xml.node("button", [&] () {
|
||||
_operation_item.gen_button_attr(xml, "format");
|
||||
xml.attribute("version", version);
|
||||
|
||||
if (partition.format_in_progress)
|
||||
xml.attribute("selected", "yes");
|
||||
|
||||
if (whole_device) {
|
||||
xml.node("label", [&] () { xml.attribute("text", "Format device"); });
|
||||
} else {
|
||||
xml.node("label", [&] () { xml.attribute("text", "Format partition"); });
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
if (expand_button_visible) {
|
||||
xml.node("button", [&] () {
|
||||
_operation_item.gen_button_attr(xml, "expand");
|
||||
xml.attribute("version", version);
|
||||
|
||||
if (partition.expand_in_progress())
|
||||
xml.attribute("selected", "yes");
|
||||
|
||||
xml.node("label", [&] () { xml.attribute("text", "Expand"); });
|
||||
});
|
||||
}
|
||||
|
||||
if (progress_msg_visible)
|
||||
xml.node("label", [&] () { xml.attribute("text", "In progress..."); });
|
||||
|
||||
if (confirm_visible) {
|
||||
xml.node("button", [&] () {
|
||||
_confirm_item.gen_button_attr(xml, "confirm");
|
||||
xml.attribute("version", version);
|
||||
xml.node("label", [&] () { xml.attribute("text", "Confirm"); });
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Storage_dialog::_gen_partition(Xml_generator &xml,
|
||||
Storage_device const &device,
|
||||
Partition const &partition) const
|
||||
{
|
||||
bool const selected = _partition_item.selected(partition.number);
|
||||
|
||||
gen_named_node(xml, "hbox", partition.number, [&] () {
|
||||
gen_named_node(xml, "float", "left", [&] () {
|
||||
xml.attribute("west", "yes");
|
||||
xml.node("hbox", [&] () {
|
||||
gen_named_node(xml, "button", "button", [&] () {
|
||||
|
||||
if (_partition_item.hovered(partition.number))
|
||||
xml.attribute("hovered", "yes");
|
||||
|
||||
if (selected)
|
||||
xml.attribute("selected", "yes");
|
||||
|
||||
xml.node("label", [&] () { xml.attribute("text", partition.number); });
|
||||
});
|
||||
|
||||
if (partition.label.length() > 1)
|
||||
gen_named_node(xml, "label", "label", [&] () {
|
||||
xml.attribute("text", String<80>(" (", partition.label, ") ")); });
|
||||
|
||||
Storage_target const target { device.label, partition.number };
|
||||
if (_used_target == target)
|
||||
gen_named_node(xml, "label", "used", [&] () { xml.attribute("text", "* "); });
|
||||
});
|
||||
});
|
||||
|
||||
gen_named_node(xml, "float", "right", [&] () {
|
||||
xml.attribute("east", "yes");
|
||||
xml.node("label", [&] () {
|
||||
xml.attribute("text", String<64>(partition.capacity, " ")); });
|
||||
});
|
||||
});
|
||||
|
||||
if (selected)
|
||||
_gen_partition_operations(xml, device, partition);
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Storage_dialog::_gen_block_device(Xml_generator &xml,
|
||||
Block_device const &dev) const
|
||||
{
|
||||
bool const selected = _device_item.selected(dev.label);
|
||||
|
||||
xml.node("button", [&] () {
|
||||
xml.attribute("name", dev.label);
|
||||
|
||||
if (_device_item.hovered(dev.label))
|
||||
xml.attribute("hovered", "yes");
|
||||
|
||||
if (selected)
|
||||
xml.attribute("selected", "yes");
|
||||
|
||||
xml.node("hbox", [&] () {
|
||||
gen_named_node(xml, "float", "info", [&] () {
|
||||
xml.attribute("west", "yes");
|
||||
xml.node("hbox", [&] () {
|
||||
gen_named_node(xml, "label", "device", [&] () {
|
||||
xml.attribute("text", dev.label); });
|
||||
gen_named_node(xml, "label", "model", [&] () {
|
||||
xml.attribute("text", String<80>(" (", dev.model, ") ")); });
|
||||
if (_used_target.device == dev.label)
|
||||
gen_named_node(xml, "label", "used", [&] () {
|
||||
xml.attribute("text", "* "); });
|
||||
});
|
||||
});
|
||||
|
||||
gen_named_node(xml, "float", "capacity", [&] () {
|
||||
xml.attribute("east", "yes");
|
||||
xml.node("label", [&] () {
|
||||
xml.attribute("text", String<64>(dev.capacity)); }); });
|
||||
});
|
||||
});
|
||||
|
||||
if (selected) {
|
||||
xml.node("frame", [&] () {
|
||||
xml.attribute("name", dev.label);
|
||||
xml.node("vbox", [&] () {
|
||||
dev.partitions.for_each([&] (Partition const &partition) {
|
||||
_gen_partition(xml, dev, partition); });
|
||||
|
||||
if (!_partition_item.any_selected())
|
||||
_gen_partition_operations(xml, dev, *dev.whole_device_partition);
|
||||
});
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Storage_dialog::_gen_usb_storage_device(Xml_generator &xml,
|
||||
Usb_storage_device const &dev) const
|
||||
{
|
||||
bool const selected = _device_item.selected(dev.label);
|
||||
|
||||
xml.node("button", [&] () {
|
||||
xml.attribute("name", dev.label);
|
||||
|
||||
if (_device_item.hovered(dev.label))
|
||||
xml.attribute("hovered", "yes");
|
||||
|
||||
if (selected)
|
||||
xml.attribute("selected", "yes");
|
||||
|
||||
xml.node("hbox", [&] () {
|
||||
gen_named_node(xml, "float", "info", [&] () {
|
||||
xml.attribute("west", "yes");
|
||||
|
||||
xml.node("hbox", [&] () {
|
||||
|
||||
gen_named_node(xml, "label", "device", [&] () {
|
||||
xml.attribute("text", dev.label); });
|
||||
|
||||
if (dev.driver_info.constructed()) {
|
||||
gen_named_node(xml, "label", "vendor", [&] () {
|
||||
String<16> const vendor { dev.driver_info->vendor };
|
||||
xml.attribute("text", String<64>(" (", vendor, ") ")); });
|
||||
}
|
||||
|
||||
if (_used_target.device == dev.label)
|
||||
gen_named_node(xml, "label", "used", [&] () {
|
||||
xml.attribute("text", " *"); });
|
||||
});
|
||||
});
|
||||
|
||||
gen_named_node(xml, "float", "capacity", [&] () {
|
||||
xml.attribute("east", "yes");
|
||||
xml.node("label", [&] () {
|
||||
xml.attribute("text", String<64>(dev.capacity)); }); });
|
||||
});
|
||||
});
|
||||
|
||||
if (selected)
|
||||
xml.node("frame", [&] () {
|
||||
xml.attribute("name", dev.label);
|
||||
xml.node("vbox", [&] () {
|
||||
dev.partitions.for_each([&] (Partition const &partition) {
|
||||
_gen_partition(xml, dev, partition); });
|
||||
|
||||
if (!_partition_item.any_selected())
|
||||
_gen_partition_operations(xml, dev, *dev.whole_device_partition);
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Storage_dialog::_gen_ram_fs(Xml_generator &xml) const
|
||||
{
|
||||
bool const selected = _device_item.selected("ram_fs");
|
||||
|
||||
gen_named_node(xml, "button", "ram_fs", [&] () {
|
||||
|
||||
if (_device_item.hovered("ram_fs"))
|
||||
xml.attribute("hovered", "yes");
|
||||
|
||||
if (selected)
|
||||
xml.attribute("selected", "yes");
|
||||
|
||||
xml.node("hbox", [&] () {
|
||||
gen_named_node(xml, "float", "info", [&] () {
|
||||
xml.attribute("west", "yes");
|
||||
|
||||
xml.node("hbox", [&] () {
|
||||
|
||||
gen_named_node(xml, "label", "device", [&] () {
|
||||
xml.attribute("text", "ram (in-memory file system) "); });
|
||||
|
||||
if (_used_target.device == "ram_fs")
|
||||
gen_named_node(xml, "label", "used", [&] () {
|
||||
xml.attribute("text", "* "); });
|
||||
});
|
||||
});
|
||||
|
||||
gen_named_node(xml, "float", "capacity", [&] () {
|
||||
xml.attribute("east", "yes");
|
||||
xml.node("label", [&] () {
|
||||
Capacity const capacity { _ram_fs_state.ram_quota.value };
|
||||
xml.attribute("text", String<64>(capacity)); }); });
|
||||
});
|
||||
});
|
||||
|
||||
if (selected) {
|
||||
xml.node("frame", [&] () {
|
||||
xml.attribute("name", "ram_fs_operations");
|
||||
xml.node("vbox", [&] () {
|
||||
|
||||
xml.node("button", [&] () {
|
||||
_inspect_item.gen_button_attr(xml, "browse");
|
||||
|
||||
if (_ram_fs_state.inspected)
|
||||
xml.attribute("selected", "yes");
|
||||
|
||||
xml.node("label", [&] () { xml.attribute("text", "Inspect"); });
|
||||
});
|
||||
|
||||
if (!_used_target.valid() || _used_target.ram_fs()) {
|
||||
xml.node("button", [&] () {
|
||||
_use_item.gen_button_attr(xml, "use");
|
||||
if (_used_target.ram_fs())
|
||||
xml.attribute("selected", "yes");
|
||||
xml.node("label", [&] () { xml.attribute("text", "Use"); });
|
||||
});
|
||||
}
|
||||
|
||||
if (!_used_target.ram_fs() && !_ram_fs_state.inspected) {
|
||||
xml.node("button", [&] () {
|
||||
_operation_item.gen_button_attr(xml, "reset");
|
||||
|
||||
xml.node("label", [&] () { xml.attribute("text", "Reset"); });
|
||||
});
|
||||
|
||||
if (_operation_item.selected("reset")) {
|
||||
xml.node("button", [&] () {
|
||||
_confirm_item.gen_button_attr(xml, "confirm");
|
||||
xml.node("label", [&] () { xml.attribute("text", "Confirm"); });
|
||||
});
|
||||
}
|
||||
}
|
||||
});
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Storage_dialog::generate(Xml_generator &xml) const
|
||||
{
|
||||
gen_named_node(xml, "frame", "storage", [&] () {
|
||||
xml.node("vbox", [&] () {
|
||||
gen_named_node(xml, "label", "title", [&] () {
|
||||
xml.attribute("text", "Storage");
|
||||
xml.attribute("font", "title/regular");
|
||||
});
|
||||
_storage_devices.block_devices.for_each([&] (Block_device const &dev) {
|
||||
_gen_block_device(xml, dev); });
|
||||
_storage_devices.usb_storage_devices.for_each([&] (Usb_storage_device const &dev) {
|
||||
_gen_usb_storage_device(xml, dev); });
|
||||
|
||||
_gen_ram_fs(xml);
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Storage_dialog::hover(Xml_node hover)
|
||||
{
|
||||
bool const changed =
|
||||
_device_item .match(hover, "vbox", "button", "name") |
|
||||
_partition_item.match(hover, "vbox", "frame", "vbox", "hbox", "name") |
|
||||
_use_item .match(hover, "vbox", "frame", "vbox", "button", "name") |
|
||||
_relabel_item .match(hover, "vbox", "frame", "vbox", "button", "name") |
|
||||
_inspect_item .match(hover, "vbox", "frame", "vbox", "button", "name") |
|
||||
_operation_item.match(hover, "vbox", "frame", "vbox", "button", "name") |
|
||||
_confirm_item .match(hover, "vbox", "frame", "vbox", "button", "name");
|
||||
|
||||
if (changed)
|
||||
_dialog_generator.generate_dialog();
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Storage_dialog::click(Action &action)
|
||||
{
|
||||
Selectable_item::Id const old_selected_device = _device_item._selected;
|
||||
Selectable_item::Id const old_selected_partition = _partition_item._selected;
|
||||
|
||||
_device_item.toggle_selection_on_click();
|
||||
_partition_item.toggle_selection_on_click();
|
||||
|
||||
if (!_device_item.selected(old_selected_device))
|
||||
_partition_item.reset();
|
||||
|
||||
if (!_device_item.selected(old_selected_device)
|
||||
|| !_partition_item.selected(old_selected_partition))
|
||||
reset_operation();
|
||||
|
||||
Storage_target const target = _selected_storage_target();
|
||||
|
||||
if (_operation_item.hovered("format")) {
|
||||
if (_operation_item.selected("format"))
|
||||
action.cancel_format(_selected_storage_target());
|
||||
else
|
||||
_operation_item.toggle_selection_on_click();
|
||||
}
|
||||
|
||||
if (_operation_item.hovered("expand")) {
|
||||
if (_operation_item.selected("expand"))
|
||||
action.cancel_expand(_selected_storage_target());
|
||||
else
|
||||
_operation_item.toggle_selection_on_click();
|
||||
}
|
||||
|
||||
/* toggle confirmation button when clicking on ram_fs reset */
|
||||
if (_operation_item.hovered("reset"))
|
||||
_operation_item.toggle_selection_on_click();
|
||||
|
||||
if (_operation_item.hovered("check"))
|
||||
action.check(target);
|
||||
|
||||
/* toggle file browser */
|
||||
if (_inspect_item.hovered("browse"))
|
||||
action.toggle_file_browser(target);
|
||||
|
||||
if (_use_item.hovered("use")) {
|
||||
|
||||
/* release currently used device */
|
||||
if (target.valid() && target == _used_target)
|
||||
action.use(Storage_target{});
|
||||
|
||||
/* select new used device if none is defined */
|
||||
else if (!_used_target.valid())
|
||||
action.use(target);
|
||||
}
|
||||
|
||||
if (_relabel_item.hovered("relabel"))
|
||||
action.toggle_default_storage_target(target);
|
||||
|
||||
if (_confirm_item.hovered("confirm")) {
|
||||
_confirm_item.propose_activation_on_click();
|
||||
}
|
||||
|
||||
_dialog_generator.generate_dialog();
|
||||
}
|
||||
|
||||
|
||||
void Sculpt::Storage_dialog::clack(Action &action)
|
||||
{
|
||||
if (_confirm_item.hovered("confirm")) {
|
||||
|
||||
_confirm_item.confirm_activation_on_clack();
|
||||
|
||||
if (_confirm_item.activated("confirm")) {
|
||||
|
||||
Storage_target const target = _selected_storage_target();
|
||||
|
||||
if (_operation_item.selected("format"))
|
||||
action.format(target);
|
||||
|
||||
if (_operation_item.selected("expand"))
|
||||
action.expand(target);
|
||||
|
||||
if (target.ram_fs() && _operation_item.selected("reset"))
|
||||
action.reset_ram_fs();
|
||||
}
|
||||
} else {
|
||||
_confirm_item.reset();
|
||||
}
|
||||
|
||||
_dialog_generator.generate_dialog();
|
||||
}
|
||||
|
114
repos/gems/src/app/sculpt_manager/view/storage_dialog.h
Normal file
114
repos/gems/src/app/sculpt_manager/view/storage_dialog.h
Normal file
@ -0,0 +1,114 @@
|
||||
/*
|
||||
* \brief Storage management dialog
|
||||
* \author Norman Feske
|
||||
* \date 2018-04-30
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2018 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _VIEW__STORAGE_DIALOG_H_
|
||||
#define _VIEW__STORAGE_DIALOG_H_
|
||||
|
||||
#include <types.h>
|
||||
#include <model/storage_devices.h>
|
||||
#include <model/storage_target.h>
|
||||
#include <model/ram_fs_state.h>
|
||||
#include <view/selectable_item.h>
|
||||
#include <view/activatable_item.h>
|
||||
#include <view/dialog.h>
|
||||
|
||||
namespace Sculpt { struct Storage_dialog; }
|
||||
|
||||
|
||||
struct Sculpt::Storage_dialog : Dialog
|
||||
{
|
||||
Env &_env;
|
||||
|
||||
Dialog::Generator &_dialog_generator;
|
||||
|
||||
Storage_devices const &_storage_devices;
|
||||
|
||||
Ram_fs_state const &_ram_fs_state;
|
||||
|
||||
Selectable_item _device_item { };
|
||||
Selectable_item _partition_item { };
|
||||
Hoverable_item _use_item { };
|
||||
Hoverable_item _relabel_item { };
|
||||
Hoverable_item _inspect_item { };
|
||||
Selectable_item _operation_item { };
|
||||
Activatable_item _confirm_item { };
|
||||
|
||||
void generate(Xml_generator &) const;
|
||||
|
||||
void _gen_block_device(Xml_generator &, Block_device const &) const;
|
||||
|
||||
void _gen_partition(Xml_generator &, Storage_device const &, Partition const &) const;
|
||||
|
||||
void _gen_partition_operations(Xml_generator &, Storage_device const &, Partition const &) const;
|
||||
|
||||
void _gen_usb_storage_device(Xml_generator &, Usb_storage_device const &) const;
|
||||
|
||||
void _gen_ram_fs(Xml_generator &) const;
|
||||
|
||||
void hover(Xml_node hover);
|
||||
|
||||
Storage_target const &_used_target;
|
||||
|
||||
struct Action : Interface
|
||||
{
|
||||
virtual void format(Storage_target const &) = 0;
|
||||
|
||||
virtual void cancel_format(Storage_target const &) = 0;
|
||||
|
||||
virtual void expand(Storage_target const &) = 0;
|
||||
|
||||
virtual void cancel_expand(Storage_target const &) = 0;
|
||||
|
||||
virtual void check(Storage_target const &) = 0;
|
||||
|
||||
virtual void toggle_file_browser(Storage_target const &) = 0;
|
||||
|
||||
virtual void toggle_default_storage_target(Storage_target const &) = 0;
|
||||
|
||||
virtual void use(Storage_target const &) = 0;
|
||||
|
||||
virtual void reset_ram_fs() = 0;
|
||||
};
|
||||
|
||||
Storage_target _selected_storage_target() const
|
||||
{
|
||||
Partition::Number partition = (_partition_item._selected == "")
|
||||
? Partition::Number { }
|
||||
: Partition::Number(_partition_item._selected);
|
||||
|
||||
return Storage_target { _device_item._selected, partition };
|
||||
}
|
||||
|
||||
void reset_operation()
|
||||
{
|
||||
_operation_item.reset();
|
||||
_confirm_item.reset();
|
||||
|
||||
_dialog_generator.generate_dialog();
|
||||
}
|
||||
|
||||
void click(Action &action);
|
||||
|
||||
void clack(Action &action);
|
||||
|
||||
Storage_dialog(Env &env, Dialog::Generator &dialog_generator,
|
||||
Storage_devices const &storage_devices,
|
||||
Ram_fs_state const &ram_fs_state, Storage_target const &used)
|
||||
:
|
||||
_env(env), _dialog_generator(dialog_generator),
|
||||
_storage_devices(storage_devices), _ram_fs_state(ram_fs_state),
|
||||
_used_target(used)
|
||||
{ }
|
||||
};
|
||||
|
||||
#endif /* _STORAGE_DIALOG_H_ */
|
136
repos/gems/src/app/sculpt_manager/xml.h
Normal file
136
repos/gems/src/app/sculpt_manager/xml.h
Normal file
@ -0,0 +1,136 @@
|
||||
/*
|
||||
* \brief Utilities for generating XML
|
||||
* \author Norman Feske
|
||||
* \date 2018-01-11
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2017 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU Affero General Public License version 3.
|
||||
*/
|
||||
|
||||
#ifndef _XML_H_
|
||||
#define _XML_H_
|
||||
|
||||
/* Genode includes */
|
||||
#include <util/xml_generator.h>
|
||||
#include <base/log.h>
|
||||
|
||||
/* local includes */
|
||||
#include "types.h"
|
||||
|
||||
namespace Sculpt {
|
||||
|
||||
template <typename FN>
|
||||
static inline void gen_named_node(Xml_generator &xml,
|
||||
char const *type, char const *name, FN const &fn)
|
||||
{
|
||||
xml.node(type, [&] () {
|
||||
xml.attribute("name", name);
|
||||
fn();
|
||||
});
|
||||
}
|
||||
|
||||
static inline void gen_named_node(Xml_generator &xml, char const *type, char const *name)
|
||||
{
|
||||
xml.node(type, [&] () { xml.attribute("name", name); });
|
||||
}
|
||||
|
||||
template <size_t N, typename FN>
|
||||
static inline void gen_named_node(Xml_generator &xml,
|
||||
char const *type, String<N> const &name, FN const &fn)
|
||||
{
|
||||
gen_named_node(xml, type, name.string(), fn);
|
||||
}
|
||||
|
||||
template <size_t N>
|
||||
static inline void gen_named_node(Xml_generator &xml, char const *type, String<N> const &name)
|
||||
{
|
||||
gen_named_node(xml, type, name.string());
|
||||
}
|
||||
|
||||
template <typename SESSION, typename FN>
|
||||
static inline void gen_service_node(Xml_generator &xml, FN const &fn)
|
||||
{
|
||||
gen_named_node(xml, "service", SESSION::service_name(), fn);
|
||||
}
|
||||
|
||||
template <typename SESSION>
|
||||
static inline void gen_parent_service(Xml_generator &xml)
|
||||
{
|
||||
gen_named_node(xml, "service", SESSION::service_name());
|
||||
};
|
||||
|
||||
template <typename SESSION>
|
||||
static inline void gen_parent_route(Xml_generator &xml)
|
||||
{
|
||||
gen_named_node(xml, "service", SESSION::service_name(), [&] () {
|
||||
xml.node("parent", [&] () { }); });
|
||||
}
|
||||
|
||||
static inline void gen_parent_rom_route(Xml_generator &xml,
|
||||
Rom_name const &name,
|
||||
Label const &label)
|
||||
{
|
||||
gen_service_node<Rom_session>(xml, [&] () {
|
||||
xml.attribute("label_last", name);
|
||||
xml.node("parent", [&] () {
|
||||
xml.attribute("label", label); });
|
||||
});
|
||||
}
|
||||
|
||||
static inline void gen_parent_rom_route(Xml_generator &xml,
|
||||
Rom_name const &name)
|
||||
{
|
||||
gen_parent_rom_route(xml, name, name);
|
||||
}
|
||||
|
||||
template <typename SESSION>
|
||||
static inline void gen_provides(Xml_generator &xml)
|
||||
{
|
||||
xml.node("provides", [&] () {
|
||||
gen_named_node(xml, "service", SESSION::service_name()); });
|
||||
}
|
||||
|
||||
static inline void gen_common_start_content(Xml_generator &xml,
|
||||
Rom_name const &name,
|
||||
Cap_quota const caps,
|
||||
Ram_quota const ram)
|
||||
{
|
||||
xml.attribute("name", name);
|
||||
xml.attribute("caps", caps.value);
|
||||
gen_named_node(xml, "resource", "RAM", [&] () {
|
||||
xml.attribute("quantum", String<64>(Number_of_bytes(ram.value))); });
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
static T _attribute_value(Xml_node node, char const *attr_name)
|
||||
{
|
||||
return node.attribute_value(attr_name, T{});
|
||||
}
|
||||
|
||||
template <typename T, typename... ARGS>
|
||||
static T _attribute_value(Xml_node node, char const *sub_node_type, ARGS... args)
|
||||
{
|
||||
if (!node.has_sub_node(sub_node_type))
|
||||
return T{};
|
||||
|
||||
return _attribute_value<T>(node.sub_node(sub_node_type), args...);
|
||||
}
|
||||
|
||||
/**
|
||||
* Query attribute value from XML sub nodd
|
||||
*
|
||||
* The list of arguments except for the last one refer to XML path into the
|
||||
* XML structure. The last argument denotes the queried attribute name.
|
||||
*/
|
||||
template <typename T, typename... ARGS>
|
||||
static T query_attribute(Xml_node node, ARGS &&... args)
|
||||
{
|
||||
return _attribute_value<T>(node, args...);
|
||||
}
|
||||
}
|
||||
|
||||
#endif /* _XML_H_ */
|
Loading…
x
Reference in New Issue
Block a user