diff --git a/repos/dde_rump/include/rump/env.h b/repos/dde_rump/include/rump/env.h index e6fb485404..31d8b8ac6d 100644 --- a/repos/dde_rump/include/rump/env.h +++ b/repos/dde_rump/include/rump/env.h @@ -44,4 +44,11 @@ class Rump::Env Genode::Attached_rom_dataspace &config_rom() { return _config; } }; +/** + * Set rump MEMLIMIT + * + * In case limit is zero, the available RAM quota will be used. + */ +void rump_set_memlimit(Genode::size_t limit); + #endif /* _INCLUDE__RUMP__ENV_H_ */ diff --git a/repos/dde_rump/run/fs_rom_update_ext2.run b/repos/dde_rump/run/fs_rom_update_ext2.run index d0d60d0adf..ff5647aedd 100644 --- a/repos/dde_rump/run/fs_rom_update_ext2.run +++ b/repos/dde_rump/run/fs_rom_update_ext2.run @@ -55,7 +55,7 @@ append config { - + diff --git a/repos/dde_rump/run/libc_vfs_ext2.run b/repos/dde_rump/run/libc_vfs_ext2.run index b520c3f56c..7812dc7dc7 100644 --- a/repos/dde_rump/run/libc_vfs_ext2.run +++ b/repos/dde_rump/run/libc_vfs_ext2.run @@ -3,7 +3,7 @@ set mkfs_opts "-F" set test_build_components "lib/vfs/rump" -set test_vfs_config "" +set test_vfs_config "" set test_boot_modules { rump_fs.lib.so diff --git a/repos/dde_rump/run/libc_vfs_fs_ext2.run b/repos/dde_rump/run/libc_vfs_fs_ext2.run index 0569bb1c6c..0e549eac5e 100644 --- a/repos/dde_rump/run/libc_vfs_fs_ext2.run +++ b/repos/dde_rump/run/libc_vfs_fs_ext2.run @@ -3,7 +3,7 @@ set mkfs_opts "-F" set test_build_components "lib/vfs/rump" -set test_vfs_config "" +set test_vfs_config "" set test_boot_modules { rump_fs.lib.so diff --git a/repos/dde_rump/run/rump_ext2.run b/repos/dde_rump/run/rump_ext2.run index 510890e5e1..1a98deb31e 100644 --- a/repos/dde_rump/run/rump_ext2.run +++ b/repos/dde_rump/run/rump_ext2.run @@ -58,7 +58,7 @@ append config { - + diff --git a/repos/dde_rump/run/vfs_stress_ext2.run b/repos/dde_rump/run/vfs_stress_ext2.run index c5ac9be1ee..4910f06645 100644 --- a/repos/dde_rump/run/vfs_stress_ext2.run +++ b/repos/dde_rump/run/vfs_stress_ext2.run @@ -47,7 +47,7 @@ install_config { - + diff --git a/repos/dde_rump/src/lib/rump/hypercall.cc b/repos/dde_rump/src/lib/rump/hypercall.cc index b8e8e38c42..d09e70d629 100644 --- a/repos/dde_rump/src/lib/rump/hypercall.cc +++ b/repos/dde_rump/src/lib/rump/hypercall.cc @@ -144,12 +144,23 @@ int rumpuser_init(int version, const struct rumpuser_hyperup *hyp) ** Parameter retrieval ** *************************/ +static size_t _rump_memlimit = 0; + + +void rump_set_memlimit(Genode::size_t limit) +{ + _rump_memlimit = limit; +} + + int rumpuser_getparam(const char *name, void *buf, size_t buflen) { - enum { RESERVE_MEM = 2U * 1024 * 1024 }; + enum { + MIN_RESERVE_MEM = 1U << 20, + MIN_RUMP_MEM = 6U << 20, + }; /* support one cpu */ - Genode::log(name); if (!Genode::strcmp(name, "_RUMPUSER_NCPU")) { Genode::strncpy((char *)buf, "1", 2); return 0; @@ -163,16 +174,39 @@ int rumpuser_getparam(const char *name, void *buf, size_t buflen) if (!Genode::strcmp(name, "RUMP_MEMLIMIT")) { - /* leave 2 MB for the Genode */ - size_t rump_ram = Rump::env().env().ram().avail_ram().value; - - if (rump_ram <= RESERVE_MEM) { - Genode::error("insufficient quota left: ", - rump_ram, " < ", (long)RESERVE_MEM, " bytes"); - return -1; + if (!_rump_memlimit) { + Genode::error("no RAM limit set"); + throw -1; + } + + /* + * Set RAM limit and reserve a 10th or at least 1MiB for + * Genode meta-data. + */ + Genode::size_t rump_ram = _rump_memlimit; + size_t const reserve = Genode::max((size_t)MIN_RESERVE_MEM, rump_ram / 10); + + if (reserve < MIN_RESERVE_MEM) { + Genode::error("could not reserve enough RAM for meta-data, need at least ", + (size_t)MIN_RESERVE_MEM >> 20, " MiB"); + throw -1; + } + + rump_ram -= reserve; + + /* check RAM limit is enough... */ + if (rump_ram < MIN_RUMP_MEM) { + Genode::error("RAM limit too small, need at least ", + (size_t)MIN_RUMP_MEM >> 20, " MiB"); + throw -1; + } + + /* ... and is in valid range (overflow) */ + if (rump_ram >= _rump_memlimit) { + Genode::error("rump RAM limit invalid"); + throw -1; } - rump_ram -= RESERVE_MEM; rump_ram = Genode::min((unsigned long)MAX_VIRTUAL_MEMORY, rump_ram); /* convert to string */ diff --git a/repos/dde_rump/src/lib/vfs/rump/README b/repos/dde_rump/src/lib/vfs/rump/README index c8490ca1bb..1413fed502 100644 --- a/repos/dde_rump/src/lib/vfs/rump/README +++ b/repos/dde_rump/src/lib/vfs/rump/README @@ -1,5 +1,7 @@ The vfs_rump plugin enables access to block device backed file systems supported by the rump kernel. A single rump kernel is in use for any -number of nodes. The configuration node takes two arguments: -'fs' specifies the file system type, and 'writeable' specifies if the -mount is read only or writeable, 'writeable' defaults to true. \ No newline at end of file +number of nodes. The configuration node needs two mandatory arguments: + +The 'fs' attribute specifies the file system type, and 'ram' limits the memory +the plugin will use internally. The optional attribute 'writeable' specifies if +the mount is read only or writeable; 'writeable' defaults to true. diff --git a/repos/dde_rump/src/lib/vfs/rump/vfs_rump.cc b/repos/dde_rump/src/lib/vfs/rump/vfs_rump.cc index b8d571e5b6..4d7e182988 100644 --- a/repos/dde_rump/src/lib/vfs/rump/vfs_rump.cc +++ b/repos/dde_rump/src/lib/vfs/rump/vfs_rump.cc @@ -795,7 +795,8 @@ class Rump_factory : public Vfs::File_system_factory public: - Rump_factory(Genode::Env &env, Genode::Allocator &alloc) + Rump_factory(Genode::Env &env, Genode::Allocator &alloc, + Genode::Xml_node config) : _timer(env, "rump-sync"), _sync_handler(env.ep(), *this, &Rump_factory::_sync) { @@ -803,8 +804,20 @@ class Rump_factory : public Vfs::File_system_factory rump_io_backend_init(); + /* limit RAM consumption */ + try { + Genode::Number_of_bytes memlimit; + config.attribute("ram").value(&memlimit); + + rump_set_memlimit(memlimit); + } catch (...) { + Genode::error("mandatory 'ram' attribute missing"); + throw Genode::Exception(); + } + /* start rump kernel */ - rump_init(); + try { rump_init(); } + catch (...) { throw Genode::Exception(); } /* register block device */ rump_pub_etfs_register( @@ -843,7 +856,7 @@ extern "C" Vfs::File_system_factory *vfs_file_system_factory(void) { Vfs::File_system *create(Vfs::Env &env, Genode::Xml_node node) override { - static Rump_factory factory(env.env(), env.alloc()); + static Rump_factory factory(env.env(), env.alloc(), node); return factory.create(env, node); } }; diff --git a/repos/dde_rump/src/server/rump_fs/file_system.cc b/repos/dde_rump/src/server/rump_fs/file_system.cc index f2183defed..ba09fd4ace 100644 --- a/repos/dde_rump/src/server/rump_fs/file_system.cc +++ b/repos/dde_rump/src/server/rump_fs/file_system.cc @@ -89,8 +89,12 @@ void File_system::init() Genode::log("Using ", fs_type, " as file system"); + size_t const avail = Rump::env().env().ram().avail_ram().value; + rump_set_memlimit(avail); + /* start rump kernel */ - rump_init(); + try { rump_init(); } + catch (...) { throw Genode::Exception(); } /* register block device */ rump_pub_etfs_register(GENODE_DEVICE, GENODE_BLOCK_SESSION, RUMP_ETFS_BLK); diff --git a/repos/ports/run/noux_fs.run b/repos/ports/run/noux_fs.run index eaad3d8cd3..4b8cf5bf04 100644 --- a/repos/ports/run/noux_fs.run +++ b/repos/ports/run/noux_fs.run @@ -72,7 +72,7 @@ append config { - +