mirror of
https://github.com/genodelabs/genode.git
synced 2025-04-11 21:32:57 +00:00
parent
19b3824bfb
commit
93b82c14ac
@ -3,6 +3,11 @@ LIBC_GEN_DIR = $(LIBC_DIR)/lib/libc/gen
|
||||
# this file produces a warning about a missing header file, lets drop it
|
||||
FILTER_OUT_C += getosreldate.c sem.c valloc.c getpwent.c
|
||||
|
||||
# the following are superceded by our minimalist sysctl and sysconf
|
||||
FILTER_OUT_C += \
|
||||
devname.c feature_present.c getpagesizes.c getvfsbyname.c \
|
||||
setproctitle.c sysconf.c sysctlbyname.c
|
||||
|
||||
SRC_C = $(filter-out $(FILTER_OUT_C),$(notdir $(wildcard $(LIBC_GEN_DIR)/*.c)))
|
||||
|
||||
# 'sysconf.c' includes the local 'stdtime/tzfile.h'
|
||||
|
@ -17,6 +17,8 @@ SRC_CC = atexit.cc dummies.cc rlimit.cc sysctl.cc \
|
||||
libc_pdbg.cc vfs_plugin.cc rtc.cc dynamic_linker.cc signal.cc \
|
||||
socket_operations.cc task.cc
|
||||
|
||||
CC_OPT_sysctl += -Wno-write-strings
|
||||
|
||||
INC_DIR += $(REP_DIR)/src/lib/libc
|
||||
INC_DIR += $(REP_DIR)/src/lib/libc/include
|
||||
|
||||
@ -31,6 +33,11 @@ SRC_C += strcoll.c strxfrm.c wcscoll.c wcsxfrm.c
|
||||
|
||||
include $(REP_DIR)/lib/mk/libc-common.inc
|
||||
|
||||
#
|
||||
# Version information for sysctl
|
||||
#
|
||||
include $(REP_DIR)/src/lib/libc/version.inc
|
||||
|
||||
vpath % $(REP_DIR)/src/lib/libc
|
||||
vpath % $(LIBC_DIR)/lib/libc/string
|
||||
|
||||
|
@ -94,5 +94,4 @@ File_descriptor *File_descriptor_allocator::find_by_libc_fd(int libc_fd)
|
||||
** Libc functions **
|
||||
********************/
|
||||
|
||||
extern "C" int __attribute__((weak)) getdtablesize(void) {
|
||||
PDBG("libc"); return MAX_NUM_FDS; }
|
||||
extern "C" int __attribute__((weak)) getdtablesize(void) { return MAX_NUM_FDS; }
|
||||
|
31
repos/libports/src/lib/libc/libc_errno.h
Normal file
31
repos/libports/src/lib/libc/libc_errno.h
Normal file
@ -0,0 +1,31 @@
|
||||
/*
|
||||
* \brief C++ wrapper over errno
|
||||
* \author Christian Helmuth
|
||||
* \date 2016-04-26
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2016 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU General Public License version 2.
|
||||
*/
|
||||
|
||||
#ifndef _LIBC_ERRNO_H_
|
||||
#define _LIBC_ERRNO_H_
|
||||
|
||||
/* libc includes */
|
||||
#include <errno.h>
|
||||
|
||||
namespace Libc { struct Errno; }
|
||||
|
||||
struct Libc::Errno
|
||||
{
|
||||
int const error;
|
||||
|
||||
explicit Errno(int error) : error(error) { errno = error; }
|
||||
|
||||
operator int() const { return -1; }
|
||||
};
|
||||
|
||||
#endif /* _LIBC_ERRNO_H_ */
|
@ -1,73 +1,266 @@
|
||||
/*
|
||||
* \brief C-library back end
|
||||
* \author Norman Feske
|
||||
* \date 2008-11-11
|
||||
* \brief Sysctl facade
|
||||
* \author Emery Hemingway
|
||||
* \date 2016-04-27
|
||||
*/
|
||||
|
||||
/*
|
||||
* Copyright (C) 2008-2013 Genode Labs GmbH
|
||||
* Copyright (C) 2016 Genode Labs GmbH
|
||||
*
|
||||
* This file is part of the Genode OS framework, which is distributed
|
||||
* under the terms of the GNU General Public License version 2.
|
||||
*/
|
||||
|
||||
#include <base/printf.h>
|
||||
/* Genode includes */
|
||||
#include <util/string.h>
|
||||
#include <base/env.h>
|
||||
|
||||
#include <sys/types.h>
|
||||
/* Genode-specific libc interfaces */
|
||||
#include <libc-plugin/plugin.h>
|
||||
#include <libc-plugin/fd_alloc.h>
|
||||
|
||||
/* Libc includes */
|
||||
#include <sys/sysctl.h>
|
||||
#include <errno.h>
|
||||
#include <fcntl.h>
|
||||
#include <stdlib.h>
|
||||
#include <unistd.h>
|
||||
|
||||
#include "libc_errno.h"
|
||||
|
||||
|
||||
enum { PAGESIZE = 4096 };
|
||||
|
||||
|
||||
extern "C" long sysconf(int name)
|
||||
{
|
||||
switch (name) {
|
||||
case _SC_CHILD_MAX: return CHILD_MAX;
|
||||
case _SC_OPEN_MAX: return getdtablesize();
|
||||
case _SC_NPROCESSORS_CONF: return 1;
|
||||
case _SC_NPROCESSORS_ONLN: return 1;
|
||||
case _SC_PAGESIZE: return PAGESIZE;
|
||||
|
||||
case _SC_PHYS_PAGES:
|
||||
return Genode::env()->ram_session()->quota() / PAGESIZE;
|
||||
default:
|
||||
PWRN("%s(%d) not implemented", __func__, name);
|
||||
return Libc::Errno(EINVAL);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* non-standard FreeBSD function not supported */
|
||||
extern "C" int sysctlbyname(char const *name, void *oldp, size_t *oldlenp,
|
||||
void *newp, size_t newlen)
|
||||
{
|
||||
PWRN("%s(%s,...) not implemented", __func__, name);
|
||||
return Libc::Errno(ENOENT);
|
||||
}
|
||||
|
||||
#include "libc_debug.h"
|
||||
|
||||
extern "C" int __sysctl(int *name, u_int namelen, void *oldp, size_t *oldlenp,
|
||||
void *newp, size_t newlen)
|
||||
{
|
||||
int i;
|
||||
raw_write_str("__sysctl called\n");
|
||||
static const ctlname ctl_names[] = CTL_NAMES;
|
||||
static const ctlname ctl_kern_names[] = CTL_KERN_NAMES;
|
||||
static const ctlname ctl_hw_names[] = CTL_HW_NAMES;
|
||||
static const ctlname ctl_user_names[] = CTL_USER_NAMES;
|
||||
static const ctlname ctl_p1003_1b_names[] = CTL_P1003_1B_NAMES;
|
||||
|
||||
/*
|
||||
* During printf, __sysctl is called by malloc with the parameters
|
||||
*
|
||||
* name[0] == 6 (CTL_HW)
|
||||
* name[1] == 3 (HW_NCPU)
|
||||
*
|
||||
* In this case, we can return -1, and the libC assumes that we
|
||||
* have one CPU.
|
||||
*/
|
||||
if ((name[0] == CTL_HW) && (name[1] == HW_NCPU))
|
||||
return -1;
|
||||
/* read only */
|
||||
if (!oldp) /* check for write attempt */
|
||||
return Libc::Errno(newp ? EPERM : EINVAL);
|
||||
|
||||
/*
|
||||
* CTL_P1003_1B is used by sysconf(_SC_PAGESIZE) to determine
|
||||
* the actual page size.
|
||||
*/
|
||||
if (((name[0] == CTL_HW) && (name[1] == HW_PAGESIZE)) ||
|
||||
((name[0] == CTL_P1003_1B) && (name[1] == CTL_P1003_1B_PAGESIZE))) {
|
||||
int result = 4096;
|
||||
if (oldp) {
|
||||
if (*oldlenp >= sizeof(result)) {
|
||||
*(int*)oldp = result;
|
||||
*oldlenp = sizeof(result);
|
||||
ctlname const *ctl = nullptr;
|
||||
char *buf = (char*)oldp;
|
||||
int index_a = name[0];
|
||||
int index_b = name[1];
|
||||
|
||||
if (namelen != 2) return Libc::Errno(ENOENT);
|
||||
if (index_a >= CTL_MAXID) return Libc::Errno(EINVAL);
|
||||
|
||||
switch(index_a) {
|
||||
case CTL_KERN:
|
||||
if (index_b >= KERN_MAXID) return Libc::Errno(EINVAL);
|
||||
ctl = &ctl_kern_names[index_b]; break;
|
||||
|
||||
case CTL_HW:
|
||||
if (index_b >= HW_MAXID) return Libc::Errno(EINVAL);
|
||||
ctl = &ctl_hw_names[index_b]; break;
|
||||
|
||||
case CTL_USER:
|
||||
if (index_b >= USER_MAXID) return Libc::Errno(EINVAL);
|
||||
ctl = &ctl_user_names[index_b]; break;
|
||||
|
||||
case CTL_P1003_1B:
|
||||
if (index_b >= CTL_P1003_1B_MAXID) return Libc::Errno(EINVAL);
|
||||
ctl = &ctl_p1003_1b_names[index_b]; break;
|
||||
}
|
||||
|
||||
if (!ctl) return Libc::Errno(EINVAL);
|
||||
|
||||
if (((ctl->ctl_type == CTLTYPE_INT) && (*oldlenp < sizeof(int))) ||
|
||||
((ctl->ctl_type == CTLTYPE_STRING) && (*oldlenp < 1)) ||
|
||||
((ctl->ctl_type == CTLTYPE_QUAD) && (*oldlenp < sizeof(Genode::uint64_t))) ||
|
||||
((ctl->ctl_type == CTLTYPE_UINT) && (*oldlenp < sizeof(unsigned int))) ||
|
||||
((ctl->ctl_type == CTLTYPE_LONG) && (*oldlenp < sizeof(long))) ||
|
||||
((ctl->ctl_type == CTLTYPE_ULONG) && (*oldlenp < sizeof(unsigned long))))
|
||||
{
|
||||
return Libc::Errno(EINVAL);
|
||||
}
|
||||
|
||||
/* builtins */
|
||||
{
|
||||
switch(index_a) {
|
||||
case CTL_HW: switch(index_b) {
|
||||
|
||||
case HW_PHYSMEM:
|
||||
case HW_USERMEM:
|
||||
*(unsigned long*)oldp = Genode::env()->ram_session()->quota();
|
||||
*oldlenp = sizeof(unsigned long);
|
||||
return 0;
|
||||
} else {
|
||||
PERR("not enough room to store the old value");
|
||||
return -1;
|
||||
}
|
||||
} else {
|
||||
PERR("cannot store the result in oldp, since it is NULL");
|
||||
return -1;
|
||||
|
||||
case HW_PAGESIZE:
|
||||
*(int*)oldp = (int)PAGESIZE;
|
||||
*oldlenp = sizeof(int);
|
||||
return 0;
|
||||
|
||||
} break;
|
||||
|
||||
case CTL_P1003_1B: switch(index_b) {
|
||||
|
||||
case CTL_P1003_1B_PAGESIZE:
|
||||
*(int*)oldp = PAGESIZE;
|
||||
*oldlenp = sizeof(int);
|
||||
return 0;
|
||||
|
||||
} break;
|
||||
}
|
||||
}
|
||||
|
||||
raw_write_str(newp ? "newp provided\n" : "no newp provided\n");
|
||||
|
||||
for (i = 0; i < name[0]; i++)
|
||||
raw_write_str("*");
|
||||
raw_write_str("\n");
|
||||
for (i = 0; i < name[1]; i++)
|
||||
raw_write_str("%");
|
||||
raw_write_str("\n");
|
||||
/* runtime overrides */
|
||||
{
|
||||
Libc::Absolute_path sysctl_path(ctl_names[index_a].ctl_name, "/.sysctl/");
|
||||
sysctl_path.append("/");
|
||||
sysctl_path.append(ctl->ctl_name);
|
||||
|
||||
return 0;
|
||||
/*
|
||||
* read from /.sysctl/...
|
||||
*
|
||||
* The abstracted libc interface is used to read files here
|
||||
* rather than to explicity resolve a file system plugin.
|
||||
*/
|
||||
int fd = open(sysctl_path.base(), 0);
|
||||
if (fd != -1) {
|
||||
auto n = read(fd, buf, *oldlenp);
|
||||
close(fd);
|
||||
|
||||
if (n > 0) switch (ctl->ctl_type) {
|
||||
case CTLTYPE_INT: {
|
||||
long value = 0;
|
||||
Genode::ascii_to((char*)oldp, value);
|
||||
*(int*)oldp = int(value);
|
||||
*oldlenp = sizeof(int);
|
||||
return 0;
|
||||
}
|
||||
|
||||
case CTLTYPE_STRING:
|
||||
*oldlenp = n;
|
||||
return 0;
|
||||
|
||||
case CTLTYPE_QUAD: {
|
||||
Genode::uint64_t value = 0;
|
||||
Genode::ascii_to((char*)oldp, value);
|
||||
*(Genode::uint64_t*)oldp = value;
|
||||
*oldlenp = sizeof(Genode::uint64_t);
|
||||
return 0;
|
||||
}
|
||||
|
||||
case CTLTYPE_UINT: {
|
||||
unsigned value = 0;
|
||||
Genode::ascii_to((char*)oldp, value);
|
||||
*(unsigned*)oldp = value;
|
||||
*oldlenp = sizeof(unsigned);
|
||||
return 0;
|
||||
}
|
||||
|
||||
case CTLTYPE_LONG: {
|
||||
long value = 0;
|
||||
Genode::ascii_to((char*)oldp, value);
|
||||
*(long*)oldp = value;
|
||||
*oldlenp = sizeof(long);
|
||||
return 0;
|
||||
}
|
||||
|
||||
case CTLTYPE_ULONG: {
|
||||
unsigned long value = 0;
|
||||
Genode::ascii_to((char*)oldp, value);
|
||||
*(unsigned long*)oldp = value;
|
||||
*oldlenp = sizeof(unsigned long);
|
||||
return 0;
|
||||
}
|
||||
|
||||
default:
|
||||
PWRN("unhandled sysctl data type for %s", sysctl_path.base());
|
||||
return Libc::Errno(EINVAL);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* fallback values */
|
||||
{
|
||||
switch(index_a) {
|
||||
|
||||
case CTL_KERN:
|
||||
switch(index_b) {
|
||||
case KERN_OSTYPE:
|
||||
Genode::strncpy(buf, "Genode", *oldlenp);
|
||||
*oldlenp = Genode::strlen(buf);
|
||||
return 0;
|
||||
|
||||
case KERN_OSRELEASE:
|
||||
Genode::strncpy(buf, GENODE_OSRELEASE, *oldlenp);
|
||||
*oldlenp = Genode::strlen(buf);
|
||||
return 0;
|
||||
|
||||
case KERN_OSREV:
|
||||
*(int*)oldp = int(GENODE_OSREV);
|
||||
*oldlenp = sizeof(int);
|
||||
return 0;
|
||||
|
||||
case KERN_VERSION:
|
||||
Genode::strncpy(buf, GENODE_VERSION, *oldlenp);
|
||||
*oldlenp = Genode::strlen(buf);
|
||||
return 0;
|
||||
|
||||
case KERN_HOSTNAME:
|
||||
Genode::strncpy(buf, "localhost", *oldlenp);
|
||||
*oldlenp = Genode::strlen(buf);
|
||||
return 0;
|
||||
|
||||
} break;
|
||||
|
||||
case CTL_HW: switch(index_b) {
|
||||
|
||||
case HW_MACHINE:
|
||||
Genode::strncpy(buf, GENODE_MACHINE, *oldlenp);
|
||||
*oldlenp = Genode::strlen(buf);
|
||||
return 0;
|
||||
|
||||
case HW_NCPU:
|
||||
*(int*)oldp = 1;
|
||||
*oldlenp = sizeof(int);
|
||||
return 0;
|
||||
|
||||
} break;
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
PWRN("sysctl: no builtin or override value found for %s.%s",
|
||||
ctl_names[index_a].ctl_name, ctl->ctl_name);
|
||||
return Libc::Errno(ENOENT);
|
||||
}
|
||||
|
||||
|
41
repos/libports/src/lib/libc/version.inc
Normal file
41
repos/libports/src/lib/libc/version.inc
Normal file
@ -0,0 +1,41 @@
|
||||
#
|
||||
# Provide version information to sysctl
|
||||
#
|
||||
GENODE_ROOT_DIR = $(REP_DIR)/../..
|
||||
|
||||
GENODE_OSRELEASE := $(shell cat $(GENODE_ROOT_DIR)/VERSION)
|
||||
|
||||
GENODE_OSREV := $(shell which git > /dev/null && git rev-list --count HEAD)
|
||||
|
||||
GENODE_VERSION := $(shell \
|
||||
which git > /dev/null \
|
||||
&& git -C $(GENODE_ROOT_DIR) describe 2> /dev/null \
|
||||
&& exit 0 \
|
||||
|| \
|
||||
test -r $(GENODE_ROOT_DIR)/VERSION \
|
||||
&& cat $(GENODE_ROOT_DIR)/VERSION \
|
||||
&& exit 0 \
|
||||
|| \
|
||||
echo "<unknown version>")
|
||||
|
||||
CC_OPT += -DGENODE_OSRELEASE="\"$(GENODE_OSRELEASE)\""
|
||||
CC_OPT += -DGENODE_OSREV="$(GENODE_OSREV)"
|
||||
CC_OPT += -DGENODE_VERSION="\"$(GENODE_VERSION)\""
|
||||
|
||||
ifeq ($(findstring arm, $(SPECS)), arm)
|
||||
CC_OPT += -DGENODE_MACHINE="\"arm\""
|
||||
else
|
||||
ifeq ($(findstring riscv, $(SPECS)), riscv)
|
||||
CC_OPT += -DGENODE_MACHINE="\"riscv\""
|
||||
else
|
||||
ifeq ($(findstring x86_32, $(SPECS)), x86_32)
|
||||
CC_OPT += -DGENODE_MACHINE="\"i686\""
|
||||
else
|
||||
ifeq ($(findstring x86_64, $(SPECS)), x86_64)
|
||||
CC_OPT += -DGENODE_MACHINE="\"x86_64\""
|
||||
else
|
||||
CC_OPT += -DGENODE_MACHINE="\"unknown\""
|
||||
endif
|
||||
endif
|
||||
endif
|
||||
endif
|
76
repos/ports/run/noux_uname.run
Normal file
76
repos/ports/run/noux_uname.run
Normal file
@ -0,0 +1,76 @@
|
||||
build { core init drivers/timer noux/minimal
|
||||
lib/libc_noux noux-pkg/coreutils }
|
||||
|
||||
# strip coreutils binaries and create tar archive
|
||||
exec sh -c "[cross_dev_prefix]strip bin/coreutils/bin/*"
|
||||
exec tar cfv bin/coreutils.tar -h -C bin/coreutils .
|
||||
|
||||
create_boot_directory
|
||||
|
||||
install_config {
|
||||
<config verbose="yes">
|
||||
<parent-provides>
|
||||
<service name="ROM"/>
|
||||
<service name="LOG"/>
|
||||
<service name="CAP"/>
|
||||
<service name="RAM"/>
|
||||
<service name="RM"/>
|
||||
<service name="CPU"/>
|
||||
<service name="PD"/>
|
||||
<service name="IRQ"/>
|
||||
<service name="IO_MEM"/>
|
||||
<service name="IO_PORT"/>
|
||||
<service name="SIGNAL"/>
|
||||
</parent-provides>
|
||||
<default-route>
|
||||
<any-service> <any-child/> <parent/> </any-service>
|
||||
</default-route>
|
||||
<start name="timer">
|
||||
<resource name="RAM" quantum="1M"/>
|
||||
<provides><service name="Timer"/></provides>
|
||||
</start>
|
||||
<start name="spoof">
|
||||
<binary name="noux"/>
|
||||
<resource name="RAM" quantum="16M"/>
|
||||
<config verbose="yes" stdin="/null" stdout="/log" stderr="/log">
|
||||
<fstab>
|
||||
<null/> <log/>
|
||||
<dir name=".sysctl">
|
||||
<dir name="kern">
|
||||
<inline name="ostype">Muck OS XIII</inline>
|
||||
<inline name="hostname">localhost</inline>
|
||||
</dir>
|
||||
<dir name="hw">
|
||||
<inline name="machine">norisc</inline>
|
||||
</dir>
|
||||
</dir>
|
||||
<tar name="coreutils.tar" />
|
||||
</fstab>
|
||||
<start name="/bin/uname"> <arg value="-a"/> </start>
|
||||
</config>
|
||||
</start>
|
||||
<start name="noux">
|
||||
<resource name="RAM" quantum="16M"/>
|
||||
<config verbose="yes" stdin="/null" stdout="/log" stderr="/log">
|
||||
<fstab> <null/> <log/> <tar name="coreutils.tar" /> </fstab>
|
||||
<start name="/bin/uname"> <arg value="-a"/> </start>
|
||||
</config>
|
||||
</start>
|
||||
</config>
|
||||
}
|
||||
|
||||
build_boot_image {
|
||||
core init timer ld.lib.so noux libc.lib.so libm.lib.so
|
||||
libc_noux.lib.so coreutils.tar
|
||||
}
|
||||
|
||||
append qemu_args " -nographic -serial mon:stdio "
|
||||
|
||||
if {[have_spec x86_64]} {
|
||||
# coreutils.tar is really huge when built for x86_64
|
||||
append qemu_args " -m 300 "
|
||||
}
|
||||
|
||||
run_genode_until {child "noux" exited with exit value 0.*\n} 30
|
||||
|
||||
exec rm bin/coreutils.tar
|
Loading…
x
Reference in New Issue
Block a user