[kernel] Expose a sysconf page to userspace

A structure, system_config, which is dynamically defined by the
definitions/sysconf.yaml config, is now mapped into every user address
space. The kernel fills this with information about itself and the
running machine.

User programs access this through the new j6_sysconf fake syscall in
libj6.

See: Github bug #242
See: [frobozz blog post](https://jsix.dev/posts/frobozz/)

Tags:
This commit is contained in:
Justin C. Miller
2022-01-13 22:08:35 -08:00
parent 939022bb5e
commit b3aaddadc8
11 changed files with 250 additions and 0 deletions

View File

@@ -0,0 +1,44 @@
#pragma once
// vim: ft=cpp
/// \file sysconf.h
/// Get kernel configuration
// The kernel depends on libj6 for some shared code,
// but should not include the user-specific code.
#ifndef __j6kernel
#include <stddef.h>
#include <stdint.h>
/*[[[cog code generation
from os.path import join
from sysconf import Sysconf
sc = Sysconf(join(definitions_path, "sysconf.yaml"))
]]]*/
///[[[end]]]
#ifdef __cplusplus
extern "C" {
#endif
enum j6_sysconf_arg
{
/*[[[cog code generation
for var in sc.vars:
cog.outl(f"j6sc_{var.name},")
]]]*/
///[[[end]]]
j6sc_MAX
};
/// Get the kernel configuration value specified by
/// the argument.
unsigned long j6_sysconf(j6_sysconf_arg arg);
#ifdef __cplusplus
} // extern C
#endif
#endif // __j6kernel

View File

@@ -6,10 +6,15 @@ j6 = module("j6",
sources = [
"init.cpp",
"include/j6/syscalls.h.cog",
"include/j6/sysconf.h.cog",
"syscalls.s.cog",
"sysconf.cpp.cog",
])
from glob import glob
from os.path import join
sysconf = join(source_root, "definitions/sysconf.yaml")
definitions = glob('definitions/**/*.def', recursive=True)
j6.add_depends([
@@ -17,3 +22,8 @@ j6.add_depends([
"syscalls.s.cog",
], definitions)
j6.add_depends([
"include/j6/sysconf.h.cog",
"sysconf.cpp.cog",
], [sysconf])

View File

@@ -0,0 +1,44 @@
// vim: ft=cpp
// The kernel depends on libj6 for some shared code,
// but should not include the user-specific code.
#ifndef __j6kernel
#include <j6/sysconf.h>
/*[[[cog code generation
from os.path import join
from sysconf import Sysconf
sc = Sysconf(join(definitions_path, "sysconf.yaml"))
cog.outl(f"constexpr uintptr_t __sysconf_address = {sc.address:#x};")
]]]*/
///[[[end]]]
struct __system_config
{
/*[[[cog code generation
for var in sc.vars:
cog.outl(f"{var.type:10} {var.section}_{var.name};")
]]]*/
///[[[end]]]
};
unsigned long
j6_sysconf(j6_sysconf_arg arg)
{
__system_config &sc =
* reinterpret_cast<__system_config*>(__sysconf_address);
switch (arg) {
/*[[[cog code generation
for var in sc.vars:
cog.outl(f"case j6sc_{var.name}: return sc.{var.section}_{var.name};")
]]]*/
///[[[end]]]
default: return 0;
}
}
#endif // __j6kernel