diff --git a/.bintray_descriptor.json b/.bintray_descriptor.json index d29ba7ff9..a066145d1 100644 --- a/.bintray_descriptor.json +++ b/.bintray_descriptor.json @@ -5,7 +5,7 @@ "subject": "rwth-os", "website_url": "http://www.hermitcore.org", "issue_tracker_url": "https://github.com/RWTH-OS/HermitCore/issues", - "vcs_url": "https://github.com/RWTH-OS/pthread-embedded.git", + "vcs_url": "https://github.com/RWTH-OS/HermitCore.git", "github_release_notes_file": "RELEASE", "licenses": ["Revised BSD"], "public_download_numbers": false, @@ -13,19 +13,23 @@ }, "version": { - "name": "0.1", + "name": "0.2", "desc": "HermitCore's kernel as libOS", "gpgSign": false }, "files": - [{ - "includePattern": "../(libhermit[^/]*deb$)", "uploadPattern": "$1", + [ + { + "includePattern": "build/(libhermit[^/]*deb$)", "uploadPattern": "$1", "matrixParams": { "deb_distribution": "vivid", "deb_component": "main", "deb_architecture": "amd64", - "override": 1} - }], + "override": 1} + }, + {"includePattern": "build/(libhermit[^/]*rpm$)", "uploadPattern": "$1", "override": 1}, + {"includePattern": "build/(libhermit[^/]*tar.bz2$)", "uploadPattern": "$1", "override": 1} + ], "publish": true } diff --git a/.gitignore b/.gitignore index a86372eea..68100574a 100644 --- a/.gitignore +++ b/.gitignore @@ -1,54 +1,15 @@ -config.log -config.status -autom4te.cache -/Makefile *.pcap *.config *.creator -*.creator.user +*.user *.files *.includes *.pyc *.callgrind *.xray *.o -*.a -*.dep -*~ -*.elf -*.elf32 -*.sym -*.bin +*.ko +**/build/* +.idea/* qemu-vlan0.pcap -autom4te.cache -documentation/html/ -include/hermit/config.inc -include/hermit/config.h -tools/proxy -usr/tests/hello -usr/tests/hello++ -usr/tests/hellof -usr/tests/jacobi -usr/tests/thr_hello -usr/tests/pi -usr/tests/RCCE_minimum -usr/tests/signals -usr/tests/server -usr/benchmarks/RCCE_pingping -usr/benchmarks/RCCE_pingpong -usr/benchmarks/stream -usr/benchmarks/hg -usr/benchmarks/netio -usr/benchmarks/basic -usr/openmpbench/schedbench -usr/openmpbench/syncbench -usr/openmpbench/taskbench -usr/tmp/ -usr/binutils/ -usr/gcc/ -usr/newlib/ -usr/pte/ -tools/Makefile -usr/ircce/Makefile -usr/xray/Makefile -arch/x86/kernel/boot.h +cmake/cmake-3.7.2-Linux-x86_64/* diff --git a/.travis.yml b/.travis.yml index 7f6157afc..116a34b6e 100644 --- a/.travis.yml +++ b/.travis.yml @@ -1,26 +1,27 @@ sudo: required dist: trusty git: - submodules: false + submodules: true language: c compiler: gcc before_install: - echo "deb https://dl.bintray.com/rwth-os/hermitcore vivid main" | sudo tee -a /etc/apt/sources.list - travis_retry sudo apt-get -qq update - - travis_retry sudo apt-get install -y curl qemu-system-x86 nasm texinfo libmpfr-dev libmpc-dev libgmp-dev libisl-dev flex bison packaging-dev - #- sudo apt-get install -y --force-yes binutils-hermit gcc-hermit-bootstrap + - travis_retry sudo apt-get install -y curl wget qemu-system-x86 nasm texinfo libmpfr-dev libmpc-dev libgmp-dev libisl-dev flex bison packaging-dev rpm - travis_retry sudo apt-get install -y --force-yes binutils-hermit libhermit newlib-hermit pthread-embedded-hermit gcc-hermit - git submodule update --init lwip usr/libomp script: - - cd .. - - mv HermitCore libhermit-0.1 - - tar -czf libhermit_0.1.orig.tar.gz libhermit-0.1 --exclude=.git - - cd libhermit-0.1 - - debuild -e PATH -e CFLAGS_FOR_TARGET -e GOFLAGS_FOR_TARGET -e FCFLAGS_FOR_TARGET -e FFLAGS_FOR_TARGET -e CXXFLAGS_FOR_TARGET -us -uc -j2 - - sudo dpkg -i ../libhermit*_amd64.deb - - make -j2 examples - - if [ "$TRAVIS_BRANCH" != "master" ]; then make test; fi + - source cmake/local-cmake.sh + - mkdir build + - cd build + - cmake .. + - make -j1 package + - cd $TRAVIS_BUILD_DIR + - ./tests.sh + +notifications: + slack: hermitcore:UtcfeEXkbpx3WyIDK2Wm2beS deploy: on: master @@ -30,16 +31,3 @@ deploy: secure: wo0yLY7xhGZYDqdB05UE+IOXXgYhAwj+zvtZh3ET2253hy35y74cDKMBNGfynH0aauPk8EFmN/LJoYaV/T9QF6pc1bilbqSg1/LJuL7hjAVVFaBSjwlE/Wbbb+EHNX5CR3qmC42SUvbrU+0WNvRu7WJBpZIoH9EtPv2Cj7uRV9+7Mtp/O3Ykl3E5LgkF5iA6Lo03TN+bZ1Vog5MbuJagDTpNa18vJ3jVYaed5gqOkghYYDpc5U9yxN3debS7/8MCl3u9V9uanMAyjc6wtbvJLotVkUwdXK8u9FohuWQ4pTEQ/QspLDDBuxaS3kLNWtzBMNQn6rcYIOWWKyD3uqvIhqjcErX7WChf3oGS1XPFfTHebNrHyV4KGvzkMAJUR/1qC5f4nZCsvgPv/35d702nky3Di2/WZsjD5zUR9g3+vPO8mnM3z8eA6ShVJcxezZ73Co3p0ZnBaF3J438bAKiT4nlrbIVpRzZzo/5nYTx//SefXSAmYCILr/y7xTYBqjfjMQHQZEMZSvJYRPbtP7eVCfWGEa2tG4rQndegUtwS+n1r8atcESL9eeUUM6sa1QzZYDYVseOc9GWcB7SIJzPOm8QTuTlkISHMGJ8FY+KHorP15VkVlr0EZ5c7KY0cBIbWoZGNQTg9+nSgChyf7ElNbAxPiCZsR0zafjMDhfcnzco= key: secure: JfsqEUO3Z60yGfuK5RSzwMoWZtaYflZtW7QE6R1DVMPEQ+CytzEdV2JaTpY14xz4yz1YpBBuQ0P3Q3e2rf/ORp8N8j7/5m3gfiDi8bRH3gX10r6vCQaUBilj0pz3amWUacxwBUEYR/f1029OnJ1qug30f4ARk7DWyuAePt0OboDXZ3j4JOi8xfXKTzofyKGugU4EuzhmKAbpHaBoX97g8z+gETC+wsBEYio8iD2h0ZOe/qZ0S+JGYkphIKcxpQazKdi3YrmWm0BUZsQRtkgoH7KUZm8vqfOUyVOrK+UGOTz4vXqCWHZ+wG1QRrGPUv8ehLrB26y2o02mmaDWQhM+I3RtllL06JDvDw40xjRImYtzg6xr7Mvl0OTQHprXrkN8gw2IbIivV8v31O46Ov+KIaN3CCx1IncnllBWjEXAIs4zPtvNj2Ad338JTkI/opHmPG0DI0DKE36r8wPZYTs/pHVpc3xEzwKYDklJkICjMLUakUGKppS7eKzKGRMjWvbT0vM/U7hHUcz0lA+BUoXedNmJQ1wBT85Ud8uobuKS4C8QmlgIuF1PI2+6LJr5LsCGZRvg7Pl1SPc3ZQLPHX4ggoLAnZZJiV/0ZPCn7XCLiUS1qws37l0uZT1zJQMFLsw9MGuP58tpT7WDuYYAwma/pL+OKC/JKoDhuJwM1I7wB4s= -env: - global: - - PATH=$PATH:/opt/hermit/bin/ - - HERMIT_ISLE=qemu - - HERMIT_CPUS=1 - - HERMIT_MEM="512M" - - HERMIT_KVM="0" - - HERMIT_VERBOSE="1" - - CFLAGS_FOR_TARGET="-m64 -mtls-direct-seg-refs -O2 -ftree-vectorize" - - GOFLAGS_FOR_TARGET"=-m64 -mtls-direct-seg-refs -O2 -ftree-vectorize" - - FCFLAGS_FOR_TARGET"=-m64 -mtls-direct-seg-refs -O2 -ftree-vectorize" - - FFLAGS_FOR_TARGET="-m64 -mtls-direct-seg-refs -O2 -ftree-vectorize" - - CXXFLAGS_FOR_TARGET="-m64 -mtls-direct-seg-refs -O2 -ftree-vectorize" diff --git a/CMakeLists.txt b/CMakeLists.txt new file mode 100644 index 000000000..e212473ce --- /dev/null +++ b/CMakeLists.txt @@ -0,0 +1,220 @@ +cmake_minimum_required(VERSION 3.7) + +include(ExternalProject) +include(cmake/HermitCore.cmake) + +project (HermitCore) + +### Kernel + +# generate config files +add_subdirectory(include/hermit) + +add_kernel_module_sources("kernel" "kernel/*.c") +add_kernel_module_sources("libkern" "libkern/*.c") +add_kernel_module_sources("mm" "mm/*.c") +add_kernel_module_sources("drivers" "drivers/net/*.c") + +set(LWIP_SRC lwip/src) +add_kernel_module_sources("lwip" "${LWIP_SRC}/api/*.c") +add_kernel_module_sources("lwip" "${LWIP_SRC}/arch/*.c") +add_kernel_module_sources("lwip" "${LWIP_SRC}/core/*.c") +add_kernel_module_sources("lwip" "${LWIP_SRC}/core/ipv4/*.c") +add_kernel_module_sources("lwip" "${LWIP_SRC}/core/ipv6/*.c") +add_kernel_module_sources("lwip" "${LWIP_SRC}/netif/*.c") + +get_kernel_modules(KERNEL_MODULES) +foreach(MODULE ${KERNEL_MODULES}) + get_kernel_module_sources(SOURCES ${MODULE}) + + # maintain list of all objects that will end up in libhermit.a + list(APPEND KERNEL_OBJECTS $) + + add_library(${MODULE} OBJECT ${SOURCES}) + + # this is kernel code + target_compile_definitions(${MODULE} + PRIVATE -D__KERNEL__) + + target_compile_options(${MODULE} + PRIVATE ${HERMIT_KERNEL_FLAGS}) + + target_include_directories(${MODULE} + PUBLIC ${HERMIT_KERNEL_INCLUDES}) + + # suppress all LwIP compiler warnings. Not our code, so we cannot fix + if("${MODULE}" STREQUAL "lwip") + target_compile_options(${MODULE} + PRIVATE -w) + endif() + +endforeach() + +# add arch/x86 and its objects +# TODO: make this conditional when new architectures are implemented +add_subdirectory(arch/x86) +list(APPEND KERNEL_OBJECTS + $ + $) + +# finally build libhermit.a +add_library(hermit-bootstrap STATIC ${KERNEL_OBJECTS}) +set_target_properties(hermit-bootstrap PROPERTIES + ARCHIVE_OUTPUT_NAME hermit) + +# after compiling ASM sources, we need to post-process them. Adding this +# dependency makes sure that this is done before hermit is linked +add_dependencies(hermit-bootstrap ${X86_KERNEL_TARGET}) + +add_custom_command( + TARGET + hermit-bootstrap POST_BUILD + # rename sections in final library + COMMAND + ${CMAKE_OBJCOPY} --rename-section .bss=.kbss + --rename-section .text=.ktext + --rename-section .data=.kdata + $ + + # copy libhermit.a into local prefix directory so that all subsequent + # targets can link against the freshly built version (as opposed to + # linking against the one supplied by the toolchain) + COMMAND + ${CMAKE_COMMAND} -E make_directory ${LOCAL_PREFIX_ARCH_LIB_DIR} + COMMAND + ${CMAKE_COMMAND} -E copy_if_different + $ + ${LOCAL_PREFIX_ARCH_LIB_DIR}/ + + # and also copy headers into local prefix + COMMAND + ${CMAKE_COMMAND} -E make_directory ${LOCAL_PREFIX_ARCH_INCLUDE_DIR}/hermit + COMMAND + ${CMAKE_COMMAND} -E copy_if_different + ${CMAKE_BINARY_DIR}/include/hermit/*.h + ${LOCAL_PREFIX_ARCH_INCLUDE_DIR}/hermit/ + COMMAND + ${CMAKE_COMMAND} -E copy_if_different + ${CMAKE_BINARY_DIR}/include/hermit/*.asm + ${LOCAL_PREFIX_ARCH_INCLUDE_DIR}/hermit/) + + +# deploy libhermit.a and headers for package creation +install(TARGETS hermit-bootstrap + DESTINATION ${TARGET_ARCH}/lib + COMPONENT bootstrap) + +install(DIRECTORY include/hermit + DESTINATION ${TARGET_ARCH}/include/ + COMPONENT bootstrap + FILES_MATCHING + PATTERN *.h) + +# provide custom target to only install libhermit without its runtimes which is +# needed during the compilation of the cross toolchain +add_custom_target(hermit-bootstrap-install + DEPENDS + hermit-bootstrap + COMMAND + ${CMAKE_COMMAND} + -DCMAKE_INSTALL_COMPONENT=bootstrap + -DCMAKE_INSTALL_PREFIX=${CMAKE_INSTALL_PREFIX} + -P cmake_install.cmake) + +# The target 'hermit' includes the HermitCore kernel and several runtimes. +# Applications should depend on this target if they link against HermitCore. +add_custom_target(hermit + DEPENDS hermit-bootstrap) + + +### External projects +# +# Build projects externally and deploy into temporary common prefix, will later +# be relocated for installation + +## HermitCore's own tools such as Qemu/KVM proxy +build_external(tools ${HERMIT_ROOT}/tools "") +build_external(arch_x86_loader ${HERMIT_ROOT}/arch/x86/loader "") + +## Intel's OpenMP runtime for x86 (libomp) +build_external(libiomp ${HERMIT_ROOT}/usr/libomp "" + -DHERMIT=1 + -DCMAKE_TOOLCHAIN_FILE=${CMAKE_TOOLCHAIN_FILE} + -DCMAKE_INSTALL_PREFIX=${CMAKE_INSTALL_PREFIX}/${TARGET_ARCH}) + +# libomp is part of HermitCore's runtime and should be available before any +# application will link +add_dependencies(hermit libiomp) + +## iRCCE +build_external(ircce ${HERMIT_ROOT}/usr/ircce "") +add_dependencies(hermit ircce) + +## XRay profiler +build_external(xray ${HERMIT_ROOT}/usr/xray "") +add_dependencies(hermit xray) + +## Tests and benchmarks +build_external(tests ${HERMIT_ROOT}/usr/tests hermit) +build_external(benchmarks ${HERMIT_ROOT}/usr/benchmarks hermit) +build_external(openmpbench ${HERMIT_ROOT}/usr/openmpbench hermit) + +## relocate the local prefix to our install destination +install(DIRECTORY ${LOCAL_PREFIX_DIR}/ + DESTINATION ${CMAKE_INSTALL_PREFIX}/ + USE_SOURCE_PERMISSIONS) + + +### QEmu +# Start HermitCore as multi-kernel in a QEmu VM + +add_custom_target(qemu + COMMAND + qemu-system-x86_64 + -machine accel=kvm -cpu host + -smp 10 -m 8G -numa node,nodeid=0,cpus=0-4 -numa node,nodeid=1,cpus=5-9 + -kernel ${HERMIT_ROOT}/config/bzImage + -append "root=/dev/ram0 rootfstype=ramfs init=init console=ttyS0" + -net nic,model=rtl8139 -net user -net dump + -nographic -monitor telnet:127.0.0.1:1235,server,nowait + -fsdev local,security_model=none,id=fsdev0,path=${LOCAL_PREFIX_DIR} + -device virtio-9p-pci,id=fs0,fsdev=fsdev0,mount_tag=hermit + -s + USES_TERMINAL VERBATIM) + +# create a QEmu target that depends on everything +get_property(_TARGETS + DIRECTORY . + PROPERTY BUILDSYSTEM_TARGETS) + +add_custom_target(qemu-dep + DEPENDS + ${_TARGETS} qemu) + + +### Packaging + +set(CPACK_PACKAGE_NAME libhermit) +set(CPACK_SYSTEM_NAME all) + +set(CPACK_PACKAGE_VERSION_MAJOR 0) +set(CPACK_PACKAGE_VERSION_MINOR 2) +set(CPACK_PACKAGE_VERSION_PATCH 0) + +set(CPACK_PACKAGE_CONTACT "Stefan Lankes ") + +# build .deb, .rpm and .tar.bz2 packages +set(CPACK_GENERATOR DEB;RPM;TBZ2) + +# needed in order for tests and bechmark to use correct install prefix +set(CPACK_SET_DESTDIR on) + +## Debian specific +# not dependent on Debian system architecture +set(CPACK_DEBIAN_PACKAGE_ARCHITECTURE all) + +## RPM specific +# libhermit is currently not relocatable +set(CPACK_PACKAGE_RELOCATABLE FALSE) + +include(CPack) diff --git a/LICENSE b/LICENSE new file mode 100644 index 000000000..9cae3d68b --- /dev/null +++ b/LICENSE @@ -0,0 +1,29 @@ +BSD 3-Clause License + +Copyright (c) 2010-2017, RWTH Aachen University, Germany +All rights reserved. + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions are met: + +* Redistributions of source code must retain the above copyright notice, this + list of conditions and the following disclaimer. + +* Redistributions in binary form must reproduce the above copyright notice, + this list of conditions and the following disclaimer in the documentation + and/or other materials provided with the distribution. + +* Neither the name of the copyright holder nor the names of its + contributors may be used to endorse or promote products derived from + this software without specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" +AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE +FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR +SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER +CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, +OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. diff --git a/Makefile.in b/Makefile.in deleted file mode 100644 index d043e0ce8..000000000 --- a/Makefile.in +++ /dev/null @@ -1,278 +0,0 @@ -TERM = xterm -TOPDIR := $(shell pwd) -ARCH = x86 -NAME = libhermit.a -DRIVERDIRS = drivers/net -LWIPDIRS = lwip/src/arch lwip/src/api lwip/src/core lwip/src/core/ipv4 lwip/src/core/ipv6 lwip/src/netif -KERNDIRS = kernel mm libkern arch/$(ARCH)/kernel arch/$(ARCH)/mm $(LWIPDIRS) $(DRIVERDIRS) -SUBDIRS = $(KERNDIRS) -TODAY := $(shell date +'%Y%m%d') -QEMU = @QEMU@ -machine accel=kvm -cpu host -CROSSDIR = @prefix@/bin -JOBS = $(shell nproc) -ARCH_OPT = @ARCH_OPT@ -TOOLCHAIN = @TOOLCHAIN@ -ifeq ($(TOOLCHAIN),0) -BUILD_BOOTSTRAP = -BUILD_TOOLCHAIN = -INSTALL_LIBHERMIT = -else -BUILD_BOOTSTRAP = bootstrap -BUILD_TOOLCHAIN = toolchain -INSTALL_LIBHERMIT = install_libhermit -endif - -prefix = @prefix@ -INSTALL = @INSTALL@ -INSTALL_PROGRAM = @INSTALL_PROGRAM@ -INSTALL_SCRIPT = @INSTALL_SCRIPT@ -INSTALL_DATA = @INSTALL_DATA@ - -# add path to the cross toolchain -PATH:=$(PATH):$(CROSSDIR) - -# Set your own cross compiler tool chain prefix here -CROSSCOMPREFIX = x86_64-hermit -STACKPROT = -fno-stack-protector - -FC_FOR_TARGET = $(CROSSCOMPREFIX)-gfortran -CC_FOR_TARGET = $(CROSSCOMPREFIX)-gcc -GO_FOR_TARGET = $(CROSSCOMPREFIX)-gccgo -CXX_FOR_TARGET = $(CROSSCOMPREFIX)-g++ -GCC_FOR_TARGET = $(CROSSCOMPREFIX)-gcc -CPP_FOR_TARGET = $(CROSSCOMPREFIX)-cpp -AR_FOR_TARGET = $(CROSSCOMPREFIX)-ar -AS_FOR_TARGET = $(CROSSCOMPREFIX)-as -LD_FOR_TARGET = $(CROSSCOMPREFIX)-ld -NM_FOR_TARGET = $(CROSSCOMPREFIX)-nm -OBJDUMP_FOR_TARGET = $(CROSSCOMPREFIX)-objdump -OBJCOPY_FOR_TARGET = $(CROSSCOMPREFIX)-objcopy -RANLIB_FOR_TARGET = $(CROSSCOMPREFIX)-ranlib -STRIP_FOR_TARGET = $(CROSSCOMPREFIX)-strip -READELF_FOR_TARGET = $(CROSSCOMPREFIX)-readelf -ELFEDIT_FOR_TARGET = $(CROSSCOMPREFIX)-elfedit - -MAKE = make -NASM = nasm -NASMFLAGS = -felf64 -g -i$(TOPDIR)/include/hermit/ - -INCLUDE = -I$(TOPDIR)/include -I$(TOPDIR)/arch/$(ARCH)/include -I$(TOPDIR)/lwip/src/include -I$(TOPDIR)/drivers -CFLAGS = -g -m64 -Wall -O2 -mno-red-zone -fno-var-tracking-assignments -fstrength-reduce -fomit-frame-pointer -finline-functions -ffreestanding -nostdinc -fno-stack-protector -mno-sse -mno-mmx -mno-sse2 -mno-3dnow -mno-avx -fno-delete-null-pointer-checks -falign-jumps=1 -falign-loops=1 -mno-80387 -mno-fp-ret-in-387 -mskip-rax-setup -fno-common -Wframe-larger-than=1024 -fno-strict-aliasing -fno-asynchronous-unwind-tables -fno-strict-overflow -maccumulate-outgoing-args $(INCLUDE) -AR = ar -ARFLAGS = rsv -RM = rm -rf -OUTPUT_FORMAT = -O elf64-x86-64-hermit - -# Additional flags for profiling using Xray -PROFILING_LDFLAGS = -PROFILING_CFLAGS = - -ifdef PROFILING - PROFILING_LDFLAGS = -lxray - - PROFILING_CFLAGS = -falign-functions=32 -finstrument-functions - PROFILING_CFLAGS += -finstrument-functions-exclude-function-list=_mm_pause,_mm_setcsr,_mm_getcsr # we need this for libiomp to work - PROFILING_CFLAGS += -DXRAY -DXRAY_DISABLE_BROWSER_INTEGRATION -DXRAY_NO_DEMANGLE - PROFILING_CFLAGS += -DXRAY_ANNOTATE -endif - -CFLAGS_FOR_NEWLIB = -m64 -mtls-direct-seg-refs -O3 -ftree-vectorize $(ARCH_OPT) #$(STACKPROT) -GOFLAGS_FOR_NEWLIB = -m64 -mtls-direct-seg-refs -O3 -ftree-vectorize $(ARCH_OPT) -FCFLAGS_FOR_NEWLIB = -m64 -mtls-direct-seg-refs -O3 -ftree-vectorize $(ARCH_OPT) -FFLAGS_FOR_NEWLIB = -m64 -mtls-direct-seg-refs -O3 -ftree-vectorize $(ARCH_OPT) -CXXFLAGS_FOR_NEWLIB = -m64 -mtls-direct-seg-refs -O3 -ftree-vectorize $(ARCH_OPT) -LDFLAGS_FOR_NEWLIB = -NASMFLAGS_FOR_NEWLIB = -felf64 -CFLAGS_FOR_TOOLS = -O2 -Wall -std=gnu99 -LDFLAGS_FOR_TOOLS = - -# Prettify output -V = 1 -ifeq ($V,0) - Q = @ - P = > /dev/null -endif - - -default: all - -all: arch/x86/kernel/boot.h $(BUILD_BOOTSTRAP) $(NAME) $(BUILD_TOOLCHAIN) tools loader - -toolchain: $(INSTALL_LIBHERMIT) - $Q$(MAKE) ARCH=$(ARCH) PREFIX=$(prefix) \ - LDFLAGS_FOR_TARGET="$(LDFLAGS_FOR_NEWLIB)" \ - GOFLAGS_FOR_TARGET="$(GOFLAGS_FOR_NEWLIB)" \ - CFLAGS_FOR_TARGET="$(CFLAGS_FOR_NEWLIB)" \ - FFLAGS_FOR_TARGET="$(FFLAGS_FOR_NEWLIB)" \ - FCFLAGS_FOR_TARGET="$(FCFLAGS_FOR_NEWLIB)" \ - FCFLAGS="$(FCFLAGS_FOR_NEWLIB)" \ - CXXFLAGS_FOR_TARGET="$(CXXFLAGS_FOR_NEWLIB)" \ - NASMFLAGS="$(NASMFLAGS_FOR_NEWLIB)" \ - CC_FOR_TARGET=$(CC_FOR_TARGET) \ - GO_FOR_TARGET=$(GO_FOR_TARGET) \ - FC_FOR_TARGET=$(FC_FOR_TARGET) \ - CXX_FOR_TARGET=$(CXX_FOR_TARGET) \ - GCC_FOR_TARGET=$(GCC_FOR_TARGET) \ - AR_FOR_TARGET=$(AR_FOR_TARGET) \ - AS_FOR_TARGET=$(AS_FOR_TARGET) \ - LD_FOR_TARGET=$(LD_FOR_TARGET) \ - NM_FOR_TARGET=$(NM_FOR_TARGET) \ - OBJDUMP_FOR_TARGET=$(OBJDUMP_FOR_TARGET) \ - OBJCOPY_FOR_TARGET=$(OBJCOPY_FOR_TARGET) \ - RANLIB_FOR_TARGET=$(RANLIB_FOR_TARGET) \ - STRIP_FOR_TARGET=$(STRIP_FOR_TARGET) \ - ELFEDIT_FOR_TARGET=$(ELFEDIT_FOR_TARGET) \ - READELF_FOR_TARGET=$(READELF_FOR_TARGET) \ - PROFILING_CFLAGS="$(PROFILING_CFLAGS)" \ - PROFILING_LDFLAGS="$(PROFILING_LDFLAGS)" -C usr toolchain - -libs: - $Q$(MAKE) ARCH=$(ARCH) PREFIX=$(prefix) \ - LDFLAGS_FOR_TARGET="$(LDFLAGS_FOR_NEWLIB)" \ - GOFLAGS_FOR_TARGET="$(GOFLAGS_FOR_NEWLIB)" \ - CFLAGS_FOR_TARGET="$(CFLAGS_FOR_NEWLIB)" \ - FFLAGS_FOR_TARGET="$(FFLAGS_FOR_NEWLIB)" \ - FCFLAGS_FOR_TARGET="$(FCFLAGS_FOR_NEWLIB)" \ - FCFLAGS="$(FCFLAGS_FOR_NEWLIB)" \ - CXXFLAGS_FOR_TARGET="$(CXXFLAGS_FOR_NEWLIB)" \ - NASMFLAGS="$(NASMFLAGS_FOR_NEWLIB)" \ - CC_FOR_TARGET=$(CC_FOR_TARGET) \ - GO_FOR_TARGET=$(GO_FOR_TARGET) \ - FC_FOR_TARGET=$(FC_FOR_TARGET) \ - CXX_FOR_TARGET=$(CXX_FOR_TARGET) \ - GCC_FOR_TARGET=$(GCC_FOR_TARGET) \ - AR_FOR_TARGET=$(AR_FOR_TARGET) \ - AS_FOR_TARGET=$(AS_FOR_TARGET) \ - LD_FOR_TARGET=$(LD_FOR_TARGET) \ - NM_FOR_TARGET=$(NM_FOR_TARGET) \ - OBJDUMP_FOR_TARGET=$(OBJDUMP_FOR_TARGET) \ - OBJCOPY_FOR_TARGET=$(OBJCOPY_FOR_TARGET) \ - RANLIB_FOR_TARGET=$(RANLIB_FOR_TARGET) \ - STRIP_FOR_TARGET=$(STRIP_FOR_TARGET) \ - ELFEDIT_FOR_TARGET=$(ELFEDIT_FOR_TARGET) \ - READELF_FOR_TARGET=$(READELF_FOR_TARGET) \ - PROFILING_CFLAGS="$(PROFILING_CFLAGS)" \ - PROFILING_LDFLAGS="$(PROFILING_LDFLAGS)" -C usr libs - -bootstrap: - $Q$(MAKE) ARCH=$(ARCH) PREFIX=$(prefix) CFLAGS="" LDFLAGS="" -C usr bootstrap - -tools: - $Q$(MAKE) ARCH=$(ARCH) PREFIX=$(prefix) CFLAGS="$(CFLAGS_FOR_TOOLS)" LDFLAGS="$(LDFLAGS_FOR_TOOLS)" -C tools - -loader: - $Q$(MAKE) -C arch/$(ARCH)/loader - -$(NAME): - @echo [AR] $(NAME) - $Q$(AR_FOR_TARGET) $(ARFLAGS) -o $(NAME) $^ - $Q$(OBJCOPY_FOR_TARGET) --rename-section .bss=.kbss --rename-section .text=.ktext --rename-section .data=.kdata $(NAME) - -examples: - $Q$(MAKE) ARCH=$(ARCH) PREFIX=$(prefix) \ - LDFLAGS_FOR_TARGET="$(LDFLAGS_FOR_NEWLIB)" \ - GOFLAGS_FOR_TARGET="$(GOFLAGS_FOR_NEWLIB)" \ - CFLAGS_FOR_TARGET="$(CFLAGS_FOR_NEWLIB)" \ - FFLAGS_FOR_TARGET="$(FFLAGS_FOR_NEWLIB)" \ - FCFLAGS_FOR_TARGET="$(FCFLAGS_FOR_NEWLIB)" \ - FCFLAGS="$(FCFLAGS_FOR_NEWLIB)" \ - CXXFLAGS_FOR_TARGET="$(CXXFLAGS_FOR_NEWLIB)" \ - NASMFLAGS="$(NASMFLAGS_FOR_NEWLIB)" \ - CC_FOR_TARGET=$(CC_FOR_TARGET) \ - GO_FOR_TARGET=$(GO_FOR_TARGET) \ - FC_FOR_TARGET=$(FC_FOR_TARGET) \ - CXX_FOR_TARGET=$(CXX_FOR_TARGET) \ - GCC_FOR_TARGET=$(GCC_FOR_TARGET) \ - AR_FOR_TARGET=$(AR_FOR_TARGET) \ - AS_FOR_TARGET=$(AS_FOR_TARGET) \ - LD_FOR_TARGET=$(LD_FOR_TARGET) \ - NM_FOR_TARGET=$(NM_FOR_TARGET) \ - OBJDUMP_FOR_TARGET=$(OBJDUMP_FOR_TARGET) \ - OBJCOPY_FOR_TARGET=$(OBJCOPY_FOR_TARGET) \ - RANLIB_FOR_TARGET=$(RANLIB_FOR_TARGET) \ - STRIP_FOR_TARGET=$(STRIP_FOR_TARGET) \ - ELFEDIT_FOR_TARGET=$(ELFEDIT_FOR_TARGET) \ - READELF_FOR_TARGET=$(READELF_FOR_TARGET) \ - PROFILING_CFLAGS="$(PROFILING_CFLAGS)" \ - PROFILING_LDFLAGS="$(PROFILING_LDFLAGS)" -C usr examples - -test: - . ./test.sh - -qemu: - $(QEMU) -smp 10 -m 8G -numa node,nodeid=0,cpus=0-4 -numa node,nodeid=1,cpus=5-9 \ - -kernel config/bzImage \ - -append "root=/dev/ram0 rootfstype=ramfs init=init console=ttyS0" \ - -net nic,model=rtl8139 -net user -net dump \ - -nographic -monitor telnet:127.0.0.1:1235,server,nowait \ - -fsdev local,security_model=none,id=fsdev0,path=$(shell realpath .) \ - -device virtio-9p-pci,id=fs0,fsdev=fsdev0,mount_tag=hermit \ - -s - -install_libhermit: - $Q$(INSTALL_PROGRAM) -d $(prefix)/$(CROSSCOMPREFIX)/lib/ - $Q$(INSTALL_DATA) $(NAME) $(prefix)/$(CROSSCOMPREFIX)/lib/ - $Q$(INSTALL_PROGRAM) -d $(prefix)/$(CROSSCOMPREFIX)/include/hermit/ - $Q$(INSTALL_DATA) include/hermit/* $(prefix)/$(CROSSCOMPREFIX)/include/hermit/ - -install: install_libhermit - $Q$(MAKE) PREFIX=$(prefix) -C usr install - $Q$(MAKE) PREFIX=$(prefix) -C tools install - -clean: - $Q$(RM) $(NAME) $(NAME).sym $(NAME).bin *~ - $Q$(MAKE) -C tools clean - $Q$(MAKE) -C usr clean - $Q$(MAKE) -C arch/$(ARCH)/loader clean - @echo Cleaned. - -veryclean: clean - $Q$(RM) qemu-vlan0.pcap include/hermit/config.inc - $Q$(MAKE) -C tools veryclean - $Q$(MAKE) -C usr veryclean - $Q$(MAKE) -C arch/$(ARCH)/loader veryclean - @echo Very cleaned - -doc: - @echo Create documentation... - @doxygen - -%.o : %.c - @echo [CC] $@ - $Q$(CC_FOR_TARGET) -c -D__KERNEL__ $(CFLAGS) -o $@ $< - @echo [DEP] $*.dep - $Q$(CC_FOR_TARGET) -MF $*.dep -MT $*.o -MM $(CFLAGS) $< - -arch/x86/kernel/boot.bin: arch/x86/kernel/boot.asm - @echo " NASM $@" - $Q$(NASM) -fbin -o $@ $< - -arch/x86/kernel/boot.h: arch/x86/kernel/boot.bin - @echo " HEXDUMP $@" - $Qecho "static const uint8_t boot_code[] = { \ - $(shell hexdump -v -e '"0x" 1/1 "%02X" ", "' $<) \ - };" > $@ - -include/hermit/config.inc: include/hermit/config.h - @echo "; This file is generated automatically from the config.h file." > include/hermit/config.inc - @echo "; Before editing this, you should consider editing config.h." >> include/hermit/config.inc - @awk '/^#define MAX_CORES/{ print "%define MAX_CORES", $$3 }' include/hermit/config.h >> include/hermit/config.inc - @awk '/^#define KERNEL_STACK_SIZE/{ print "%define KERNEL_STACK_SIZE", $$3 }' include/hermit/config.h >> include/hermit/config.inc - @awk '/^#define VIDEO_MEM_ADDR/{ print "%define VIDEO_MEM_ADDR", $$3 }' include/hermit/config.h >> include/hermit/config.inc - @awk '/^#define CONFIG_VGA/{ print "%define CONFIG_VGA", $$3 }' include/hermit/config.h >> include/hermit/config.inc - @awk '/^#define DYNAMIC_TICKS/{ print "%define DYNAMIC_TICKS", $$3 }' include/hermit/config.h >> include/hermit/config.inc - @awk '/^#define SAVE_FPU/{ print "%define SAVE_FPU", $$3 }' include/hermit/config.h >> include/hermit/config.inc - -%.o : %.asm include/hermit/config.inc - @echo [ASM] $@ - $Q$(NASM) $(NASMFLAGS) -o $@ $< - $Q$(ELFEDIT_FOR_TARGET) --output-osabi HermitCore $@ - #$Q$(OBJCOPY_FOR_TARGET) $(OUTPUT_FORMAT) $@ - -%.o : %.S - @echo [GCC-ASM] $@ - $Q$(CC_FOR_TARGET) $(CFLAGS) -c -o $@ $< - -.PHONY: default all clean qemu gdb usr test toolchain tools examples libs - -include $(addsuffix /Makefile,$(SUBDIRS)) diff --git a/Makefile.inc b/Makefile.inc deleted file mode 100644 index c0e214dc9..000000000 --- a/Makefile.inc +++ /dev/null @@ -1,20 +0,0 @@ -C_source-$(MODULE) := $(addprefix $(subst _,/,$(MODULE))/,$(filter %.c,$(C_source))) -ASM_source-$(MODULE) := $(addprefix $(subst _,/,$(MODULE))/,$(filter %.asm,$(ASM_source))) -C_source := -ASM_source := - -OBJS-$(MODULE) := $(C_source-$(MODULE):.c=.o) -OBJS-$(MODULE) += $(ASM_source-$(MODULE):.asm=.o) - -$(MODULE): $(OBJS-$(MODULE)) - -$(NAME): $(OBJS-$(MODULE)) - -clean: clean-$(MODULE) -clean-$(MODULE): clean-% : - @echo Cleaning $(subst _,/,$*) - $Q$(RM) $(OBJS-$*) $(C_source-$*:.c=.dep) - -.PHONY: clean-$(MODULE) $(MODULE) - --include $(C_source-$(MODULE):.c=.dep) diff --git a/README.md b/README.md index cd42ae4a0..1de5d9155 100644 --- a/README.md +++ b/README.md @@ -1,91 +1,291 @@ + + + # HermitCore - A lightweight unikernel for a scalable and predictable runtime behavior -The project [HermitCore](http://www.hermitcore.org) is new [unikernel](http://unikernel.org) targeting at a scalable and predictable runtime for high-performance and cloud computing. -HermitCore extends the multi-kernel approach (like [McKernel](http://www-sys-aics.riken.jp/ResearchTopics/os/mckernel.html)) with unikernel features for a better programmability and scalability for hierarchical systems. -On the startup of HermitCore applications, cores are isolated from the Linux system enabling the bare-metal of the applications on these cores. -This approach achieves lower OS jitter and a better scalability compared to full-weight kernels. -Inter-kernel communication between HermitCore applications and the Linux system is realized by means of an IP interface. +[![Build Status](https://travis-ci.org/RWTH-OS/HermitCore.svg?branch=master)](https://travis-ci.org/RWTH-OS/HermitCore) +[![Slack Status](https://radiant-ridge-95061.herokuapp.com/badge.svg)](https://radiant-ridge-95061.herokuapp.com) -In addition to the multi-kernel approach described above, HermitCore can be used as classical standalone unikernel as well. -In this case HermitCore runs a single-kernel exclusively on the hardware or within a virtual machine. -This reduces the resource demand and improves the boot time which is critical for cloud computing applications. -It is the result of a research project at RWTH Aachen University and is currently an experimental approach, i.e., not production ready. -Please use it with caution. +The project [HermitCore]( http://www.hermitcore.org ) is a new +[unikernel](http://unikernel.org) targeting a scalable and predictable runtime +for high-performance and cloud computing. HermitCore extends the multi-kernel +approach (like +[McKernel](http://www-sys-aics.riken.jp/ResearchTopics/os/mckernel.html)) with +unikernel features for a better programmability and scalability for hierarchical +systems. + +![HermitCore Demo](img/demo.gif) + +On the startup of HermitCore applications, cores are isolated from the Linux +system enabling bare-metal execution of on these cores. This approach achieves +lower OS jitter and a better scalability compared to full-weight kernels. +Inter-kernel communication between HermitCore applications and the Linux system +is realized by means of an IP interface. + +In addition to the multi-kernel approach described above, HermitCore can be used +as a classical standalone unikernel as well. In this case, HermitCore runs a +single-kernel exclusively on the hardware or within a virtual machine. This +reduces the resource demand and loweres the boot time which is critical for +cloud computing applications. It is the result of a research project at RWTH +Aachen University and is currently an experimental approach, i.e., not +production ready. Please use it with caution. + +## Contributing + +HermitCore is being developed on [GitHub](https://github.com/RWTH-OS/HermitCore). +Create your own fork, send us a pull request, and chat with us on [Slack](https://radiant-ridge-95061.herokuapp.com). ## Requirements -The build process works currently only on **x86-based Linux** systems. The following software packets are required to build HermitCore on a Linux system: +The build process works currently only on **x86-based Linux** systems. To build +the HermitCore kernel and applications you need: -* Netwide Assembler (NASM) -* GNU Make, GNU Binutils -* Tools and libraries to build *linux*, *binutils* and *gcc* (e.g. flex, bison, MPFR library, GMP library, MPC library, ISL library) -* texinfo -* Qemu + * CMake + * Netwide Assember (NASM) + * recent host compiler such as GCC + * HermitCore cross-toolchain, i.e. Binutils, GCC, newlib, pthreads -On Debian-based systems the packets can be installed by executing: -``` - sudo apt-get install qemu-system-x86 nasm texinfo libmpfr-dev libmpc-dev libgmp-dev libisl-dev flex bison +### HermitCore cross-toolchain + +We provide prebuilt packages (currently Debian-based only) of the HermitCore +toolchain, which can be installed as follows: + +```bash +$ echo "deb [trusted=yes] https://dl.bintray.com/rwth-os/hermitcore vivid main" | sudo tee -a /etc/apt/sources.list +$ sudo apt-get -qq update +$ sudo apt-get install binutils-hermit newlib-hermit pthread-embedded-hermit gcc-hermit libhermit ``` -## Installing HermitCore with by using debian packets +If you want to build the toolchain yourself, have a look at the repository [hermit-toolchain](https://github.com/RWTH-OS/hermit-toolchain), which contains scripts to build the whole toolchain. -We provide binary packets for debian-based systems containing the complete HermitCore toolchain including a cross-compiler. -To install the packets you have to execute the following commands: +Depending on how you want to use HermitCore, you might need additional packages +such as: + + * QEMU (`apt-get install qemu-system-x86`) + +## Building HermitCore + +### Preliminary work + +To build HermitCore from source (without compiler), the repository with its submodules has to be cloned. + +```bash +$ git clone git@github.com:RWTH-OS/HermitCore.git +$ cd HermitCore +$ git submodule init +$ git submodule update ``` -echo "deb [trusted=yes] https://dl.bintray.com/rwth-os/hermitcore vivid main" | sudo tee -a /etc/apt/sources.list -sudo apt-get -qq update -sudo apt-get install binutils-hermit newlib-hermit pthread-embedded-hermit gcc-hermit libhermit + +We require a fairly recent version of CMake (`3.7`) which is not yet present in +most Linux distributions. We therefore provide a helper script that fetches the +required CMake binaries from the upstream project and stores them locally, so +you only need to download it once. + +```bash +$ . cmake/local-cmake.sh +-- Downloading CMake +--2017-03-28 16:13:37-- https://cmake.org/files/v3.7/cmake-3.7.2-Linux-x86_64.tar.gz +Loaded CA certificate '/etc/ssl/certs/ca-certificates.crt' +Resolving cmake.org... 66.194.253.19 +Connecting to cmake.org|66.194.253.19|:443... connected. +HTTP request sent, awaiting response... 200 OK +Length: 30681434 (29M) [application/x-gzip] +Saving to: ‘cmake-3.7.2-Linux-x86_64.tar.gz’ + +cmake-3.7.2-Linux-x86_64.tar.gz 100%[===================>] 29,26M 3,74MB/s in 12s + +2017-03-28 16:13:50 (2,48 MB/s) - ‘cmake-3.7.2-Linux-x86_64.tar.gz’ saved [30681434/30681434] + +-- Unpacking CMake +-- Local CMake v3.7.2 installed to cmake/cmake-3.7.2-Linux-x86_64 +-- Next time you source this script, no download will be neccessary ``` -This toolchain is able to build applications for [classical unikernel](#building-and-testing-hermitcore-as-classical-standalone-unikernel) environments within virtual machines or bare-metal in a multi-kernel environment. -For the latter, you have to install the modified Linux kernel. -An introduction to this execution mode is provided in section [Building and testing HermitCore as multi-kernel on a real machine](#building-and-testing-hermitcore-as-multi-kernel-on a-real-machine). -## Building and testing HermitCore as multi-kernel within a virtual machine +So before you build HermitCore you have to source the `local-cmake.sh` script +everytime you open a new terminal. -1. Please make sure that you cloned this repository and all its submodules. -2. To configure the system, run the *configure* script in the directory, which contains this *README*. - With the flag `--with-toolchain`, the HermitCore's complete cross toolchain (cross compiler, binutils, etc.) will be downloaded and built. - **NOTE**: This requires write access to the installation directory, which is specified by the flag `--prefix`. - At the end of this *README* in section *Tips* you find hints to enable optimization for the target. -3. The command `make all` build the the HermitCore kernel and depending on the configuration flags the cross toolchain. -4. Install the kernel with `make install`. -5. Build all example applications with `make examples`. -6. To start a virtual machine and to boot a small Linux version use the command `make qemu`. - Per default, the virtual machine has 10 cores, 2 NUMA nodes, and 8 GiB RAM. - To increase or to decrease the machine size, the label `qemu` in the Makefile has to be modified accordingly. -7. Inside the VM runs a small Linux system, which already includes the patches for HermitCore. - Per NUMA node (= HermitCore isle) there is a directory called `isleX` under `/sys/hermit` , where `X` represents the NUMA node ID. - The demo applications are located in the directories `/hermit/usr/{tests,benchmarks}`. - A HermitCore loader is already registered. - By starting a HermitCore application, a proxy will be executed on the Linux system, while the HermitCore binary will be started on isle 0 with cpu 1. - To change the default behavior, the environment variable `HERMIT_ISLE` is used to specify the (memory) location of the isle, while the environment variable `HERMIT_CPUS` is used to specify the cores. - For instance, `HERMIT_ISLE=1 HERMIT_CPUS="3-5" /hermit/usr/tests/hello` starts a HelloWorld demo on the HermitCore isle 1, which uses the cores 3 to 5. - The output messages are forwarded to the Linux proxy and printed on the Linux system. -8. HermitCore's kernel messages of `isleX` are available via `cat /sys/hermit/isleX/log`. -9. There is a virtual IP device for the communication between the HermitCore isles and the Linux system (see output of `ifconfig`). - Per default, the Linux system has the IP address `192.168.28.1`. - The HermitCore isles starts with the IP address `192.168.28.2` for isle 0 and is increased by one for every isle. -10. More HermitCore applications are available at `/hermit/usr/{tests,benchmarks}` which is a shared directory between the host and QEmu. +### Building the library perating systems and its examples -## Building and testing HermitCore as multi-kernel on a real machine +To build HermitCore go to the directory with the source code, create a `build` directory and call `cmake` followed by `make`. + +```bash +$ mkdir build +$ cd build +$ cmake .. +$ make +$ sudo make install +``` + +If your toolchain is not located in `/opt/hermit/bin` then you have to supply +its location to the `cmake` command above like so: + +```bash +$ cmake -DTOOLCHAIN_BIN_DIR=/home/user/hermit/bin .. +``` + +assuming that binaries like `x86_64-hermit-gcc` and friends are located in that +directory. To install your new version in the same directory, you have to set the installation path and to install HermitCore as follows: + +```bash +$ cmake -DTOOLCHAIN_BIN_DIR=/home/user/hermit/bin -DCMAKE_INSTALL_PREFIX=/home/user/hermit .. +$ make +$ make install +``` + +**Note:** If you use the cross compiler outside of this repository, the compiler uses per default the library operating systems located by the toolchain (e.g. `/opt/hermit/x86_64-hermit/lib/libhermit.a`). + +## Testing + +### As multi-kernel within a virtual machine + +```bash +$ cd build +$ make qemu +$ # or 'make qemu-dep' to build HermitCore dependencies before +``` + +Within the QEMU session you can start HermitCore application just the same as +traditional Linux programs: + +```bash +(QEMU) $ /hermit/x86_64-hermit/extra/tests/hello +smpboot: CPU 1 is now offline +Hello World!!! +argv[0] = /hermit/x86_64-hermit/extra/tests/hello +Receive signal with number 30 +Hostname: hermit.localdomain +x86: Booting SMP configuration: +smpboot: Booting Node 0 Processor 1 APIC 0x1 +``` + +Per default, the virtual machine has 10 cores, 2 NUMA nodes, and 8 GiB RAM. +Inside the VM runs a small Linux system, which already includes the patches for +HermitCore. Per NUMA node (= HermitCore isle) there is a directory called +`isleX` under `/sys/hermit` , where `X` represents the NUMA node ID. + +The demo applications are located in the directories +`/hermit/x86_64-hermit/extra/{tests,benchmarks}`. A HermitCore loader is already registered. +By starting a HermitCore application, a proxy will be executed on the Linux +system, while the HermitCore binary will be started on isle 0 with cpu 1. To +change the default behavior, the environment variable `HERMIT_ISLE` is used to +specify the (memory) location of the isle, while the environment variable +`HERMIT_CPUS` is used to specify the cores. + +For instance, `HERMIT_ISLE=1 HERMIT_CPUS="3-5" /hermit/x86_64-hermit/extra/tests/hello` starts +a HelloWorld demo on the HermitCore isle 1, which uses the cores 3 to 5. The +output messages are forwarded to the Linux proxy and printed on the Linux +system. + +HermitCore's kernel messages of `isleX` are available via `cat +/sys/hermit/isleX/log`. + +There is a virtual IP device for the communication between the HermitCore isles +and the Linux system (see output of `ifconfig`). Per default, the Linux system +has the IP address `192.168.28.1`. The HermitCore isles starts with the IP +address `192.168.28.2` for isle 0 and is increased by one for every isle. + +More HermitCore applications are available at `/hermit/usr/{tests,benchmarks}` +which is a shared directory between the host and QEMU. + + +### As classical standalone unikernel within a virtual machine + +HermitCore applications can be directly started as standalone kernel within a +virtual machine. In this case, +[iRCCE](http://www.lfbs.rwth-aachen.de/publications/files/iRCCE.pdf ) is not +supported. + +```bash +$ cd build +$ make install DESTDIR=~/hermit-build +$ cd ~/hermit-build/opt/hermit +$ # using QEMU +$ HERMIT_ISLE=qemu bin/proxy x86_64-hermit/extra/tests/hello +$ # using uHyve +$ HERMIT_ISLE=uhyve bin/proxy x86_64-hermit/extra/tests/hello +``` + +With `HERMIT_ISLE=qemu`, the application will be started within a QEMU VM. +Please note that the loader requires QEMU and uses per default *KVM*. +Furthermore, it expects that the executable is called `qemu-system-x86_64`. + +With `HERMIT_ISLE=hyve`, the application will be started within a thin +hypervisor powered by Linux's KVM API and therefore requires *KVM* support. +uHyve has a considerably smaller startup time than QEMU, but lacks some features +such as GDB debugging. + +In this context, the environment variable `HERMIT_CPUS` specifies the number of +cpus (and no longer a range of core ids). Furthermore, the variable `HERMIT_MEM` +defines the memory size of the virtual machine. The suffix of *M* or *G* can be +used to specify a value in megabytes or gigabytes respectively. Per default, the +loader initializes a system with one core and 2 GiB RAM. + +The virtual machine opens two TCP/IP ports. One is used for the communication +between HermitCore application and its proxy. The second port is used to create +a connection via telnet to QEMU's system monitor. With the environment variable +`HERMIT_PORT`, the default port (18766) can be changed for the communication +between the HermitCore application and its proxy. The connection to the system +monitor used automatically `HERMIT_PORT+1`, i.e., the default port is 18767. + +The following command starts the stream benchmark in a virtual machine, which +has 4 cores and 6GB memory. + +```bash +$ HERMIT_ISLE=qemu HERMIT_CPUS=4 HERMIT_MEM=6G bin/proxy x86_64-hermit/extra/benchmarks/stream +``` + + +### As multi-kernel on a real machine *Note*: to launch HermitCore applications, root privileges are required. -1. In principle you have to follow the tutorial above. - After the configuration, building of the cross-compilers and all example application (Step 5 in the [above tutorial](#building-and-testing-hermitcore-within-a-virtual-machine)), a modified Linux kernel has to be installed. - Please clone the repository with the [modified Linux kernel](https://github.com/RWTH-OS/linux). - Afterwards switch to the branch `hermit` for a relative new vanilla kernel or to `centos`, which is compatible to the current CentOS 7 kernel. - Configure the kernel with `make menuconfig` for your system. - Be sure, that the option `CONFIG_HERMIT_CORE` in `Processor type and features` is enabled. -2. Install the Linux kernel and its initial ramdisk on your system (see descriptions of your Linux distribution). - We recommend to disable Linux NO_HZ feature by setting the kernel parameter `nohz=off`. -3. After a reboot of the system, register the HermitCore loader at your system with following command: `echo ":hermit:M:7:\\x42::/path2proyxy/proxy:" > /proc/sys/fs/binfmt_misc/register`, in which `path2proxy` defines the path to the loader. - You find the loader `proxy` after building the HermiCore sources in the subdirectory `tools` of the directory, which contains this *README*. -4. The IP device between HermitCore and Linux currently does not support IPv6. - Consequently, disable IPv6 by adding following line to `/etc/sysctl.conf`: `net.ipv6.conf.mmnif.disable_ipv6 = 1`. -5. Per default, the IP device uses a static IP address range. - Linux has to use `162.168.28.1`, where HermitCore isles start with `192.168.28.2` (isle 0). - The network manager must be configured accordingly and therefore the file `/etc/sysconfig/network-scripts/ifcfg-mmnif` must be created with the following content: +A [modified Linux kernel](https://github.com/RWTH-OS/linux) has to be installed. +Afterwards switch to the branch `hermit` for a relative new vanilla kernel or to +`centos`, which is compatible to the current CentOS 7 kernel. Configure the +kernel with `make menuconfig` for your system. Be sure, that the option +`CONFIG_HERMIT_CORE` in `Processor type and features` is enabled. + +```bash +$ git clone https://github.com/RWTH-OS/linux +$ cd linux +$ # see comments above +$ git checkout hermit +$ make menuconfig +$ make +``` + +Install the Linux kernel and its initial ramdisk on your system (see +descriptions of your Linux distribution). We recommend to disable Linux NO_HZ +feature by setting the kernel parameter `nohz=off`. + +Install HermitCore to your system (by default to `/opt/hermit`): + +```bash +$ cd build +$ sudo make install +$ ls -l /opt/hermit +``` + +After a reboot of the system, register the HermitCore loader at your system with +following command: + +```bash +$ sudo -c sh 'echo ":hermit:M:7:\\x42::/opt/hermit/bin/proxy:" > /proc/sys/fs/binfmt_misc/register' +``` + +The IP device between HermitCore and Linux currently does not support IPv6. +Consequently, disable it (might be slightly different on your distribution): + +```bash +$ echo 'net.ipv6.conf.mmnif.disable_ipv6 = 1' | sudo tee /etc/sysctl.conf +``` + +Per default, the IP device uses a static IP address range. Linux has to use +`162.168.28.1`, where HermitCore isles start with `192.168.28.2` (isle 0). The +interface is `mmnif`. + +Please configure your network accordingly. For CentOS, you have to create the +file `/etc/sysconfig/network-scripts/ifcfg-mmnif`: ``` DEVICE=mmnif @@ -96,63 +296,76 @@ NETMASK=255.255.255.0 IPADDR=192.168.28.1 NM_CONTROLLED=yes ``` -Finally, follow the [above tutorial](#building-and-testing-hermitcore-within-a-virtual-machine) from Step 5. -The demo applications are located in their subdirectories `usr/{tests,benchmarks}`. -## Building and testing HermitCore as classical standalone unikernel +You can now start applications the same way as from within a virtual machine +(see description above). -HermitCore applications can be directly started as standalone kernel within a virtual machine. -In this case, [iRCCE](http://www.lfbs.rwth-aachen.de/publications/files/iRCCE.pdf) is not supported. -Please build HermitCore and register the loader in the same way as done for the multi-kernel version (see [Building and testing HermitCore on a real machine](#building-and-testing-hermitcore-on-a-real-machine)). -If the environment variable `HERMIT_ISLE` is set to `qemu`, the application will be started within a VM. -Please note that the loader requires QEMU and uses per default *KVM*. -Furthermore, it expects that the executable is called `qemu-system-x86_64`. -You can adapt the name by setting the environment variable `HERMIT_QEMU`. -In this context, the environment variable `HERMIT_CPUS` specifies the number of cpus (and no longer a range of core ids). -Furthermore, the variable `HERMIT_MEM` defines the memory size of the virtual machine. -The suffix of *M* or *G* can be used to specify a value in megabytes or gigabytes respectively. -Per default, the loader initializes a system with one core and 2 GiB RAM. +## Building your own HermitCore applications -The virtual machine opens two TCP/IP ports. -One is used for the communication between HermitCore application and its proxy. -The second port is used to create a connection via telnet to QEMU's system monitor. -With the environment variable `HERMIT_PORT`, the default port (18766) can be changed for the communication between the HermitCore application and its proxy. -The connection to the system monitor used automatically `HERMIT_PORT+1`, i.e., the default port is 18767. +You can take `usr/tests` as a starting point to build your own applications. All +that is required is that you include +`[...]/HermitCore/cmake/HermitCore-Application.cmake` in your application's +`CMakeLists.txt`. It doesn't have to reside inside the HermitCore repository. +Other than that, it should behave like normal CMake. + + +## Profiling + +We provide profiling support via the XRay profiler. See `usr/xray/README.md` for +more information on how to use it. + + +## Debugging + +If the application is started via `make qemu`, debugging via GDB is enabled by +default on port 1234. When run via proxy (`HERMIT_ISLE=qemu`), set +`HERMIT_DEBUG=1`. -The following example starts the stream benchmark in a virtual machine, which has 4 cores and 6GB memory. ``` -HERMIT_ISLE=qemu HERMIT_CPUS=4 HERMIT_MEM=6G usr/benchmarks/stream +$ gdb x86_64-hermit/extra/tests/hello +(gdb) target extended-remote :1234 +Remote debugging using :1234 +0xffffffff8100b542 in ?? () ``` -## Building HermitCore applications - -After successful building of HermitCore and its demo applications (see above), HermitCore’s cross toolchain (*gcc*, *g++*, *gfortran*, *gccgo*, *objdump*, etc.) is located at the subdiretory `usr/x86` of the directory, which contains this *README*. -To use these tools, add `usr/x86/bin` to your environment variable `PATH`. -As with any other cross toolchain, the tool names begin with the target architecture (*x86_64*) and the name of the operating system (*hermit*). -For instance, `x86_64-hermit-gcc` stands for the GNU C compiler, which is able to build HermitCore applications. - -All tools can be used as the well-known GNU tools. Only the Go compiler works different to the typical workflow. -Instead of building Go application like -``` -go build main.go -``` -you have to use the compiler as follows -``` -x86_64-hermit-gccgo -pthread -Wall -o main main.go -``` -For network support, you have to link the Go application with the flag `-lnetgo`. ## Tips -1. The configuration flag `--with-mtune=name` specifies the name of the target processor for which GCC should tune the performance of the code. - You can use any architecture name, which is supported by GCC. - For instance, `--with-mtune=native` optimzes the code for the host system. - Please note, if the applications is started within a VM, the hypervisor has to support the specified architecture name. - Per default the system will be accelerated by KVM and the host architecture will be used as target processor. -2. If Qemu is started by our proxy and the environment variable `HERMIT_KVM` is set to `0`, the virtual machine will be not accelerated by KVM. - In this case, the configuration flag `--with-mtune=name` should be avoided. - With the environment variable `HERMIT_APP_PORT`, an additional port can be open to establish an TCP/IP connection with your application. -3. By setting the environment variable `HERMIT_VERBOSE` to `1`, the proxy prints at termination the kernel log messages onto the screen. -4. If `HERMIT_DEBUG` is set to `1`, Qemu will establish an gdbserver, which will be listen port 1234. - Afterwards you are able debug HermitCore applications remotely. +### Optimization + +You can configure the `-mtune=name` compiler flag by adding `-DMTUNE=name` to +the `cmake` command when configuring the project. + +Please note, if the applications is started within a VM, the hypervisor has to +support the specified architecture name. + +If QEMU is started by our proxy and the environment variable `HERMIT_KVM` is set +to `0`, the virtual machine will be not accelerated by KVM. In this case, the +`-mtune` flag should be avoided. + +### TCP connections + +With the environment variable `HERMIT_APP_PORT`, an additional port can be open +to establish an TCP/IP connection with your application. + +### Dumping the kernel log + +By setting the environment variable `HERMIT_VERBOSE` to `1`, the proxy prints at +termination the kernel log messages onto the screen. + +### Network tracing + +By setting the environment variable `HERMIT_CAPTURE_NET` to `1` and +`HERMIT_ISLE` to `qemu`, QEMU captures the network traffic and creates the trace +file *qemu-vlan0.pcap*. For instance with [Wireshark](https://www.wireshark.org) +you are able to analyze the file. + +### Monitor + +If `HERMIT_MONITOR` is set to `1` and `HERMIT_ISLE` to `qemu`, QEMU establishes +a monitor which is available via telnet at port 18767. + +## Credits + +HermitCore's Emoji is provided free by [EmojiOne](https://www.gfxmag.com/crab-emoji-vector-icon/). diff --git a/arch/x86/CMakeLists.txt b/arch/x86/CMakeLists.txt new file mode 100644 index 000000000..cb88ba498 --- /dev/null +++ b/arch/x86/CMakeLists.txt @@ -0,0 +1,88 @@ +cmake_minimum_required(VERSION 3.7) +include(../../cmake/HermitCore.cmake) + +project(arch_x86_kernel C ASM_NASM) + +set_parent(X86_KERNEL_TARGET ${PROJECT_NAME}) +set_parent(X86_KERNEL_ASM_TARGET ${X86_KERNEL_TARGET}_asm) +set_parent(X86_KERNEL_C_TARGET ${X86_KERNEL_TARGET}_c) + +add_custom_target(${X86_KERNEL_TARGET}) + +# compiling kernel code here +add_definitions(-D__KERNEL__) + + +### ASM sources ### + +add_library(${X86_KERNEL_ASM_TARGET} OBJECT + kernel/entry.asm + libkern/string.asm) + +# HACK: We need to post-process the objects by running elfedit on them, but +# there is currently no way to get the list of objects out of CMake +# except for $, which only works with add_library() +# and add_executable(). +# So predict path to objects and add custom commands that depend on +# the asm target. +# +# Upstream issue: https://gitlab.kitware.com/cmake/cmake/issues/15226 +# +set(_BUILD_DIR "${CMAKE_CURRENT_BINARY_DIR}/${CMAKE_FILES_DIRECTORY}") +set(_BUILD_DIR "${_BUILD_DIR}/${X86_KERNEL_ASM_TARGET}.dir") + +get_target_property(ASM_SOURCES ${X86_KERNEL_ASM_TARGET} SOURCES) +foreach(SOURCE ${ASM_SOURCES}) + set(OBJECT "${SOURCE}.obj") + set(OBJECT_PATH "${_BUILD_DIR}/${OBJECT}") + + # slash (/) not allowed in target names + string(REPLACE "/" "-" + OBJECT_TARGET_NAME + "${OBJECT}") + + add_custom_target("${OBJECT_TARGET_NAME}" + COMMAND + ${CMAKE_ELFEDIT} --output-osabi HermitCore ${OBJECT_PATH} + DEPENDS + ${X86_KERNEL_ASM_TARGET}) + + # make main target depend on this + add_dependencies(${PROJECT_NAME} ${OBJECT_TARGET_NAME}) +endforeach() + + +### C sources ### + +file(GLOB KERNEL_SOURCES "kernel/*.c") +file(GLOB MM_SOURCES "mm/*.c") + +# add boot.h as source to mark dependency boot.asm -> boot.h -> apic.c +add_library(${X86_KERNEL_C_TARGET} OBJECT + ${KERNEL_SOURCES} ${MM_SOURCES} + ${GENERATED_CONFIG_DIR}/hermit/boot.h) + +target_include_directories(${X86_KERNEL_C_TARGET} BEFORE + PUBLIC ${HERMIT_KERNEL_INCLUDES} + PRIVATE ${GENERATED_CONFIG_DIR}) + +target_compile_options(${X86_KERNEL_C_TARGET} + PRIVATE ${HERMIT_KERNEL_FLAGS}) + +# assemble boot.asm and dump to C-array in boot.h +add_custom_command( + OUTPUT + ${GENERATED_CONFIG_DIR}/hermit/boot.h + DEPENDS + kernel/boot.asm + COMMAND + echo "static const uint8_t boot_code[] = {" > boot.h + COMMAND + nasm -f bin -o boot.bin ${CMAKE_CURRENT_LIST_DIR}/kernel/boot.asm + COMMAND + hexdump -v -e "7/1 \"0x%02X, \" 1/1 \" 0x%02X,\\n\"" boot.bin >> boot.h + COMMAND + echo "};" >> boot.h + WORKING_DIRECTORY + ${GENERATED_CONFIG_DIR}/hermit/ + VERBATIM USES_TERMINAL) diff --git a/arch/x86/include/asm/atomic32.h b/arch/x86/include/asm/atomic32.h index 25bb80e48..aa9a9cf28 100644 --- a/arch/x86/include/asm/atomic32.h +++ b/arch/x86/include/asm/atomic32.h @@ -52,8 +52,8 @@ typedef struct { volatile int32_t counter; } atomic_int32_t; * This function will atomically exchange the value of an atomic variable and * return its old value. Is used in locking-operations.\n * \n - * Intel manuals: If a memory operand is referenced, the processor's locking - * protocol is automatically implemented for the duration of the exchange + * Intel manuals: If a memory operand is referenced, the processor's locking + * protocol is automatically implemented for the duration of the exchange * operation, regardless of the presence or absence of the LOCK prefix. * * @param d Pointer to the atomic_int_32_t with the value you want to exchange @@ -79,7 +79,7 @@ inline static int32_t atomic_int32_test_and_set(atomic_int32_t* d, int32_t ret) inline static int32_t atomic_int32_add(atomic_int32_t *d, int32_t i) { int32_t res = i; - asm volatile(LOCK "xaddl %0, %1" : "=r"(i) : "m"(d->counter), "0"(i) : "memory", "cc"); + asm volatile(LOCK "xaddl %0, %1" : "+r"(i), "+m"(d->counter) : : "memory", "cc"); return res+i; } @@ -95,7 +95,7 @@ inline static int32_t atomic_int32_add(atomic_int32_t *d, int32_t i) */ inline static int32_t atomic_int32_sub(atomic_int32_t *d, int32_t i) { - return atomic_int32_add(d, -i); + return atomic_int32_add(d, -i); } /** @brief Atomic increment by one @@ -105,7 +105,9 @@ inline static int32_t atomic_int32_sub(atomic_int32_t *d, int32_t i) * @param d The atomic_int32_t var you want to increment */ inline static int32_t atomic_int32_inc(atomic_int32_t* d) { - return atomic_int32_add(d, 1); + int32_t res = 1; + asm volatile(LOCK "xaddl %0, %1" : "+r"(res), "+m"(d->counter) : : "memory", "cc"); + return ++res; } /** @brief Atomic decrement by one @@ -115,7 +117,9 @@ inline static int32_t atomic_int32_inc(atomic_int32_t* d) { * @param d The atomic_int32_t var you want to decrement */ inline static int32_t atomic_int32_dec(atomic_int32_t* d) { - return atomic_int32_add(d, -1); + int32_t res = -1; + asm volatile(LOCK "xaddl %0, %1" : "+r"(res), "+m"(d->counter) : : "memory", "cc"); + return --res; } /** @brief Read out an atomic_int32_t var @@ -132,7 +136,7 @@ inline static int32_t atomic_int32_read(atomic_int32_t *d) { /** @brief Set the value of an atomic_int32_t var * - * This function is for convenience: It sets the internal value of + * This function is for convenience: It sets the internal value of * an atomic_int32_t var for you. * * @param d Pointer to the atomic_int32_t var you want to set diff --git a/arch/x86/include/asm/atomic64.h b/arch/x86/include/asm/atomic64.h index 02bf98437..b741f0026 100644 --- a/arch/x86/include/asm/atomic64.h +++ b/arch/x86/include/asm/atomic64.h @@ -52,8 +52,8 @@ typedef struct { volatile int64_t counter; } atomic_int64_t; * This function will atomically exchange the value of an atomic variable and * return its old value. Is used in locking-operations.\n * \n - * Intel manuals: If a memory operand is referenced, the processor's locking - * protocol is automatically implemented for the duration of the exchange + * Intel manuals: If a memory operand is referenced, the processor's locking + * protocol is automatically implemented for the duration of the exchange * operation, regardless of the presence or absence of the LOCK prefix. * * @param d Pointer to the atomic_int_64_t with the value you want to exchange @@ -79,7 +79,7 @@ inline static int64_t atomic_int64_test_and_set(atomic_int64_t* d, int64_t ret) inline static int64_t atomic_int64_add(atomic_int64_t *d, int64_t i) { int64_t res = i; - asm volatile(LOCK "xaddq %0, %1" : "=r"(i) : "m"(d->counter), "0"(i) : "memory", "cc"); + asm volatile(LOCK "xaddq %0, %1" : "+r"(i), "+m"(d->counter) : : "memory", "cc"); return res+i; } @@ -95,7 +95,7 @@ inline static int64_t atomic_int64_add(atomic_int64_t *d, int64_t i) */ inline static int64_t atomic_int64_sub(atomic_int64_t *d, int64_t i) { - return atomic_int64_add(d, -i); + return atomic_int64_add(d, -i); } /** @brief Atomic increment by one @@ -105,7 +105,9 @@ inline static int64_t atomic_int64_sub(atomic_int64_t *d, int64_t i) * @param d The atomic_int64_t var you want to increment */ inline static int64_t atomic_int64_inc(atomic_int64_t* d) { - return atomic_int64_add(d, 1); + int64_t res = 1; + asm volatile(LOCK "xaddq %0, %1" : "+r"(res), "+m"(d->counter) : : "memory", "cc"); + return ++res; } /** @brief Atomic decrement by one @@ -115,7 +117,9 @@ inline static int64_t atomic_int64_inc(atomic_int64_t* d) { * @param d The atomic_int64_t var you want to decrement */ inline static int64_t atomic_int64_dec(atomic_int64_t* d) { - return atomic_int64_add(d, -1); + int64_t res = -1; + asm volatile(LOCK "xaddq %0, %1" : "+r"(res), "+m"(d->counter) : : "memory", "cc"); + return --res; } /** @brief Read out an atomic_int64_t var @@ -132,7 +136,7 @@ inline static int64_t atomic_int64_read(atomic_int64_t *d) { /** @brief Set the value of an atomic_int64_t var * - * This function is for convenience: It sets the internal value of + * This function is for convenience: It sets the internal value of * an atomic_int64_t var for you. * * @param d Pointer to the atomic_int64_t var you want to set diff --git a/arch/x86/include/asm/multiboot.h b/arch/x86/include/asm/multiboot.h index 5b8826a9a..1745f8db5 100644 --- a/arch/x86/include/asm/multiboot.h +++ b/arch/x86/include/asm/multiboot.h @@ -143,6 +143,8 @@ typedef struct multiboot_mod_list multiboot_module_t; /// Pointer to multiboot structure /// This pointer is declared at set by entry.asm -extern multiboot_info_t* mb_info; +extern const multiboot_info_t* const mb_info; +extern char* cmdline; +extern size_t cmdsize; #endif diff --git a/arch/x86/include/asm/page.h b/arch/x86/include/asm/page.h index 107476001..cac2e633b 100644 --- a/arch/x86/include/asm/page.h +++ b/arch/x86/include/asm/page.h @@ -36,19 +36,23 @@ #include #include +#include #ifndef __PAGE_H__ #define __PAGE_H__ /// Page offset bits #define PAGE_BITS 12 +#define PAGE_2M_BITS 21 /// The size of a single page in bytes #define PAGE_SIZE ( 1L << PAGE_BITS) /// Mask the page address without page map flags and XD flag #if 0 #define PAGE_MASK ((~0L) << PAGE_BITS) +#define PAGE_2M_MASK (~0L) << PAGE_2M_BITS) #else #define PAGE_MASK (((~0L) << PAGE_BITS) & ~PG_XD) +#define PAGE_2M_MASK (((~0L) << PAGE_2M_BITS) & ~PG_XD) #endif #if 0 @@ -141,6 +145,8 @@ static inline size_t sign_extend(ssize_t addr, int bits) /// Disable execution for this page #define PG_XD (1L << 63) +#define PG_NX (has_nx() ? PG_XD : 0) + /** @brief Converts a virtual address to a physical * * A non mapped virtual address causes a pagefault! diff --git a/arch/x86/include/asm/pci.h b/arch/x86/include/asm/pci.h index 26d4b0860..211aa03bd 100644 --- a/arch/x86/include/asm/pci.h +++ b/arch/x86/include/asm/pci.h @@ -26,7 +26,7 @@ */ -/** +/** * @author Stefan Lankes * @file arch/x86/include/asm/pci.h * @brief functions related to PCI initialization and information @@ -48,6 +48,8 @@ typedef struct { uint32_t irq; } pci_info_t; +#define PCI_IGNORE_SUBID (0) + /** @brief Initialize the PCI environment */ int pci_init(void); @@ -55,15 +57,16 @@ int pci_init(void); /** @brief Determine the IObase address and the interrupt number of a specific device * * @param vendor_id The device's vendor ID - * @param device_id the device's ID + * @param device_id The device's ID + * @param subystem_id The subsystem DI * @param info Pointer to the record pci_info_t where among other the IObase address will be stored * @param enable_bus_master If true, the bus mastering will be enabled. * - * @return + * @return * - 0 on success * - -EINVAL (-22) on failure */ -int pci_get_device_info(uint32_t vendor_id, uint32_t device_id, pci_info_t* info, int8_t enble_bus_master); +int pci_get_device_info(uint32_t vendor_id, uint32_t device_id, uint32_t subsystem_id, pci_info_t* info, int8_t enble_bus_master); /** @brief Print information of existing pci adapters * diff --git a/arch/x86/include/asm/processor.h b/arch/x86/include/asm/processor.h index b8d672cc7..24ae11b78 100644 --- a/arch/x86/include/asm/processor.h +++ b/arch/x86/include/asm/processor.h @@ -41,6 +41,7 @@ #include #include #include +#include #ifdef __cplusplus extern "C" { @@ -89,6 +90,7 @@ extern "C" { // feature list 0x00000007:0 #define CPU_FEATURE_FSGSBASE (1 << 0) #define CPU_FEATURE_TSC_ADJUST (1 << 1) +#define CPU_FEATURE_SGX (1 << 2) #define CPU_FEATURE_BMI1 (1 << 3) #define CPU_FEATURE_HLE (1 << 4) #define CPU_FEATURE_AVX2 (1 << 5) @@ -110,6 +112,8 @@ extern "C" { #define CPU_FEATURE_AVX512ER (1 << 27) #define CPU_FEATURE_AVX512CD (1 << 28) #define CPU_FEATURE_SHA_NI (1 << 29) +#define CPU_FEATURE_AVX512BW (1 << 30) +#define CPU_FEATURE_AVX512VL (1 <<31) // feature list 0x00000006 #define CPU_FEATURE_IDA (1 << 0) @@ -407,6 +411,10 @@ inline static uint32_t has_fsgsbase(void) { return (cpu_info.feature4 & CPU_FEATURE_FSGSBASE); } +inline static uint32_t has_sgx(void) { + return (cpu_info.feature4 & CPU_FEATURE_SGX); +} + inline static uint32_t has_avx2(void) { return (cpu_info.feature4 & CPU_FEATURE_AVX2); } @@ -431,6 +439,14 @@ inline static uint32_t has_rtm(void) { return (cpu_info.feature4 & CPU_FEATURE_RTM); } +inline static uint32_t has_clflushopt(void) { + return (cpu_info.feature4 & CPU_FEATURE_CLFLUSHOPT); +} + +inline static uint32_t has_clwb(void) { + return (cpu_info.feature4 & CPU_FEATURE_CLWB); +} + inline static uint32_t has_avx512f(void) { return (cpu_info.feature4 & CPU_FEATURE_AVX512F); } @@ -447,6 +463,14 @@ inline static uint32_t has_avx512cd(void) { return (cpu_info.feature4 & CPU_FEATURE_AVX512CD); } +inline static uint32_t has_avx512bw(void) { + return (cpu_info.feature4 & CPU_FEATURE_AVX512BW); +} + +inline static uint32_t has_avx512vl(void) { + return (cpu_info.feature4 & CPU_FEATURE_AVX512VL); +} + inline static uint32_t has_rdtscp(void) { return (cpu_info.feature3 & CPU_FEATURE_RDTSCP); } @@ -722,6 +746,16 @@ static inline void clflush(volatile void *addr) asm volatile("clflush %0" : "+m" (*(volatile char *)addr)); } +static inline void clwb(volatile void *addr) +{ + asm volatile("clwb %0" : "+m" (*(volatile char *)addr)); +} + +static inline void clflushopt(volatile void *addr) +{ + asm volatile("clflushopt %0" : "+m" (*(volatile char *)addr)); +} + #if 0 // the old way to serialize the store and load operations static inline void mb(void) { asm volatile ("lock; addl $0,0(%%esp)" ::: "memory", "cc"); } @@ -791,6 +825,66 @@ static inline uint64_t read_rflags(void) return result; } +/* For KVM hypercalls, a three-byte sequence of either the vmcall or the vmmcall + * instruction. The hypervisor may replace it with something else but only the + * instructions are guaranteed to be supported. + * + * Up to four arguments may be passed in rbx, rcx, rdx, and rsi respectively. + * The hypercall number should be placed in rax and the return value will be + * placed in rax. No other registers will be clobbered unless explicitly + * noted by the particular hypercall. + */ + +inline static size_t vmcall0(int nr) +{ + size_t res; + + asm volatile ("vmcall" : "=a" (res): "a" (nr) + : "memory"); + + return res; +} + +inline static size_t vmcall1(int nr, size_t arg0) +{ + size_t res; + + asm volatile ("vmcall" : "=a" (res): "a" (nr), "b"(arg0) + : "memory"); + + return res; +} + +inline static size_t vmcall2(int nr, size_t arg0, size_t arg1) +{ + size_t res; + + asm volatile ("vmcall" : "=a" (res): "a" (nr), "b"(arg0), "c"(arg1) + : "memory"); + + return res; +} + +inline static size_t vmcall3(int nr, size_t arg0, size_t arg1, size_t arg2) +{ + size_t res; + + asm volatile ("vmcall" : "=a" (res): "a" (nr), "b"(arg0), "c"(arg1), "d"(arg2) + : "memory"); + + return res; +} + +inline static size_t vmcall4(int nr, size_t arg0, size_t arg1, size_t arg2, size_t arg3) +{ + size_t res; + + asm volatile ("vmcall" : "=a" (res): "a" (nr), "b"(arg0), "c"(arg1), "d"(arg2), "S"(arg3) + : "memory"); + + return res; +} + /** @brief search the first most significant bit * * @param i source operand @@ -894,7 +988,7 @@ inline static int system_calibration(void) size_t cr0; apic_init(); - if (is_single_kernel()) + if (is_single_kernel() && !is_uhyve()) pci_init(); register_task(); diff --git a/arch/x86/include/asm/stddef.h b/arch/x86/include/asm/stddef.h index 7678456f0..42d68ed0a 100644 --- a/arch/x86/include/asm/stddef.h +++ b/arch/x86/include/asm/stddef.h @@ -205,6 +205,7 @@ typedef struct { size_t ss_size; /* Stack size. */ } stack_t; +const int32_t is_uhyve(void); const int32_t is_single_kernel(void); #ifdef __cplusplus diff --git a/arch/x86/include/asm/string.h b/arch/x86/include/asm/string.h index d17c3d7a0..1fb2e52d8 100644 --- a/arch/x86/include/asm/string.h +++ b/arch/x86/include/asm/string.h @@ -26,7 +26,7 @@ extern "C" { #endif -#ifdef HAVE_ARCH_MEMCPY +#if HAVE_ARCH_MEMCPY /** @brief Copy a byte range from source to dest * * @param dest Destination address @@ -52,7 +52,7 @@ inline static void *memcpy(void* dest, const void *src, size_t count) } #endif -#ifdef HAVE_ARCH_MEMSET +#if HAVE_ARCH_MEMSET /** @brief Repeated write of a value to a whole range of bytes * * @param dest Destination address @@ -84,7 +84,7 @@ inline static void *memset(void* dest, int val, size_t count) } #endif -#ifdef HAVE_ARCH_STRLEN +#if HAVE_ARCH_STRLEN /** @brief Standard string length * * This function computed the length of the given null terminated string @@ -111,7 +111,7 @@ inline static size_t strlen(const char* str) } #endif -#ifdef HAVE_ARCH_STRNCPY +#if HAVE_ARCH_STRNCPY /** @brief Copy string with maximum of n byte length * * @param dest Destination string pointer @@ -121,7 +121,7 @@ inline static size_t strlen(const char* str) char* strncpy(char* dest, const char* src, size_t n); #endif -#ifdef HAVE_ARCH_STRCPY +#if HAVE_ARCH_STRCPY /** @brief Copy string * * Note that there is another safer variant of this function: strncpy.\n diff --git a/arch/x86/include/asm/tasks.h b/arch/x86/include/asm/tasks.h index 2d8995fcc..7e128843b 100644 --- a/arch/x86/include/asm/tasks.h +++ b/arch/x86/include/asm/tasks.h @@ -30,7 +30,7 @@ * @file arch/x86/include/asm/tasks.h * @brief Task related structure definitions * - * This file contains the task_t structure definition + * This file contains the task_t structure definition * and task state define constants */ @@ -55,7 +55,7 @@ void switch_context(size_t** stack); * @param task Pointer to the task structure * @param ep The entry point for code execution * @param arg Arguments list pointer for the task's stack - * @param core_id Id of the core, which is firstly used by the task + * @param core_id Id of the core, which is firstly used by the task * @return * - 0 on success * - -EINVAL (-22) on failure @@ -77,6 +77,13 @@ static inline int jump_to_user_code(size_t ep, size_t stack) return 0; } +/** @brief Architecture dependent initialize routine + */ +static inline void arch_init_task(task_t* task) +{ + set_tss((size_t) task->stack + KERNEL_STACK_SIZE - 0x10, (size_t) task->ist_addr + KERNEL_STACK_SIZE - 0x10); +} + #ifdef __cplusplus } #endif diff --git a/arch/x86/loader/include/vga.h b/arch/x86/include/asm/time.h similarity index 74% rename from arch/x86/loader/include/vga.h rename to arch/x86/include/asm/time.h index ff85ff996..f59658cfb 100644 --- a/arch/x86/loader/include/vga.h +++ b/arch/x86/include/asm/time.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2010, Stefan Lankes, RWTH Aachen University + * Copyright (c) 2017, Stefan Lankes, RWTH Aachen University * All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -25,34 +25,26 @@ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -#ifndef __VGA_H__ -#define __VGA_H__ +/** + * @author Stefan Lankes + * @file arch/x86/include/asm/string.h + * @brief Time related functions + */ -#include +#ifndef __ARCH_TIME_H__ +#define __ARCH_TIME_H__ + +#include #ifdef __cplusplus extern "C" { #endif -/** @brief Initialize VGA output and clear the screen */ -void vga_init(void); +static inline int timer_deadline(uint32_t t) { return apic_timer_deadline(t); } -/** @brief Simple string output on screen. - * - * If you want a new line you will have to "\\n". - * - * @return Length of output in bytes - */ -int vga_puts(const char *text); +static inline void timer_disable(void) { apic_disable_timer(); } -/** @brief Simple character output on screen. - * - * @return The original input character casted to int - */ -int vga_putchar(unsigned char c); - -/** @brief Clear the screen */ -void vga_cls(void); +static inline int timer_is_running(void) { return apic_timer_is_running(); } #ifdef __cplusplus } diff --git a/arch/x86/include/asm/uart.h b/arch/x86/include/asm/uart.h index 3514c30a2..f849fabeb 100644 --- a/arch/x86/include/asm/uart.h +++ b/arch/x86/include/asm/uart.h @@ -40,12 +40,6 @@ extern "C" { */ int uart_init(void); -/** @brief Initialize UART output without a device check - * - * @return Returns 0 on success - */ -int uart_early_init(char*); - /** @brief Simple string output on a serial device. * * If you want a new line you will have to "\\n". diff --git a/arch/x86/include/asm/vga.h b/arch/x86/include/asm/uhyve.h similarity index 75% rename from arch/x86/include/asm/vga.h rename to arch/x86/include/asm/uhyve.h index d531a8863..745ef3c32 100644 --- a/arch/x86/include/asm/vga.h +++ b/arch/x86/include/asm/uhyve.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2010, Stefan Lankes, RWTH Aachen University + * Copyright (c) 2017, Stefan Lankes, RWTH Aachen University * All rights reserved. * * Redistribution and use in source and binary forms, with or without @@ -25,34 +25,26 @@ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. */ -#ifndef __VGA_H__ -#define __VGA_H__ +/** + * @author Stefan Lankes + * @file arch/x86/include/asm/uhyve.h + * @brief interface to our machine monitor + */ + +#ifndef __ARCH_UHYVE_H__ +#define __ARCH_UHYVE_H__ #include +#include #ifdef __cplusplus extern "C" { #endif -/** @brief Initialize VGA output and clear the screen */ -void vga_init(void); - -/** @brief Simple string output on screen. - * - * If you want a new line you will have to "\\n". - * - * @return Length of output in bytes - */ -int vga_puts(const char *text); - -/** @brief Simple character output on screen. - * - * @return The original input character casted to int - */ -int vga_putchar(unsigned char c); - -/** @brief Clear the screen */ -void vga_cls(void); +inline static void uhyve_send(unsigned short _port, unsigned int _data) +{ + outportl(_port, _data); +} #ifdef __cplusplus } diff --git a/arch/x86/kernel/Makefile b/arch/x86/kernel/Makefile deleted file mode 100644 index df969fd2f..000000000 --- a/arch/x86/kernel/Makefile +++ /dev/null @@ -1,5 +0,0 @@ -C_source := irq.c idt.c isrs.c gdt.c processor.c timer.c tasks.c apic.c pci.c vga.c uart.c syscall.c -ASM_source := entry.asm string.asm -MODULE := arch_x86_kernel - -include $(TOPDIR)/Makefile.inc diff --git a/arch/x86/kernel/apic.c b/arch/x86/kernel/apic.c index 3319b2c70..dc401bcc4 100644 --- a/arch/x86/kernel/apic.c +++ b/arch/x86/kernel/apic.c @@ -42,7 +42,7 @@ #include #include #include -#include "boot.h" +#include /* * Note that linker symbols are not variables, they have no memory allocated for @@ -408,6 +408,7 @@ static apic_mp_t* search_mptable(size_t base, size_t limit) { return NULL; } +#if 0 static size_t search_ebda(void) { size_t ptr=PAGE_CEIL(0x400), vptr=0xF0000; size_t flags = PG_GLOBAL | PG_RW | PG_PCD; @@ -421,12 +422,13 @@ static size_t search_ebda(void) { uint16_t addr = *((uint16_t*) (vptr+0x40E)); LOG_INFO("Found EBDA at 0x%x!\n", (uint32_t)addr); - + // unmap page via mapping a zero page page_unmap(vptr, 1); return (size_t) addr; } +#endif static int lapic_reset(void) { @@ -454,8 +456,8 @@ static int lapic_reset(void) lapic_write(APIC_LVT_TSR, 0x10000); // disable thermal sensor interrupt if (max_lvt >= 5) lapic_write(APIC_LVT_PMC, 0x10000); // disable performance counter interrupt - lapic_write(APIC_LINT0, 0x7C); // connect LINT0 to idt entry 124 - lapic_write(APIC_LINT1, 0x7D); // connect LINT1 to idt entry 125 + lapic_write(APIC_LINT0, 0x00010000); // disable LINT0 + lapic_write(APIC_LINT1, 0x00010000); // disable LINT1 lapic_write(APIC_LVT_ER, 0x7E); // connect error to idt entry 126 return 0; @@ -479,7 +481,7 @@ static int wakeup_ap(uint32_t start_eip, uint32_t id) reset_vector = (char*) vma_alloc(PAGE_SIZE, VMA_READ|VMA_WRITE); page_map((size_t)reset_vector, 0x00, 1, PG_RW|PG_GLOBAL|PG_PCD); reset_vector += 0x467; // add base address of the reset vector - LOG_INFO("Map reset vector to %p\n", reset_vector); + LOG_DEBUG("Map reset vector to %p\n", reset_vector); } *((volatile unsigned short *) (reset_vector+2)) = start_eip >> 4; @@ -546,7 +548,7 @@ static int wakeup_ap(uint32_t start_eip, uint32_t id) set_ipi_dest(id); lapic_write(APIC_ICR1, APIC_DM_STARTUP|(start_eip >> 12)); if (traditional_delay) - udelay(200); + udelay(200); else udelay(10); @@ -568,7 +570,7 @@ int smp_init(void) if (ncores <= 1) return -EINVAL; - LOG_INFO("CR0 of core %u: 0x%x\n", apic_cpu_id(), read_cr0()); + LOG_DEBUG("CR0 of core %u: 0x%x\n", apic_cpu_id(), read_cr0()); /* * dirty hack: Reserve memory for the bootup code. @@ -609,7 +611,7 @@ int smp_init(void) } } - LOG_INFO("%d cores online\n", atomic_int32_read(&cpu_online)); + LOG_DEBUG("%d cores online\n", atomic_int32_read(&cpu_online)); return 0; } @@ -664,7 +666,8 @@ int apic_calibration(void) apic_initialized = 1; atomic_int32_inc(&cpu_online); - if(is_single_kernel()) { + if (is_single_kernel()) { + LOG_INFO("Disable PIC\n"); // Now, HermitCore is able to use the APIC => Therefore, we disable the PIC outportb(0xA1, 0xFF); outportb(0x21, 0xFF); @@ -681,6 +684,7 @@ int apic_calibration(void) } // now, we don't longer need the IOAPIC timer and turn it off + LOG_INFO("Disable IOAPIC timer\n"); ioapic_intoff(2, apic_processors[boot_processor]->id); } @@ -694,7 +698,7 @@ int apic_calibration(void) static int apic_probe(void) { - size_t addr, ebda; + size_t addr; uint32_t i, j, count; int isa_bus = -1; size_t flags = PG_GLOBAL | PG_RW | PG_PCD; @@ -703,10 +707,12 @@ static int apic_probe(void) if (has_nx()) flags |= PG_XD; - ebda = search_ebda(); +#if 0 + size_t ebda = search_ebda(); apic_mp = search_mptable(ebda, ebda+0x400); if (apic_mp) goto found_mp; +#endif apic_mp = search_mptable(0xF0000, 0x100000); if (apic_mp) @@ -717,7 +723,7 @@ static int apic_probe(void) found_mp: if (!apic_mp) { - LOG_ERROR("Didn't find MP config table\n"); + LOG_INFO("Didn't find MP config table\n"); goto no_mp; } @@ -887,7 +893,8 @@ no_mp: boot_processor = 0; apic_mp = NULL; apic_config = NULL; - ncores = 1; + if (!is_uhyve()) + ncores = 1; goto check_lapic; } @@ -903,7 +910,7 @@ int smp_start(void) // reset APIC and set id lapic_reset(); - LOG_INFO("Processor %d (local id %d) is entering its idle task\n", apic_cpu_id(), atomic_int32_read(¤t_boot_id)); + LOG_DEBUG("Processor %d (local id %d) is entering its idle task\n", apic_cpu_id(), atomic_int32_read(¤t_boot_id)); // use the same gdt like the boot processors gdt_flush(); @@ -911,12 +918,6 @@ int smp_start(void) // install IDT idt_install(); - /* - * we turned on paging - * => now, we are able to register our task - */ - register_task(); - // enable additional cpu features cpu_detection(); @@ -931,6 +932,12 @@ int smp_start(void) set_idle_task(); + /* + * TSS is set, pagining is enabled + * => now, we are able to register our task + */ + register_task(); + irq_enable(); atomic_int32_inc(&cpu_online); @@ -1077,19 +1084,16 @@ void shutdown_system(void) } } -volatile uint32_t go_down = 0; - -static void apic_shutdown(struct state * s) +static void apic_shutdown(struct state* s) { go_down = 1; LOG_DEBUG("Receive shutdown interrupt\n"); } -static void apic_lint0(struct state * s) +static void apic_wakeup(struct state* s) { - // Currently nothing to do - LOG_INFO("Receive LINT0 interrupt\n"); + LOG_DEBUG("Receive wakeup interrupt\n"); } int apic_init(void) @@ -1101,12 +1105,12 @@ int apic_init(void) return ret; // set APIC error handler + irq_install_handler(121, apic_wakeup); irq_install_handler(126, apic_err_handler); #if MAX_CORES > 1 irq_install_handler(80+32, apic_tlb_handler); #endif irq_install_handler(81+32, apic_shutdown); - irq_install_handler(124, apic_lint0); if (apic_processors[boot_processor]) LOG_INFO("Boot processor %u (ID %u)\n", boot_processor, apic_processors[boot_processor]->id); else diff --git a/arch/x86/kernel/entry.asm b/arch/x86/kernel/entry.asm index a8b38fd62..e68e2d481 100644 --- a/arch/x86/kernel/entry.asm +++ b/arch/x86/kernel/entry.asm @@ -1,4 +1,3 @@ - ; Copyright (c) 2010-2015, Stefan Lankes, RWTH Aachen University ; All rights reserved. ; @@ -29,12 +28,11 @@ ; perhaps setting up the GDT and segments. Please note that interrupts ; are disabled at this point: More on interrupts later! -%include "config.inc" +%include "hermit/config.asm" [BITS 64] extern kernel_start ; defined in linker script -extern kernel_end MSR_FS_BASE equ 0xc0000100 MSR_GS_BASE equ 0xc0000101 @@ -69,6 +67,11 @@ align 4 global mb_info global hbmem_base global hbmem_size + global uhyve + global image_size + global uartport + global cmdline + global cmdsize base dq 0 limit dq 0 cpu_freq dd 0 @@ -92,6 +95,10 @@ align 4 mb_info dq 0 hbmem_base dq 0 hbmem_size dq 0 + uhyve dd 0 + uartport dq 0 + cmdline dq 0 + cmdsize dq 0 ; Bootstrap page tables are used during the initialization. align 4096 @@ -113,9 +120,6 @@ boot_pgt: SECTION .ktext align 4 start64: - ; store pointer to the multiboot information - mov [mb_info], QWORD rdx - ; reset registers to kill any stale realmode selectors xor eax, eax mov ds, eax @@ -133,10 +137,8 @@ start64: cmp eax, 0 jne Lno_pml4_init - ; determine full image size - mov rax, kernel_end - sub rax, kernel_start - mov QWORD [image_size], rax + ; store pointer to the multiboot information + mov [mb_info], QWORD rdx ; relocate page tables mov rdi, boot_pml4 @@ -172,16 +174,6 @@ start64: add rax, [base] mov QWORD [rdi+511*8], rax -%ifdef CONFIG_VGA - ; map vga 1:1 - mov rax, VIDEO_MEM_ADDR ; map vga - and rax, ~0xFFF ; page align lower half - mov rdi, rax - shr rdi, 9 ; (edi >> 12) * 8 (index for boot_pgt) - add rdi, boot_pgt - or rax, 0x113 ; set present, global, writable and cache disable bits - mov QWORD [rdi], rax -%endif ; map multiboot info mov rax, QWORD [mb_info] and rax, ~0xFFF ; page align lower half @@ -190,7 +182,7 @@ start64: mov rdi, rax shr rdi, 9 ; (edi >> 12) * 8 (index for boot_pgt) add rdi, boot_pgt - or rax, 0x103 ; set present, global and writable bits + or rax, 0x23 ; set present, accessed and writable bits mov QWORD [rdi], rax Lno_mbinfo: ; remap kernel @@ -198,13 +190,18 @@ Lno_mbinfo: shr rdi, 18 ; (edi >> 21) * 8 (index for boot_pgd) add rdi, boot_pgd mov rax, [base] - or rax, 0x83 ; PG_GLOBAL isn't required because HermitCore is a single-address space OS + or rax, 0xA3 ; PG_GLOBAL isn't required because HermitCore is a single-address space OS xor rcx, rcx + mov rsi, 510*0x200000 + sub rsi, kernel_start Lremap: mov QWORD [rdi], rax add rax, 0x200000 add rcx, 0x200000 add rdi, 8 + ; note: the whole code segement muust fit in the first pgd + cmp rcx, rsi + jnb Lno_pml4_init cmp rcx, QWORD [image_size] jb Lremap @@ -609,7 +606,7 @@ common_switch: call get_current_stack ; get new rsp mov rsp, rax -%ifdef SAVE_FPU +%ifidn SAVE_FPU,ON ; set task switched flag mov rax, cr0 or rax, 8 @@ -666,6 +663,12 @@ Lgo3: add rsp, 16 iretq +global is_uhyve +align 64 +is_uhyve: + mov eax, DWORD [uhyve] + ret + global is_single_kernel align 64 is_single_kernel: diff --git a/arch/x86/kernel/isrs.c b/arch/x86/kernel/isrs.c index f5e1c32ee..f79cdbd0b 100644 --- a/arch/x86/kernel/isrs.c +++ b/arch/x86/kernel/isrs.c @@ -82,10 +82,11 @@ extern void isr29(void); extern void isr30(void); extern void isr31(void); -static void fault_handler(struct state *s); -extern void fpu_handler(struct state *s); +static void arch_fault_handler(struct state *s); +static void arch_fpu_handler(struct state *s); +extern void fpu_handler(void); -/* +/* * This is a very repetitive function... it's not hard, it's * just annoying. As you can see, we set the first 32 entries * in the IDT to the first 32 ISRs. We can't use a for loop @@ -94,7 +95,7 @@ extern void fpu_handler(struct state *s); * flags to 0x8E. This means that the entry is present, is * running in ring 0 (kernel level), and has the lower 5 bits * set to the required '14', which is represented by 'E' in - * hex. + * hex. */ void isrs_install(void) { @@ -174,11 +175,11 @@ void isrs_install(void) // install the default handler for(i=0; i<32; i++) - irq_install_handler(i, fault_handler); + irq_install_handler(i, arch_fault_handler); // set hanlder for fpu exceptions irq_uninstall_handler(7); - irq_install_handler(7, fpu_handler); + irq_install_handler(7, arch_fpu_handler); } /** @brief Exception messages @@ -186,35 +187,45 @@ void isrs_install(void) * This is a simple string array. It contains the message that * corresponds to each and every exception. We get the correct * message by accessing it like this: - * exception_message[interrupt_number] + * exception_message[interrupt_number] */ -static const char *exception_messages[] = { - "Division By Zero", "Debug", "Non Maskable Interrupt", +static const char *exception_messages[] = { + "Division By Zero", "Debug", "Non Maskable Interrupt", "Breakpoint", "Into Detected Overflow", "Out of Bounds", "Invalid Opcode", - "No Coprocessor", "Double Fault", "Coprocessor Segment Overrun", "Bad TSS", - "Segment Not Present", "Stack Fault", "General Protection Fault", "Page Fault", - "Unknown Interrupt", "Coprocessor Fault", "Alignment Check", "Machine Check", + "No Coprocessor", "Double Fault", "Coprocessor Segment Overrun", "Bad TSS", + "Segment Not Present", "Stack Fault", "General Protection Fault", "Page Fault", + "Unknown Interrupt", "Coprocessor Fault", "Alignment Check", "Machine Check", "SIMD Floating-Point", "Virtualization", "Reserved", "Reserved", "Reserved", "Reserved", "Reserved", "Reserved", "Reserved", "Reserved", "Reserved", "Reserved", "Reserved" }; -/* +/* interrupt handler to save / restore the FPU context */ +static void arch_fpu_handler(struct state *s) +{ + (void) s; + + clts(); // clear the TS flag of cr0 + + fpu_handler(); +} + +/* * All of our Exception handling Interrupt Service Routines will * point to this function. This will tell us what exception has - * occured! Right now, we simply abort the current task. + * occured! Right now, we simply abort the current task. * All ISRs disable interrupts while they are being * serviced as a 'locking' mechanism to prevent an IRQ from * happening and messing up kernel data structures */ -static void fault_handler(struct state *s) +static void arch_fault_handler(struct state *s) { - + if (s->int_no < 32) LOG_INFO("%s", exception_messages[s->int_no]); else LOG_WARNING("Unknown exception %d", s->int_no); - LOG_ERROR(" Exception (%d) on core %d at %#x:%#lx, fs = %#lx, gs = %#lx, error code = 0x%#lx, task id = %u, rflags = %#x\n", + LOG_ERROR(" Exception (%d) on core %d at %#x:%#lx, fs = %#lx, gs = %#lx, error code = %#lx, task id = %u, rflags = %#x\n", s->int_no, CORE_ID, s->cs, s->rip, s->fs, s->gs, s->error, per_core(current_task)->id, s->rflags); LOG_ERROR("rax %#lx, rbx %#lx, rcx %#lx, rdx %#lx, rbp, %#lx, rsp %#lx rdi %#lx, rsi %#lx, r8 %#lx, r9 %#lx, r10 %#lx, r11 %#lx, r12 %#lx, r13 %#lx, r14 %#lx, r15 %#lx\n", s->rax, s->rbx, s->rcx, s->rdx, s->rbp, s->rsp, s->rdi, s->rsi, s->r8, s->r9, s->r10, s->r11, s->r12, s->r13, s->r14, s->r15); diff --git a/arch/x86/kernel/pci.c b/arch/x86/kernel/pci.c index 79991b69f..d35e919fc 100644 --- a/arch/x86/kernel/pci.c +++ b/arch/x86/kernel/pci.c @@ -45,6 +45,7 @@ #define PCI_CFRV 0x08 /* Configuration Revision */ #define PCI_CFLT 0x0c /* Configuration Latency Timer */ #define PCI_CBIO 0x10 /* Configuration Base IO Address */ +#define PCI_CSID 0x2C /* Configuration Subsystem Id & Subsystem Vendor Id */ #define PCI_CFIT 0x3c /* Configuration Interrupt */ #define PCI_CFDA 0x40 /* Configuration Driver Area */ @@ -101,6 +102,11 @@ static uint32_t pci_conf_read(uint32_t bus, uint32_t slot, uint32_t off) return data; } +static inline uint32_t pci_subid(uint32_t bus, uint32_t slot) +{ + return pci_conf_read(bus, slot, PCI_CSID); +} + static inline uint32_t pci_what_irq(uint32_t bus, uint32_t slot) { return pci_conf_read(bus, slot, PCI_CFIT) & 0xFF; @@ -139,29 +145,30 @@ static inline uint32_t pci_what_size(uint32_t bus, uint32_t slot, uint32_t nr) int pci_init(void) { uint32_t slot, bus; - + for (bus = 0; bus < MAX_BUS; bus++) for (slot = 0; slot < MAX_SLOTS; slot++) adapters[bus][slot] = pci_conf_read(bus, slot, PCI_CFID); - + return 0; } -int pci_get_device_info(uint32_t vendor_id, uint32_t device_id, pci_info_t* info, int8_t bus_master) +int pci_get_device_info(uint32_t vendor_id, uint32_t device_id, uint32_t subsystem_id, pci_info_t* info, int8_t bus_master) { uint32_t slot, bus, i; if (!info) return -EINVAL; - if (!mechanism) + if (!mechanism && !is_uhyve()) pci_init(); for (bus = 0; bus < MAX_BUS; bus++) { for (slot = 0; slot < MAX_SLOTS; slot++) { if (adapters[bus][slot] != -1) { - if (((adapters[bus][slot] & 0xffff) == vendor_id) && - (((adapters[bus][slot] & 0xffff0000) >> 16) == device_id)) { + if (((adapters[bus][slot] & 0xffff) == vendor_id) && + (((adapters[bus][slot] & 0xffff0000) >> 16) == device_id) && + (((pci_subid(bus, slot) >> 16) & subsystem_id) == subsystem_id)) { for(i=0; i<6; i++) { info->base[i] = pci_what_iobase(bus, slot, i); info->size[i] = (info->base[i]) ? pci_what_size(bus, slot, i) : 0; @@ -195,7 +202,7 @@ int print_pci_adapters(void) if (adapters[bus][slot] != -1) { counter++; LOG_INFO("%d) Vendor ID: 0x%x Device Id: 0x%x\n", - counter, adapters[bus][slot] & 0xffff, + counter, adapters[bus][slot] & 0xffff, (adapters[bus][slot] & 0xffff0000) >> 16); #ifdef WITH_PCI_IDS diff --git a/arch/x86/kernel/processor.c b/arch/x86/kernel/processor.c index ac37161fd..55f6dbdc1 100644 --- a/arch/x86/kernel/processor.c +++ b/arch/x86/kernel/processor.c @@ -49,6 +49,8 @@ extern atomic_int32_t current_boot_id; extern void isrsyscall(void); cpu_info_t cpu_info = { 0, 0, 0, 0, 0}; +static char cpu_vendor[13] = {[0 ... 12] = 0}; +static char cpu_brand[4*3*sizeof(uint32_t)+1] = {[0 ... 4*3*sizeof(uint32_t)] = 0}; extern uint32_t cpu_freq; static void default_save_fpu_state(union fpu_state* state) @@ -170,17 +172,16 @@ static void fpu_init_xsave(union fpu_state* fpu) static uint32_t get_frequency_from_mbinfo(void) { -#if 0 - if (mb_info && (mb_info->flags & MULTIBOOT_INFO_CMDLINE)) + if (mb_info && (mb_info->flags & MULTIBOOT_INFO_CMDLINE) && (cmdline)) { // search in the command line for cpu frequency - char* found = strstr((char*) mb_info->cmdline, "-freq"); + char* found = strstr((char*) (size_t)cmdline, "-freq"); if (!found) return 0; return atoi(found+strlen("-freq")); } -#endif + return 0; } @@ -189,52 +190,37 @@ static uint32_t get_frequency_from_mbinfo(void) // Identification and the CPUID Instruction". static uint32_t get_frequency_from_brand(void) { - char brand[4*3*sizeof(uint32_t)+1]; - uint32_t eax = 0, ebx = 0; - uint32_t ecx = 0, edx = 0; uint32_t index, multiplier = 0; - uint32_t* bint = (uint32_t*) brand; - memset(brand, 0x00, sizeof(brand)); - - cpuid(0x80000000, &eax, &ebx, &ecx, &edx); - if (eax >= 0x80000004) + for(index=0; index 0) { + uint32_t freq; + + // Compute frequency (in MHz) from brand string + if (cpu_brand[index-3] == '.') { // If format is “x.xx” + freq = (uint32_t)(cpu_brand[index-4] - '0') * multiplier; + freq += (uint32_t)(cpu_brand[index-2] - '0') * (multiplier / 10); + freq += (uint32_t)(cpu_brand[index-1] - '0') * (multiplier / 100); + } else { // If format is xxxx + freq = (uint32_t)(cpu_brand[index-4] - '0') * 1000; + freq += (uint32_t)(cpu_brand[index-3] - '0') * 100; + freq += (uint32_t)(cpu_brand[index-2] - '0') * 10; + freq += (uint32_t)(cpu_brand[index-1] - '0'); + freq *= multiplier; } - if (multiplier > 0) { - uint32_t freq; - - // Compute frequency (in MHz) from brand string - if (brand[index-3] == '.') { // If format is “x.xx” - freq = (uint32_t)(brand[index-4] - '0') * multiplier; - freq += (uint32_t)(brand[index-2] - '0') * (multiplier / 10); - freq += (uint32_t)(brand[index-1] - '0') * (multiplier / 100); - } else { // If format is xxxx - freq = (uint32_t)(brand[index-4] - '0') * 1000; - freq += (uint32_t)(brand[index-3] - '0') * 100; - freq += (uint32_t)(brand[index-2] - '0') * 10; - freq += (uint32_t)(brand[index-1] - '0'); - freq *= multiplier; - } - - return freq; - } + return freq; } } @@ -407,7 +393,7 @@ static void check_est(uint8_t out) int cpu_detection(void) { uint64_t xcr0; - uint32_t a=0, b=0, c=0, d=0, level = 0; + uint32_t a=0, b=0, c=0, d=0, level = 0, extended = 0; uint32_t family, model, stepping; size_t cr0, cr4; uint8_t first_time = 0; @@ -415,10 +401,10 @@ int cpu_detection(void) { if (!cpu_info.feature1) { first_time = 1; - cpuid(0, &level, &b, &c, &d); - LOG_INFO("cpuid level %d\n", level); + cpuid(0, &level, (uint32_t*) cpu_vendor, (uint32_t*)(cpu_vendor+8), (uint32_t*)(cpu_vendor+4)); + kprintf("cpuid level %d\n", level); + kprintf("CPU vendor: %s\n", cpu_vendor); - a = b = c = d = 0; cpuid(1, &a, &b, &cpu_info.feature2, &cpu_info.feature1); family = (a & 0x00000F00) >> 8; @@ -427,18 +413,29 @@ int cpu_detection(void) { if ((family == 6) && (model < 3) && (stepping < 3)) cpu_info.feature1 &= ~CPU_FEATURE_SEP; - cpuid(0x80000001, &a, &b, &c, &cpu_info.feature3); - cpuid(0x80000008, &cpu_info.addr_width, &b, &c, &d); + cpuid(0x80000000, &extended, &b, &c, &d); + if (extended >= 0x80000001) + cpuid(0x80000001, &a, &b, &c, &cpu_info.feature3); + if (extended >= 0x80000008) { + uint32_t* bint = (uint32_t*) cpu_brand; + + cpuid(0x80000002, bint+0, bint+1, bint+2, bint+3); + cpuid(0x80000003, bint+4, bint+5, bint+6, bint+7); + cpuid(0x80000004, bint+8, bint+9, bint+10, bint+11); + kprintf("Processor: %s\n", cpu_brand); + } + if (extended >= 0x80000008) + cpuid(0x80000008, &cpu_info.addr_width, &b, &c, &d); /* Additional Intel-defined flags: level 0x00000007 */ - if (level >= 0x00000007) { + if (level >= 0x00000007) { a = b = c = d = 0; cpuid(7, &a, &cpu_info.feature4, &c, &d); } } if (first_time) { - LOG_INFO("Paging features: %s%s%s%s%s%s%s%s\n", + kprintf("Paging features: %s%s%s%s%s%s%s%s\n", (cpu_info.feature1 & CPU_FEATURE_PSE) ? "PSE (2/4Mb) " : "", (cpu_info.feature1 & CPU_FEATURE_PAE) ? "PAE " : "", (cpu_info.feature1 & CPU_FEATURE_PGE) ? "PGE " : "", @@ -448,10 +445,10 @@ int cpu_detection(void) { (cpu_info.feature3 & CPU_FEATURE_1GBHP) ? "PSE (1Gb) " : "", (cpu_info.feature3 & CPU_FEATURE_LM) ? "LM" : ""); - LOG_INFO("Physical adress-width: %u bits\n", cpu_info.addr_width & 0xff); - LOG_INFO("Linear adress-width: %u bits\n", (cpu_info.addr_width >> 8) & 0xff); - LOG_INFO("Sysenter instruction: %s\n", (cpu_info.feature1 & CPU_FEATURE_SEP) ? "available" : "unavailable"); - LOG_INFO("Syscall instruction: %s\n", (cpu_info.feature3 & CPU_FEATURE_SYSCALL) ? "available" : "unavailable"); + kprintf("Physical adress-width: %u bits\n", cpu_info.addr_width & 0xff); + kprintf("Linear adress-width: %u bits\n", (cpu_info.addr_width >> 8) & 0xff); + kprintf("Sysenter instruction: %s\n", (cpu_info.feature1 & CPU_FEATURE_SEP) ? "available" : "unavailable"); + kprintf("Syscall instruction: %s\n", (cpu_info.feature3 & CPU_FEATURE_SYSCALL) ? "available" : "unavailable"); } //TODO: add check for SMEP and SMAP @@ -509,7 +506,8 @@ int cpu_detection(void) { xcr0 |= 0xE0; xsetbv(0, xcr0); - LOG_INFO("Set XCR0 to 0x%llx\n", xgetbv(0)); + if (first_time) + kprintf("Set XCR0 to 0x%llx\n", xgetbv(0)); } // libos => currently no support of syscalls @@ -520,7 +518,7 @@ int cpu_detection(void) { wrmsr(MSR_LSTAR, (size_t) &isrsyscall); // clear IF flag during an interrupt wrmsr(MSR_SYSCALL_MASK, EFLAGS_TF|EFLAGS_DF|EFLAGS_IF|EFLAGS_AC|EFLAGS_NT); - } else LOG_INFO("Processor doesn't support syscalls\n"); + } else kprintf("Processor doesn't support syscalls\n"); #endif if (has_nx()) @@ -554,7 +552,7 @@ int cpu_detection(void) { a = b = c = d = 0; cpuid(1, &a, &b, &cpu_info.feature2, &cpu_info.feature1); - LOG_INFO("CPU features: %s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s\n", + LOG_INFO("CPU features: %s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s%s\n", has_sse() ? "SSE " : "", has_sse2() ? "SSE2 " : "", has_sse3() ? "SSE3 " : "", @@ -573,6 +571,7 @@ int cpu_detection(void) { has_vmx() ? "VMX " : "", has_rdtscp() ? "RDTSCP " : "", has_fsgsbase() ? "FSGSBASE " : "", + has_sgx() ? "SGX " : "", has_mwait() ? "MWAIT " : "", has_clflush() ? "CLFLUSH " : "", has_bmi1() ? "BMI1 " : "", @@ -581,10 +580,14 @@ int cpu_detection(void) { has_rtm() ? "RTM " : "", has_hle() ? "HLE " : "", has_cqm() ? "CQM " : "", + has_clflushopt() ? "CLFLUSHOPT " : "", + has_clwb() ? "CLWB " : "", has_avx512f() ? "AVX512F " : "", has_avx512cd() ? "AVX512CD " : "", has_avx512pf() ? "AVX512PF " : "", - has_avx512er() ? "AVX512ER " : ""); + has_avx512er() ? "AVX512ER " : "", + has_avx512vl() ? "AVX512VL " : "", + has_avx512bw() ? "AVX512BW " : ""); } if (first_time && has_osxsave()) { @@ -616,15 +619,11 @@ int cpu_detection(void) { check_est(first_time); if (first_time && on_hypervisor()) { - uint32_t c, d; char vendor_id[13]; LOG_INFO("HermitCore is running on a hypervisor!\n"); - cpuid(0x40000000, &a, &b, &c, &d); - memcpy(vendor_id, &b, 4); - memcpy(vendor_id + 4, &c, 4); - memcpy(vendor_id + 8, &d, 4); + cpuid(0x40000000, &a, (uint32_t*)vendor_id, (uint32_t*)(vendor_id+4), (uint32_t*)(vendor_id+8)); vendor_id[12] = '\0'; LOG_INFO("Hypervisor Vendor Id: %s\n", vendor_id); diff --git a/kernel/signal.c b/arch/x86/kernel/signal.c similarity index 80% rename from kernel/signal.c rename to arch/x86/kernel/signal.c index 78faa4c33..b25240a0b 100644 --- a/kernel/signal.c +++ b/arch/x86/kernel/signal.c @@ -1,3 +1,29 @@ +/* + * Copyright (c) 2017, Daniel Krebs, RWTH Aachen University + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * * Neither the name of the University nor the names of its contributors + * may be used to endorse or promote products derived from this + * software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ #include #include #include @@ -186,7 +212,7 @@ int hermit_kill(tid_t dest, int signum) return 0; } -void signal_init() +void signal_init(void) { // initialize per-core signal queue for(int i = 0; i < MAX_CORES; i++) { @@ -196,4 +222,3 @@ void signal_init() irq_install_handler(SIGNAL_IRQ, _signal_irq_handler); } - diff --git a/arch/x86/kernel/tasks.c b/arch/x86/kernel/tasks.c index 516eede51..d063662d8 100644 --- a/arch/x86/kernel/tasks.c +++ b/arch/x86/kernel/tasks.c @@ -37,16 +37,55 @@ #include #include #include +#include + +#define TLS_ALIGNBITS 5 +#define TLS_ALIGNSIZE (1L << TLS_ALIGNBITS) +#define TSL_ALIGNMASK ((~0L) << TLS_ALIGNBITS) +#define TLS_FLOOR(addr) ((((size_t)addr) + TLS_ALIGNSIZE - 1) & TSL_ALIGNMASK) /* * Note that linker symbols are not variables, they have no memory allocated for * maintaining a value, rather their address is their value. */ +extern const void tls_start; +extern const void tls_end; extern const void percore_start; extern const void percore_end0; extern uint64_t base; +static int init_tls(void) +{ + task_t* curr_task = per_core(current_task); + + // do we have a thread local storage? + if (((size_t) &tls_end - (size_t) &tls_start) > 0) { + char* tls_addr = NULL; + size_t fs; + + curr_task->tls_addr = (size_t) &tls_start; + curr_task->tls_size = (size_t) &tls_end - (size_t) &tls_start; + + tls_addr = kmalloc(curr_task->tls_size + TLS_ALIGNSIZE + sizeof(size_t)); + if (BUILTIN_EXPECT(!tls_addr, 0)) { + LOG_ERROR("load_task: heap is missing!\n"); + return -ENOMEM; + } + + memset(tls_addr, 0x00, TLS_ALIGNSIZE); + memcpy((void*) TLS_FLOOR(tls_addr), (void*) curr_task->tls_addr, curr_task->tls_size); + fs = (size_t) TLS_FLOOR(tls_addr) + curr_task->tls_size; + *((size_t*)fs) = fs; + + // set fs register to the TLS segment + set_tls(fs); + LOG_INFO("TLS of task %d on core %d starts at 0x%zx (size 0x%zx)\n", curr_task->id, CORE_ID, TLS_FLOOR(tls_addr), curr_task->tls_size); + } else set_tls(0); // no TLS => clear fs register + + return 0; +} + static int thread_entry(void* arg, size_t ep) { @@ -61,6 +100,22 @@ static int thread_entry(void* arg, size_t ep) return 0; } +int is_proxy(void) +{ + if (is_uhyve()) + return 0; + if (!is_single_kernel()) + return 1; + if (mb_info && (mb_info->flags & MULTIBOOT_INFO_CMDLINE) && (cmdline)) + { + // search in the command line for the "proxy" hint + char* found = strstr((char*) (size_t) cmdline, "-proxy"); + if (found) + return 1; + } + return 0; +} + size_t* get_current_stack(void) { task_t* curr_task = per_core(current_task); @@ -141,7 +196,7 @@ int create_default_frame(task_t* task, entry_point_t ep, void* arg, uint32_t cor void wait_for_task(void) { if (!has_mwait()) { - PAUSE; + HALT; } else { void* queue = get_readyqueue(); @@ -152,3 +207,17 @@ void wait_for_task(void) mwait(0x2 /* 0x2 = c3, 0xF = c0 */, 1 /* break on interrupt flag */); } } + +void wakeup_core(uint32_t core_id) +{ + // if mwait is available, an IPI isn't required to wakeup the core + if (has_mwait()) + return; + + // no self IPI required + if (core_id == CORE_ID) + return; + + LOG_DEBUG("wakeup core %d\n", core_id); + apic_send_ipi(core_id, 121); +} diff --git a/arch/x86/kernel/uart.c b/arch/x86/kernel/uart.c index 3be2dbbf3..38ce21427 100644 --- a/arch/x86/kernel/uart.c +++ b/arch/x86/kernel/uart.c @@ -41,8 +41,6 @@ #include #endif -#ifndef CONFIG_VGA - /* * This implementation based on following tutorial: * http://en.wikibooks.org/wiki/Serial_Programming/8250_UART_Programming @@ -99,40 +97,40 @@ #define UART_MCR_RTS 0x02 /* RTS complement */ #define UART_MCR_DTR 0x01 /* DTR complement */ -static uint8_t mmio = 0; -static size_t iobase = 0; +#define DEFAULT_UART_PORT 0xc110 + +extern size_t uartport; static inline unsigned char read_from_uart(uint32_t off) { uint8_t c = 0; - if (mmio) - c = *((const volatile unsigned char*) (iobase + off)); - else if (iobase) - c = inportb(iobase + off); + if (uartport) + c = inportb(uartport + off); return c; } -static void write_to_uart(uint32_t off, unsigned char c) +static inline int is_transmit_empty(void) { - if (mmio) - *((volatile unsigned char*) (iobase + off)) = c; - else if (iobase) - outportb(iobase + off, c); + if (uartport) + return inportb(uartport + UART_LSR) & 0x20; + + return 1; } - -/* Get a single character on a serial device */ -static unsigned char uart_getchar(void) +static inline void write_to_uart(uint32_t off, unsigned char c) { - return read_from_uart(UART_RX); + while (is_transmit_empty() == 0) { PAUSE; } + + if (uartport) + outportb(uartport + off, c); } /* Puts a single character on a serial device */ int uart_putchar(unsigned char c) { - if (!iobase && !mmio) + if (!uartport) return 0; write_to_uart(UART_TX, c); @@ -145,7 +143,7 @@ int uart_puts(const char *text) { size_t i, len = strlen(text); - if (!iobase && !mmio) + if (!uartport) return 0; for (i = 0; i < len; i++) @@ -154,54 +152,14 @@ int uart_puts(const char *text) return len; } -/* Handles all UART's interrupt */ -static void uart_handler(struct state *s) -{ - unsigned char c = read_from_uart(UART_IIR); - - while (!(c & UART_IIR_NO_INT)) { - if (c & UART_IIR_RDI) { - c = uart_getchar(); - - //TODO: handle input messages - - goto out; - } - - if(c & UART_IIR_THRI) { - // acknowledge interrupt - c = read_from_uart(UART_IIR); - - goto out; - } - - if(c & UART_IIR_RLSI) { - // acknowledge interrupt - c = read_from_uart(UART_LSR); - - goto out; - } - -out: - c = read_from_uart(UART_IIR); - } -} - static int uart_config(void) { - /* - * enable FIFOs - * clear RX and TX FIFO - * set irq trigger to 8 bytes - */ - write_to_uart(UART_FCR, UART_FCR_ENABLE_FIFO | UART_FCR_CLEAR_RCVR | UART_FCR_CLEAR_XMIT | UART_FCR_TRIGGER_1); + if (!uartport) + return 0; /* disable interrupts */ write_to_uart(UART_IER, 0); - /* DTR + RTS */ - write_to_uart(UART_MCR, UART_MCR_DTR|UART_MCR_RTS); - /* * 8bit word length * 1 stop bit @@ -214,116 +172,60 @@ static int uart_config(void) write_to_uart(UART_LCR, lcr); /* - * set baudrate to 115200 + * set baudrate to 38400 */ - uint32_t divisor = 1843200 / 115200; - write_to_uart(UART_DLL, divisor & 0xff); - write_to_uart(UART_DLM, (divisor >> 8) & 0xff); + write_to_uart(UART_DLL, 0x03); + write_to_uart(UART_DLM, 0x00); /* set DLAB=0 */ write_to_uart(UART_LCR, lcr & (~UART_LCR_DLAB)); + /* + * enable FIFOs + * clear RX and TX FIFO + * set irq trigger to 8 bytes + */ + write_to_uart(UART_FCR, UART_FCR_ENABLE_FIFO | UART_FCR_CLEAR_RCVR | UART_FCR_CLEAR_XMIT | UART_FCR_TRIGGER_1); + return 0; } -extern const void kernel_start; - -int uart_early_init(char* cmdline) -{ -#if 1 - // default value of our QEMU configuration - iobase = 0xc110; -#else - if (BUILTIN_EXPECT(!cmdline, 0)) - return -EINVAL; - - char* str = strstr(cmdline, "uart="); - if (!str) - return -EINVAL; - - if (strncmp(str, "uart=io:", 8) == 0) { - iobase = strtol(str+8, (char **)NULL, 16); - if (!iobase) - return -EINVAL; - mmio = 0; - } else if (strncmp(str, "uart=mmio:", 10) == 0) { - iobase = strtol(str+10, (char **)NULL, 16); - if (!iobase) - return -EINVAL; - if (iobase >= PAGE_MAP_ENTRIES*PAGE_SIZE) { - /* at this point we use the boot page table - * => IO address is not mapped - * => dirty hack, map device before the kernel - */ - int err; - size_t newaddr = ((size_t) &kernel_start - PAGE_SIZE); - - err = page_map_bootmap(newaddr & PAGE_MASK, iobase & PAGE_MASK, PG_GLOBAL | PG_ACCESSED | PG_DIRTY | PG_RW | PG_PCD); - if (BUILTIN_EXPECT(err, 0)) { - iobase = 0; - return err; - } - iobase = newaddr; - } - mmio = 1; - } -#endif - - // configure uart - return uart_config(); -} - int uart_init(void) { -#ifdef CONFIG_PCI + if (is_uhyve()) + return 0; + + if (uartport) + return uart_config(); + pci_info_t pci_info; uint32_t bar = 0; // Searching for Intel's UART device - if (pci_get_device_info(0x8086, 0x0936, iobase, &pci_info) == 0) + if (pci_get_device_info(0x8086, 0x0936, PCI_IGNORE_SUBID, &pci_info, 1) == 0) goto Lsuccess; - // Searching for Qemu's UART device - if (pci_get_device_info(0x1b36, 0x0002, iobase, &pci_info) == 0) + // Searching for Qemu's UART device + if (pci_get_device_info(0x1b36, 0x0002, PCI_IGNORE_SUBID, &pci_info, 1) == 0) goto Lsuccess; // Searching for Qemu's 2x UART device (pci-serial-2x) - if (pci_get_device_info(0x1b36, 0x0003, iobase, &pci_info) == 0) + if (pci_get_device_info(0x1b36, 0x0003, PCI_IGNORE_SUBID, &pci_info, 1) == 0) goto Lsuccess; // Searching for Qemu's 4x UART device (pci-serial-4x) - if (pci_get_device_info(0x1b36, 0x0004, iobase, &pci_info) == 0) + if (pci_get_device_info(0x1b36, 0x0004, PCI_IGNORE_SUBID, &pci_info, 1) == 0) goto Lsuccess; - return -1; + // default value of our QEMU configuration + uartport = DEFAULT_UART_PORT; + + // configure uart + return uart_config(); Lsuccess: - iobase = pci_info.base[bar]; - irq_install_handler(32+pci_info.irq, uart_handler); - if (pci_info.type[0]) { - mmio = 0; - LOG_INFO("UART uses io address 0x%x\n", iobase); - } else { - mmio = 1; - page_map(iobase & PAGE_MASK, iobase & PAGE_MASK, 1, PG_GLOBAL | PG_ACCESSED | PG_DIRTY | PG_RW | PG_PCD); - LOG_INFO("UART uses mmio address 0x%x\n", iobase); - vma_add(iobase, iobase + PAGE_SIZE, VMA_READ|VMA_WRITE); - } + uartport = pci_info.base[bar]; + + //irq_install_handler(32+pci_info.irq, uart_handler); + kprintf("UART uses io address 0x%x\n", uartport); // configure uart return uart_config(); -#else - // per default we use COM1... - if (!iobase) - iobase = 0x3F8; - mmio = 0; - if ((iobase == 0x3F8) || (iobase == 0x3E8)) - irq_install_handler(32+4, uart_handler); - else if ((iobase == 0x2F8) || (iobase == 0x2E8)) - irq_install_handler(32+3, uart_handler); - else - return -EINVAL; - - // configure uart - return uart_config(); -#endif } - -#endif diff --git a/arch/x86/kernel/vga.c b/arch/x86/kernel/vga.c deleted file mode 100644 index 09b863e11..000000000 --- a/arch/x86/kernel/vga.c +++ /dev/null @@ -1,240 +0,0 @@ -/* - * Copyright (c) 2010, Stefan Lankes, RWTH Aachen University - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions are met: - * * Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * * Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * * Neither the name of the University nor the names of its contributors - * may be used to endorse or promote products derived from this - * software without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED - * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE - * DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE FOR ANY - * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES - * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; - * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND - * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT - * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS - * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - */ - -#include -#include -#include - -#ifdef CONFIG_VGA - -/* - * These define our textpointer, our background and foreground - * colors (attributes), and x and y cursor coordinates - */ -static unsigned short *textmemptr; -static int attrib = 0x0F; -static int csr_x = 0, csr_y = 0; - -inline static unsigned short *memsetw(unsigned short *dest, unsigned short val, size_t count) -{ - size_t i; - - if (BUILTIN_EXPECT(!dest, 0)) - return dest; - - for (i = 0; i < count; i++) - dest[i] = val; - - return dest; -} - -/* Scrolls the screen */ -static void scroll(void) -{ - unsigned blank, temp; - - /* - * A blank is defined as a space... we need to give it - * backcolor too - */ - blank = 0x20 | (attrib << 8); - - /* Row 25 is the end, this means we need to scroll up */ - if (csr_y >= 25) { - - /* - * Move the current text chunk that makes up the screen - * - * back in the buffer by one line - */ - temp = csr_y - 25 + 1; - memcpy(textmemptr, textmemptr + temp * 80, - (25 - temp) * 80 * 2); - - /* - * Finally, we set the chunk of memory that occupies - * the last line of text to our 'blank' character - */ - memsetw(textmemptr + (25 - temp) * 80, blank, 80); - csr_y = 25 - 1; - } -} - -/* - * Updates the hardware cursor: the little blinking line - * on the screen under the last character pressed! - */ -static void move_csr(void) -{ - unsigned temp; - - /* - * The equation for finding the index in a linear - * chunk of memory can be represented by: - * Index = [(y * width) + x] */ - temp = csr_y * 80 + csr_x; - - /* - * This sends a command to indicies 14 and 15 in the - * CRT Control Register of the VGA controller. These - * are the high and low bytes of the index that show - * where the hardware cursor is to be 'blinking'. To - * learn more, you should look up some VGA specific - * programming documents. A great start to graphics: - * http://www.brackeen.com/home/vga - */ - outportb(0x3D4, 14); - outportb(0x3D5, temp >> 8); - outportb(0x3D4, 15); - outportb(0x3D5, temp); -} - -/* Clears the screen */ -void vga_clear(void) -{ - unsigned blank; - int i; - - /* - * Again, we need the 'short' that will be used to - * represent a space with color - */ - blank = 0x20 | (attrib << 8); - - /* - * Fills the entire screen with spaces in our current - * color - **/ - for (i = 0; i < 25; i++) - memsetw(textmemptr + i * 80, blank, 80); - - /* - * Update out virtual cursor, and then move the - * hardware cursor - */ - csr_x = 0; - csr_y = 0; - move_csr(); -} - -/* Puts a single character on the screen */ -int vga_putchar(unsigned char c) -{ - unsigned short *where; - unsigned att = attrib << 8; - - /* Handle a backspace by moving the cursor back one space */ - if (c == 0x08) { - if (csr_x != 0) - csr_x--; - } - - /* - * Handles a tab by incrementing the cursor's x, but only - * to a point that will make it divisible by 8 - */ - else if (c == 0x09) { - csr_x = (csr_x + 8) & ~(8 - 1); - } - - /* - * Handles a 'Carriage Return', which simply brings the - * cursor back to the margin - */ - else if (c == '\r') { - csr_x = 0; - } - - /* - * We handle our newlines the way DOS and BIOS do: we - * treat it as if a 'CR' was there also, so we bring the - * cursor to the margin and increment the 'y' value - */ - else if (c == '\n') { - csr_x = 0; - csr_y++; - } - - /* - * Any character greater than and including the space is a - * printable character. The equation for finding the index - * in a linear chunk of memory can be represented by: - * Index = [(y * width) + x] - */ - else if (c >= ' ') { - where = textmemptr + (csr_y * 80 + csr_x); - *where = c | att; /* Character AND attributes: color */ - csr_x++; - } - - /* - * If the cursor has reached the edge of the screen's width, we - * insert a new line in there - */ - if (csr_x >= 80) { - csr_x = 0; - csr_y++; - } - - /* Scroll the screen if needed, and finally move the cursor */ - scroll(); - move_csr(); - - return (int) c; -} - -/* Uses the routine above to output a string... */ -int vga_puts(const char *text) -{ - size_t i; - - for (i = 0; i < strlen(text); i++) - vga_putchar(text[i]); - - return i-1; -} - -/* Sets the forecolor and backcolor we will use */ -//void settextcolor(unsigned char forecolor, unsigned char backcolor) -//{ - - /* - * Top 4 bytes are the background, bottom 4 bytes - * are the foreground color - */ -// attrib = (backcolor << 4) | (forecolor & 0x0F); -//} - -/* Sets our text-mode VGA pointer, then clears the screen for us */ -void vga_init(void) -{ - textmemptr = (unsigned short *)VIDEO_MEM_ADDR; - // our bootloader already cleared the screen - vga_clear(); -} - -#endif diff --git a/arch/x86/kernel/string.asm b/arch/x86/libkern/string.asm similarity index 97% rename from arch/x86/kernel/string.asm rename to arch/x86/libkern/string.asm index a289375ae..06affde19 100644 --- a/arch/x86/kernel/string.asm +++ b/arch/x86/libkern/string.asm @@ -8,7 +8,7 @@ ; WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. ; -%include "config.inc" +%include "hermit/config.asm" %ifdef CONFIG_X86_32 [BITS 32] diff --git a/arch/x86/loader/CMakeLists.txt b/arch/x86/loader/CMakeLists.txt new file mode 100644 index 000000000..0d142c166 --- /dev/null +++ b/arch/x86/loader/CMakeLists.txt @@ -0,0 +1,50 @@ +cmake_minimum_required(VERSION 3.7) + +project(arch_x86_loader C ASM_NASM) + +## ASM sources + +file(GLOB ASM_SOURCES *.asm) +add_library(arch_x86_loader_asm STATIC ${ASM_SOURCES}) + +## C sources + +file(GLOB C_SOURCES *.c) +add_executable(arch_x86_loader ${C_SOURCES}) + +target_include_directories(arch_x86_loader + PRIVATE include/) + +target_compile_options(arch_x86_loader + PRIVATE -O2 -Wall -m64 -std=gnu99 -ffreestanding -mno-red-zone + -fstrength-reduce -fomit-frame-pointer -finline-functions) + +target_link_libraries(arch_x86_loader + arch_x86_loader_asm + "-T ${CMAKE_CURRENT_LIST_DIR}/link.ld" + "-z max-page-size=4096" + -Wl,--build-id=none # required because CMake links with gcc, not ld + -nostdlib) + +# tools/proxy looks for `ldhermit.elf` +set_target_properties(arch_x86_loader PROPERTIES + OUTPUT_NAME ldhermit.elf) + +add_custom_command( + TARGET arch_x86_loader POST_BUILD + # Split debug symbols into seperate file + COMMAND + ${CMAKE_OBJCOPY} --only-keep-debug + $ + $.sym + # Qemu requires 32-bit ELF + COMMAND + ${CMAKE_OBJCOPY} -O elf32-i386 --strip-debug + $) + +install(TARGETS arch_x86_loader + DESTINATION bin) + +# Show include files in IDE +file(GLOB_RECURSE ARCH_X86_LOADER_INCLUDES "include/*") +add_custom_target(arch_x86_loader_includes_ide SOURCES ${ARCH_X86_LOADER_INCLUDES}) diff --git a/arch/x86/loader/Makefile b/arch/x86/loader/Makefile deleted file mode 100644 index ed39c5fa8..000000000 --- a/arch/x86/loader/Makefile +++ /dev/null @@ -1,69 +0,0 @@ -MAKE = make -QEMU = qemu-system-x86_64 -machine accel=kvm -cpu host -OBJDUMP = objdump -OBJCOPY = objcopy -CC = gcc -CFLAGS = -O2 -Wall -m64 -std=gnu99 -ffreestanding -mno-red-zone -fstrength-reduce -fomit-frame-pointer -finline-functions -Iinclude -NASM = nasm -NASMFLAGS = -felf64 -g -LD = ld -LDFLAGS = -T link.ld -z max-page-size=4096 -STRIP_DEBUG = --strip-debug -KEEP_DEBUG = --only-keep-debug -OUTPUT_FORMAT = -O elf32-i386 -NAME = ldhermit -TTY := $(shell tty) - -C_source := main.c printf.c string.c stdio.c vga.c uart.c page.c -ASM_source := entry.asm - -OBJS := $(C_source:.c=.o) -OBJS += $(ASM_source:.asm=.o) - -# Prettify output -V = 0 -ifeq ($V,0) - Q = @ - P = > /dev/null -endif - -# other implicit rules -%.o : %.c - @echo [CC] $@ - $Q$(CC) -c $(CFLAGS) -o $@ $< - @echo [DEP] $*.dep - $Q$(CC) -MF $*.dep -MT $*.o -MM $(CFLAGS) $< - -%.o : %.asm - @echo [ASM] $@ - $Q$(NASM) $(NASMFLAGS) -o $@ $< - -all: ldhermit.elf - -$(NAME).elf: $(OBJS) - @echo [LD] $@ - $Q$(LD) $(LDFLAGS) -o $@ $(OBJS) - @echo [OBJCOPY] $(NAME).sym - $Q$(OBJCOPY) $(KEEP_DEBUG) $(NAME).elf $(NAME).sym - @echo [OBJCOPY] $(NAME).elf - $Q$(OBJCOPY) $(STRIP_DEBUG) $(OUTPUT_FORMAT) $(NAME).elf - -#qemu: -# @echo "Do you already start netcat (nc -l 4555)?" -# $(QEMU) -smp 4 -m 4G -kernel $(NAME).elf -initrd ../../../usr/benchmarks/stream \ - -net nic,model=rtl8139 -net user -net dump \ - -chardev socket,host=127.0.0.1,port=4555,id=gnc0 \ - -device pci-serial,chardev=gnc0 \ - -monitor telnet:127.0.0.1:1235,server,nowait -nographic - -clean: - @echo Cleaning loader - $Q$(RM) -rf *.o *~ *.bin *.obj - -veryclean: clean - -depend: - $(CC) -MM $(CFLAGS) *.c > Makefile.dep - --include -include $(C_source:.c=.dep) -# DO NOT DELETE diff --git a/arch/x86/loader/entry.asm b/arch/x86/loader/entry.asm index 2d99a6f36..3ae3d7c1a 100644 --- a/arch/x86/loader/entry.asm +++ b/arch/x86/loader/entry.asm @@ -99,32 +99,24 @@ stublet: ; Interpret multiboot information mov DWORD [mb_info], ebx - ; Initialize CPU features - call cpu_init - - pop ebx ; restore pointer to multiboot structure - lgdt [GDT64.Pointer] ; Load the 64-bit global descriptor table. - jmp GDT64.Code:start64 ; Set the code segment and enter 64-bit long mode. - ; This will set up the x86 control registers: ; Caching and the floating point unit are enabled ; Bootstrap page tables are loaded and page size ; extensions (huge pages) enabled. -global cpu_init cpu_init: ; initialize page tables ; map vga 1:1 - push edi - mov eax, VIDEO_MEM_ADDR ; map vga - and eax, 0xFFFFF000 ; page align lower half - mov edi, eax - shr edi, 9 ; (edi >> 12) * 8 (index for boot_pgt) - add edi, boot_pgt - or eax, 0x113 ; set present, global, writable and cache disable bits - mov DWORD [edi], eax - pop edi + ; push edi + ; mov eax, VIDEO_MEM_ADDR ; map vga + ; and eax, 0xFFFFF000 ; page align lower half + ; mov edi, eax + ; shr edi, 9 ; (edi >> 12) * 8 (index for boot_pgt) + ; add edi, boot_pgt + ; or eax, 0x13 ; set present, writable and cache disable bits + ; mov DWORD [edi], eax + ; pop edi ; map multiboot info 1:1 push edi @@ -133,7 +125,7 @@ cpu_init: mov edi, eax shr edi, 9 ; (edi >> 12) * 8 (index for boot_pgt) add edi, boot_pgt - or eax, 0x101 ; set present and global bits + or eax, 0x3 ; set present and writable bits mov DWORD [edi], eax pop edi @@ -151,7 +143,7 @@ L0: cmp ecx, ebx mov edi, eax shr edi, 9 ; (edi >> 12) * 8 (index for boot_pgt) add edi, boot_pgt - or eax, 0x103 ; set present, global and writable bits + or eax, 0x3 ; set present and writable bits mov DWORD [edi], eax add ecx, 0x1000 jmp L0 @@ -188,23 +180,22 @@ L1: test edx, 1 << 29 ; Test if the LM-bit, which is bit 29, is set in the D-register. jz Linvalid ; They aren't, there is no long mode. + ; Set CR3 + mov eax, boot_pml4 + ;or eax, (1 << 0) ; set present bit + mov cr3, eax - ; we need to enable PAE modus + ; we need to enable PAE modus mov eax, cr4 or eax, 1 << 5 mov cr4, eax - ; switch to the compatibility mode (which is part of long mode) + ; switch to the compatibility mode (which is part of long mode) mov ecx, 0xC0000080 rdmsr or eax, 1 << 8 wrmsr - ; Set CR3 - mov eax, boot_pml4 - or eax, (1 << 0) ; set present bit - mov cr3, eax - ; Set CR4 mov eax, cr4 and eax, 0xfffbf9ff ; disable SSE @@ -221,7 +212,9 @@ L1: or eax, (1 << 31) ; enable paging mov cr0, eax - ret + ;pop ebx ; restore pointer to multiboot structure + lgdt [GDT64.Pointer] ; Load the 64-bit global descriptor table. + jmp GDT64.Code:start64 ; Set the code segment and enter 64-bit long mode. ; there is no long mode Linvalid: @@ -244,7 +237,7 @@ start64: ; jump to the boot processors's C code extern main - call main + jmp main jmp $ SECTION .data @@ -262,17 +255,17 @@ boot_stack: ; Bootstrap page tables are used during the initialization. ALIGN 4096 boot_pml4: - DQ boot_pdpt + 0x107 ; PG_PRESENT | PG_GLOBAL | PG_RW | PG_USER - times 510 DQ 0 ; PAGE_MAP_ENTRIES - 2 - DQ boot_pml4 + 0x303 ; PG_PRESENT | PG_GLOBAL | PG_RW | PG_SELF (self-reference) + DQ boot_pdpt + 0x7 ; PG_PRESENT | PG_GLOBAL | PG_RW | PG_USER + times 510 DQ 0 ; PAGE_MAP_ENTRIES - 2 + DQ boot_pml4 + 0x3 ; PG_PRESENT | PG_GLOBAL | PG_RW boot_pdpt: - DQ boot_pgd + 0x107 ; PG_PRESENT | PG_GLOBAL | PG_RW | PG_USER - times 510 DQ 0 ; PAGE_MAP_ENTRIES - 2 - DQ boot_pml4 + 0x303 ; PG_PRESENT | PG_GLOBAL | PG_RW | PG_SELF (self-reference) + DQ boot_pgd + 0x7 ; PG_PRESENT | PG_GLOBAL | PG_RW | PG_USER + times 510 DQ 0 ; PAGE_MAP_ENTRIES - 2 + DQ boot_pml4 + 0x3 ; PG_PRESENT | PG_GLOBAL | PG_RW boot_pgd: - DQ boot_pgt + 0x107 ; PG_PRESENT | PG_GLOBAL | PG_RW | PG_USER - times 510 DQ 0 ; PAGE_MAP_ENTRIES - 2 - DQ boot_pml4 + 0x303 ; PG_PRESENT | PG_GLOBAL | PG_RW | PG_SELF (self-reference) + DQ boot_pgt + 0x7 ; PG_PRESENT | PG_GLOBAL | PG_RW | PG_USER + times 510 DQ 0 ; PAGE_MAP_ENTRIES - 2 + DQ boot_pml4 + 0x3 ; PG_PRESENT | PG_GLOBAL | PG_RW boot_pgt: times 512 DQ 0 diff --git a/arch/x86/loader/include/ctype.h b/arch/x86/loader/include/ctype.h new file mode 100644 index 000000000..c5aa3915b --- /dev/null +++ b/arch/x86/loader/include/ctype.h @@ -0,0 +1,129 @@ +/**************************************************************************************** + * + * Author: Stefan Lankes + * Chair for Operating Systems, RWTH Aachen University + * Date: 24/03/2011 + * + **************************************************************************************** + * + * Written by the Chair for Operating Systems, RWTH Aachen University + * + * NO Copyright (C) 2010, Stefan Lankes, + * consider these trivial functions to be public domain. + * + * These functions are distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + */ + +/** + * @author Stefan Lankes + * @file include/ctype.h + * @brief Functions related to alphanumerical character values + * + * This file contains functions helping to determine + * the type of alphanumerical character values. + */ + +#ifndef __CTYPE_H_ +#define __CYTPE_H_ + +/** Returns true if the value of 'c' is an ASCII-charater */ +static inline int isascii(int c) +{ + return (((unsigned char)(c))<=0x7f); +} + +/** Applies an and-operation to + * push the value of 'c' into the ASCII-range */ +static inline int toascii(int c) +{ + return (((unsigned char)(c))&0x7f); +} + +/** Returns true if the value of 'c' is the + * space character or a control character */ +static inline int isspace(int c) +{ + if (!isascii(c)) + return 0; + + if (' ' == (unsigned char) c) + return 1; + if ('\n' == (unsigned char) c) + return 1; + if ('\r' == (unsigned char) c) + return 1; + if ('\t' == (unsigned char) c) + return 1; + if ('\v' == (unsigned char) c) + return 1; + if ('\f' == (unsigned char) c) + return 1; + + return 0; +} + +/** Returns true if the value of 'c' is a number */ +static inline int isdigit(int c) +{ + if (!isascii(c)) + return 0; + + if (((unsigned char) c >= '0') && ((unsigned char) c <= '9')) + return 1; + + return 0; +} + +/** Returns true if the value of 'c' is a lower case letter */ +static inline int islower(int c) +{ + if (!isascii(c)) + return 0; + + if (((unsigned char) c >= 'a') && ((unsigned char) c <= 'z')) + return 1; + + return 0; +} + +/** Returns true if the value of 'c' is an upper case letter */ +static inline int isupper(int c) +{ + if (!isascii(c)) + return 0; + + if (((unsigned char) c >= 'A') && ((unsigned char) c <= 'Z')) + return 1; + + return 0; +} + +/** Returns true if the value of 'c' is an alphabetic character */ +static inline int isalpha(int c) +{ + if (isupper(c) || islower(c)) + return 1; + + return 0; +} + +/** Makes the input character lower case.\n Will do nothing if it + * was something different than an upper case letter before. */ +static inline unsigned char tolower(unsigned char c) +{ + if (isupper(c)) + c -= 'A'-'a'; + return c; +} + +/** Makes the input character upper case.\n Will do nothing if it + * was something different than a lower case letter before. */ +static inline unsigned char toupper(unsigned char c) +{ + if (islower(c)) + c -= 'a'-'A'; + return c; +} + +#endif diff --git a/arch/x86/loader/include/limits.h b/arch/x86/loader/include/limits.h new file mode 100644 index 000000000..4f311b8ad --- /dev/null +++ b/arch/x86/loader/include/limits.h @@ -0,0 +1,87 @@ +/* + * Copyright (c) 2010, Stefan Lankes, RWTH Aachen University + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * * Neither the name of the University nor the names of its contributors + * may be used to endorse or promote products derived from this + * software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +/** + * author Stefan Lankes + * @file include/limits.h + * @brief Define constants related to numerical value-ranges of variable types + * + * This file contains define constants for the numerical + * ranges of the most typical variable types. + */ + +#ifndef __ARCH_LIMITS_H__ +#define __ARCH_LIMITS_H__ + +#ifdef __cplusplus +extern "C" { +#endif + +/** Number of bits in a char */ +#define CHAR_BIT 8 + +/** Maximum value for a signed char */ +#define SCHAR_MAX 0x7f +/** Minimum value for a signed char */ +#define SCHAR_MIN (-0x7f - 1) + +/** Maximum value for an unsigned char */ +#define UCHAR_MAX 0xff + +/** Maximum value for an unsigned short */ +#define USHRT_MAX 0xffff +/** Maximum value for a short */ +#define SHRT_MAX 0x7fff +/** Minimum value for a short */ +#define SHRT_MIN (-0x7fff - 1) + +/** Maximum value for an unsigned int */ +#define UINT_MAX 0xffffffffU +/** Maximum value for an int */ +#define INT_MAX 0x7fffffff +/** Minimum value for an int */ +#define INT_MIN (-0x7fffffff - 1) + +/** Maximum value for an unsigned long */ +#define ULONG_MAX 0xffffffffUL +/** Maximum value for a long */ +#define LONG_MAX 0x7fffffffL +/** Minimum value for a long */ +#define LONG_MIN (-0x7fffffffL - 1) + +/** Maximum value for an unsigned long long */ +#define ULLONG_MAX 0xffffffffffffffffULL +/** Maximum value for a long long */ +#define LLONG_MAX 0x7fffffffffffffffLL +/** Minimum value for a long long */ +#define LLONG_MIN (-0x7fffffffffffffffLL - 1) + +#ifdef __cplusplus +} +#endif + +#endif diff --git a/arch/x86/loader/include/stddef.h b/arch/x86/loader/include/stddef.h index 36f95f25f..76c2add7b 100644 --- a/arch/x86/loader/include/stddef.h +++ b/arch/x86/loader/include/stddef.h @@ -85,6 +85,14 @@ typedef char int8_t; /// 16 bit wide char type typedef unsigned short wchar_t; +/** @brief String to long + * + * @return Long value of the parsed numerical string + */ +long _strtol(const char* str, char** endptr, int base); + +#define strtol(str, endptr, base) _strtol((str), (endptr), (base)) + #ifdef __cplusplus } #endif diff --git a/arch/x86/loader/include/string.h b/arch/x86/loader/include/string.h index 84ef64a67..3d51a9492 100644 --- a/arch/x86/loader/include/string.h +++ b/arch/x86/loader/include/string.h @@ -41,7 +41,9 @@ char *strncpy(char *dest, const char *src, size_t n); char *strcpy(char *dest, const char *src); int strcmp(const char *s1, const char *s2); int strncmp(const char *s1, const char *s2, size_t n); -char *strstr(const char *s, const char *find); +char *_strstr(const char *s, const char *find); + +#define strstr(s, find) _strstr((s), (find)) #ifdef __cplusplus } diff --git a/arch/x86/loader/include/uart.h b/arch/x86/loader/include/uart.h index 0567aafa5..52d041b9c 100644 --- a/arch/x86/loader/include/uart.h +++ b/arch/x86/loader/include/uart.h @@ -34,17 +34,11 @@ extern "C" { #endif -/** @brief Initialize UART output - * - * @return Returns 0 on success - */ -int uart_init(void); - /** @brief Initialize UART output without a device check * * @return Returns 0 on success */ -int uart_early_init(char*); +int uart_init(const char*); /** @brief Simple string output on a serial device. * @@ -56,7 +50,7 @@ int uart_puts(const char *text); /** @brief Simple character output on a serial device. * - * @return The original input character casted to int + * @return The original input character casted to int */ int uart_putchar(unsigned char c); diff --git a/arch/x86/loader/main.c b/arch/x86/loader/main.c index 9f783f485..a753f2b1a 100644 --- a/arch/x86/loader/main.c +++ b/arch/x86/loader/main.c @@ -42,11 +42,56 @@ extern const void kernel_start; extern const void kernel_end; extern const void bss_start; extern const void bss_end; +extern size_t uartport; + +static int load_code(size_t viraddr, size_t phyaddr, size_t limit, uint32_t file_size, size_t mem_size, size_t cmdline, size_t cmdsize) +{ + const size_t displacement = 0x200000ULL - (phyaddr & 0x1FFFFFULL); + + kprintf("Found program segment at 0x%zx-0x%zx (viraddr 0x%zx-0x%zx)\n", phyaddr, phyaddr+file_size-1, viraddr, viraddr+file_size-1); + + uint32_t npages = (file_size >> PAGE_BITS); + if (file_size & (PAGE_SIZE-1)) + npages++; + + kprintf("Map %u pages from physical start address 0x%zx linear to 0x%zx\n", npages + (displacement >> PAGE_BITS), phyaddr, viraddr); + int ret = page_map(viraddr, phyaddr, npages + (displacement >> PAGE_BITS), PG_GLOBAL|PG_RW); + if (ret) + return -1; + + phyaddr += displacement; + *((uint64_t*) (viraddr + 0x08)) = phyaddr; // physical start address + *((uint64_t*) (viraddr + 0x10)) = limit; // physical limit + *((uint32_t*) (viraddr + 0x24)) = 1; // number of used cpus + *((uint32_t*) (viraddr + 0x30)) = 0; // apicid + *((uint64_t*) (viraddr + 0x38)) = mem_size; + *((uint32_t*) (viraddr + 0x60)) = 1; // numa nodes + *((uint64_t*) (viraddr + 0x98)) = uartport; + *((uint64_t*) (viraddr + 0xA0)) = cmdline; + *((uint64_t*) (viraddr + 0xA8)) = cmdsize; + + // move file to a 2 MB boundary + for(size_t va = viraddr+(npages << PAGE_BITS)+displacement-sizeof(uint8_t); va >= viraddr+displacement; va-=sizeof(uint8_t)) + *((uint8_t*) va) = *((uint8_t*) (va-displacement)); + + kprintf("Remap %u pages from physical start address 0x%zx linear to 0x%zx\n", npages, phyaddr, viraddr); + ret = page_map(viraddr, phyaddr, npages, PG_GLOBAL|PG_RW); + if (ret) + return -1; + + return 0; +} void main(void) { size_t limit = 0; + size_t viraddr = 0; + size_t phyaddr = 0; elf_header_t* header = NULL; + uint32_t file_size = 0; + size_t mem_size = 0; + size_t cmdline_size = 0; + size_t cmdline = 0; // initialize .bss section memset((void*)&bss_start, 0x00, ((size_t) &bss_end - (size_t) &bss_start)); @@ -56,6 +101,12 @@ void main(void) kprintf("Loader starts at %p and ends at %p\n", &kernel_start, &kernel_end); kprintf("Found mb_info at %p\n", mb_info); + if (mb_info && mb_info->cmdline) { + cmdline = (size_t) mb_info->cmdline; + cmdline_size = strlen((char*)cmdline); + } + + // enable paging page_init(); if (mb_info) { @@ -128,35 +179,12 @@ void main(void) switch(prog_header->type) { case ELF_PT_LOAD: { // load program segment - size_t viraddr = prog_header->virt_addr; - size_t phyaddr = prog_header->offset + (size_t)header; - const size_t displacement = 0x200000ULL - (phyaddr & 0x1FFFFFULL); - - uint32_t npages = (prog_header->file_size >> PAGE_BITS); - if (prog_header->file_size & (PAGE_SIZE-1)) - npages++; - - kprintf("Map %u pages from physical start address 0x%zx linear to 0x%zx\n", npages + (displacement >> PAGE_BITS), phyaddr, viraddr); - int ret = page_map(viraddr, phyaddr, npages + (displacement >> PAGE_BITS), PG_GLOBAL|PG_RW); - if (ret) - goto failed; - - phyaddr += displacement; - *((uint64_t*) (viraddr + 0x08)) = phyaddr; // physical start address - *((uint64_t*) (viraddr + 0x10)) = limit; // physical limit - *((uint32_t*) (viraddr + 0x24)) = 1; // number of used cpus - *((uint32_t*) (viraddr + 0x30)) = 0; // apicid - *((uint64_t*) (viraddr + 0x38)) = prog_header->file_size; - *((uint32_t*) (viraddr + 0x60)) = 1; // numa nodes - - // move file to a 2 MB boundary - for(size_t va = viraddr+(npages << PAGE_BITS)+displacement-sizeof(uint8_t); va >= viraddr+displacement; va-=sizeof(uint8_t)) - *((uint8_t*) va) = *((uint8_t*) (va-displacement)); - - kprintf("Remap %u pages from physical start address 0x%zx linear to 0x%zx\n", npages, phyaddr, viraddr); - ret = page_map(viraddr, phyaddr, npages, PG_GLOBAL|PG_RW); - if (ret) - goto failed; + if (!viraddr) + viraddr = prog_header->virt_addr; + if (!phyaddr) + phyaddr = prog_header->offset + (size_t)header; + file_size = prog_header->virt_addr + PAGE_FLOOR(prog_header->file_size) - viraddr; + mem_size += prog_header->mem_size; } break; case ELF_PT_GNU_STACK: // Indicates stack executability => nothing to do @@ -168,6 +196,9 @@ void main(void) } } + if (BUILTIN_EXPECT(load_code(viraddr, phyaddr, limit, file_size, mem_size, cmdline, cmdline_size), 0)) + goto failed; + kprintf("Entry point: 0x%zx\n", header->entry); // jump to the HermitCore app asm volatile ("jmp *%0" :: "r"(header->entry), "d"(mb_info) : "memory"); diff --git a/arch/x86/loader/stdio.c b/arch/x86/loader/stdio.c index 585e95a9e..9c3e5f422 100644 --- a/arch/x86/loader/stdio.c +++ b/arch/x86/loader/stdio.c @@ -27,27 +27,18 @@ #include #include -#include #include int koutput_init(void) { -#ifdef CONFIG_VGA - vga_init(); -#else - uart_early_init((char*) mb_info->cmdline); -#endif + uart_init((const char*) (size_t)mb_info->cmdline); return 0; } int kputchar(int c) { -#ifdef CONFIG_VGA - vga_putchar(c); -#else uart_putchar(c); -#endif return 1; } diff --git a/arch/x86/loader/strstr.c b/arch/x86/loader/strstr.c new file mode 100644 index 000000000..d2b687e86 --- /dev/null +++ b/arch/x86/loader/strstr.c @@ -0,0 +1,73 @@ +/* $NetBSD: strstr.c,v 1.1 2005/12/20 19:28:52 christos Exp $ */ + +/*- + * Copyright (c) 1990, 1993 + * The Regents of the University of California. All rights reserved. + * + * This code is derived from software contributed to Berkeley by + * Chris Torek. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of the University nor the names of its contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +/* + * The code has been taken from NetBSD (sys/libkern/strstr.c) and is consequently + * BSD-licensed. Unnecessary functions have been removed and all typedefs required + * have been added. + */ + +/* HermiCore prelude */ +#include +#include +#include +#include + +/* + * Find the first occurrence of find in s. + */ +char * +_strstr(s, find) + const char *s, *find; +{ + char c, sc; + size_t len; + + if (BUILTIN_EXPECT(!s, 0)) + return NULL; + if (BUILTIN_EXPECT(!find, 0)) + return NULL; + + if ((c = *find++) != 0) { + len = strlen(find); + do { + do { + if ((sc = *s++) == 0) + return (NULL); + } while (sc != c); + } while (strncmp(s, find, len) != 0); + s--; + } + return ((char *) s); +} diff --git a/arch/x86/loader/strtol.c b/arch/x86/loader/strtol.c new file mode 100644 index 000000000..639e11e9f --- /dev/null +++ b/arch/x86/loader/strtol.c @@ -0,0 +1,132 @@ +/*- + * Copyright (c) 1990, 1993 + * The Regents of the University of California. All rights reserved. + * + * This code is derived from software contributed to Berkeley by + * Chris Torek. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 4. Neither the name of the University nor the names of its contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * From: @(#)strtol.c 8.1 (Berkeley) 6/4/93 + */ + +/* + * The code has been taken from FreeBSD (sys/libkern/strtol.c) and is consequently + * BSD-licensed. Unnecessary functions have been removed and all typedefs required + * have been added. + */ + +/* HermitCore prelude */ +#include +#include +#include + +/* + * Convert a string to a long integer. + * + * Ignores `locale' stuff. Assumes that the upper and lower case + * alphabets and digits are each contiguous. + */ +long +_strtol(nptr, endptr, base) + const char *nptr; + char **endptr; + int base; +{ + const char *s = nptr; + unsigned long acc; + unsigned char c; + unsigned long cutoff; + int neg = 0, any, cutlim; + + /* + * Skip white space and pick up leading +/- sign if any. + * If base is 0, allow 0x for hex and 0 for octal, else + * assume decimal; if base is already 16, allow 0x. + */ + do { + c = *s++; + } while (isspace(c)); + if (c == '-') { + neg = 1; + c = *s++; + } else if (c == '+') + c = *s++; + if ((base == 0 || base == 16) && + c == '0' && (*s == 'x' || *s == 'X')) { + c = s[1]; + s += 2; + base = 16; + } + if (base == 0) + base = c == '0' ? 8 : 10; + + /* + * Compute the cutoff value between legal numbers and illegal + * numbers. That is the largest legal value, divided by the + * base. An input number that is greater than this value, if + * followed by a legal input character, is too big. One that + * is equal to this value may be valid or not; the limit + * between valid and invalid numbers is then based on the last + * digit. For instance, if the range for longs is + * [-2147483648..2147483647] and the input base is 10, + * cutoff will be set to 214748364 and cutlim to either + * 7 (neg==0) or 8 (neg==1), meaning that if we have accumulated + * a value > 214748364, or equal but the next digit is > 7 (or 8), + * the number is too big, and we will return a range error. + * + * Set any if any `digits' consumed; make it negative to indicate + * overflow. + */ + cutoff = neg ? -(unsigned long)LONG_MIN : LONG_MAX; + cutlim = cutoff % (unsigned long)base; + cutoff /= (unsigned long)base; + for (acc = 0, any = 0;; c = *s++) { + if (!isascii(c)) + break; + if (isdigit(c)) + c -= '0'; + else if (isalpha(c)) + c -= isupper(c) ? 'A' - 10 : 'a' - 10; + else + break; + if (c >= base) + break; + if (any < 0 || acc > cutoff || (acc == cutoff && c > cutlim)) + any = -1; + else { + any = 1; + acc *= base; + acc += c; + } + } + if (any < 0) { + acc = neg ? LONG_MIN : LONG_MAX; + } else if (neg) + acc = -acc; + if (endptr != 0) + *((const char **)endptr) = any ? s - 1 : nptr; + return (acc); +} diff --git a/arch/x86/loader/uart.c b/arch/x86/loader/uart.c index 545780e25..5d0599843 100644 --- a/arch/x86/loader/uart.c +++ b/arch/x86/loader/uart.c @@ -90,33 +90,40 @@ #define UART_MCR_RTS 0x02 /* RTS complement */ #define UART_MCR_DTR 0x01 /* DTR complement */ -static uint8_t mmio = 0; -static size_t iobase = 0; +#define DEFAULT_UART_PORT 0 //0xc110 + +size_t uartport = 0; static inline unsigned char read_from_uart(uint32_t off) { uint8_t c; - if (mmio) - c = *((const volatile unsigned char*) (iobase + off)); - else - c = inportb(iobase + off); + if (uartport) + c = inportb(uartport + off); return c; } +static inline int is_transmit_empty(void) +{ + if (uartport) + return inportb(uartport + UART_LSR) & 0x20; + + return 1; +} + static void write_to_uart(uint32_t off, unsigned char c) { - if (mmio) - *((volatile unsigned char*) (iobase + off)) = c; - else - outportb(iobase + off, c); + while (is_transmit_empty() == 0) ; + + if (uartport) + outportb(uartport + off, c); } /* Puts a single character on a serial device */ int uart_putchar(unsigned char c) { - if (!iobase) + if (!uartport) return 0; write_to_uart(UART_TX, c); @@ -129,7 +136,7 @@ int uart_puts(const char *text) { size_t i, len = strlen(text); - if (!iobase) + if (!uartport) return 0; for (i = 0; i < len; i++) @@ -140,19 +147,12 @@ int uart_puts(const char *text) static int uart_config(void) { - /* - * enable FIFOs - * clear RX and TX FIFO - * set irq trigger to 8 bytes - */ - write_to_uart(UART_FCR, UART_FCR_ENABLE_FIFO | UART_FCR_CLEAR_RCVR | UART_FCR_CLEAR_XMIT | UART_FCR_TRIGGER_1); + if (!uartport) + return 0; /* disable interrupts */ write_to_uart(UART_IER, 0); - /* DTR + RTS */ - write_to_uart(UART_MCR, UART_MCR_DTR|UART_MCR_RTS); - /* * 8bit word length * 1 stop bit @@ -165,110 +165,39 @@ static int uart_config(void) write_to_uart(UART_LCR, lcr); /* - * set baudrate to 115200 + * set baudrate to 38400 */ - uint32_t divisor = 1843200 / 115200; - write_to_uart(UART_DLL, divisor & 0xff); - write_to_uart(UART_DLM, (divisor >> 8) & 0xff); + write_to_uart(UART_DLL, 0x03); + write_to_uart(UART_DLM, 0x00); /* set DLAB=0 */ write_to_uart(UART_LCR, lcr & (~UART_LCR_DLAB)); + /* + * enable FIFOs + * clear RX and TX FIFO + * set irq trigger to 8 bytes + */ + write_to_uart(UART_FCR, UART_FCR_ENABLE_FIFO | UART_FCR_CLEAR_RCVR | UART_FCR_CLEAR_XMIT | UART_FCR_TRIGGER_1); + return 0; } -extern const void kernel_start; - -int uart_early_init(char* cmdline) +int uart_init(const char* cmdline) { -#if 1 - // default value of our QEMU configuration - iobase = 0xc110; -#else - if (BUILTIN_EXPECT(!cmdline, 0)) - return -EINVAL; + char* str; - char* str = strstr(cmdline, "uart="); - if (!str) - return -EINVAL; + if (!uartport && cmdline && ((str = strstr(cmdline, "uart=io:")) != NULL)) + uartport = strtol(str+8, (char **)NULL, 16); - if (strncmp(str, "uart=io:", 8) == 0) { - iobase = strtol(str+8, (char **)NULL, 16); - if (!iobase) - return -EINVAL; - mmio = 0; - } else if (strncmp(str, "uart=mmio:", 10) == 0) { - iobase = strtol(str+10, (char **)NULL, 16); - if (!iobase) - return -EINVAL; - if (iobase >= PAGE_MAP_ENTRIES*PAGE_SIZE) { - /* at this point we use the boot page table - * => IO address is not mapped - * => dirty hack, map device before the kernel - */ - int err; - size_t newaddr = ((size_t) &kernel_start - PAGE_SIZE); + if (!uartport) + uartport = DEFAULT_UART_PORT; - err = page_map_bootmap(newaddr & PAGE_MASK, iobase & PAGE_MASK, PG_GLOBAL | PG_ACCESSED | PG_DIRTY | PG_RW | PG_PCD); - if (BUILTIN_EXPECT(err, 0)) { - iobase = 0; - return err; - } - iobase = newaddr; - } - mmio = 1; - } -#endif + if (!uartport) + return 0; // configure uart return uart_config(); } -int uart_init(void) -{ -#ifdef CONFIG_PCI - pci_info_t pci_info; - uint32_t bar = 0; - - // Searching for Intel's UART device - if (pci_get_device_info(0x8086, 0x0936, iobase, &pci_info) == 0) - goto Lsuccess; - // Searching for Qemu's UART device - if (pci_get_device_info(0x1b36, 0x0002, iobase, &pci_info) == 0) - goto Lsuccess; - // Searching for Qemu's 2x UART device (pci-serial-2x) - if (pci_get_device_info(0x1b36, 0x0003, iobase, &pci_info) == 0) - goto Lsuccess; - // Searching for Qemu's 4x UART device (pci-serial-4x) - if (pci_get_device_info(0x1b36, 0x0004, iobase, &pci_info) == 0) - goto Lsuccess; - - return -1; - -Lsuccess: - iobase = pci_info.base[bar]; - //irq_install_handler(32+pci_info.irq, uart_handler); - if (pci_info.type[0]) { - mmio = 0; - kprintf("UART uses io address 0x%x\n", iobase); - } else { - mmio = 1; - page_map(iobase & PAGE_MASK, iobase & PAGE_MASK, 1, PG_GLOBAL | PG_ACCESSED | PG_DIRTY | PG_RW | PG_PCD); - kprintf("UART uses mmio address 0x%x\n", iobase); - vma_add(iobase, iobase + PAGE_SIZE, VMA_READ|VMA_WRITE); - } - - // configure uart - return uart_config(); -#else - // per default we use COM1... - if (!iobase) - iobase = 0x3F8; - mmio = 0; - - // configure uart - return uart_config(); -#endif -} - #endif diff --git a/arch/x86/loader/vga.c b/arch/x86/loader/vga.c deleted file mode 100644 index b69f0e714..000000000 --- a/arch/x86/loader/vga.c +++ /dev/null @@ -1,241 +0,0 @@ -/* - * Copyright (c) 2010, Stefan Lankes, RWTH Aachen University - * All rights reserved. - * - * Redistribution and use in source and binary forms, with or without - * modification, are permitted provided that the following conditions are met: - * * Redistributions of source code must retain the above copyright - * notice, this list of conditions and the following disclaimer. - * * Redistributions in binary form must reproduce the above copyright - * notice, this list of conditions and the following disclaimer in the - * documentation and/or other materials provided with the distribution. - * * Neither the name of the University nor the names of its contributors - * may be used to endorse or promote products derived from this - * software without specific prior written permission. - * - * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND - * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED - * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE - * DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE FOR ANY - * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES - * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; - * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND - * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT - * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS - * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - */ - -#include -#include -#include - -#ifdef CONFIG_UART - -#define VIDEO_MEM_ADDR 0xB8000 /* the video memory address */ - -/* - * These define our textpointer, our background and foreground - * colors (attributes), and x and y cursor coordinates - */ -static unsigned short *textmemptr; -static int attrib = 0x0F; -static int csr_x = 0, csr_y = 0; - -inline static unsigned short *memsetw(unsigned short *dest, unsigned short val, size_t count) -{ - size_t i; - - if (BUILTIN_EXPECT(!dest, 0)) - return dest; - - for (i = 0; i < count; i++) - dest[i] = val; - - return dest; -} - -/* Scrolls the screen */ -static void scroll(void) -{ - unsigned blank, temp; - - /* - * A blank is defined as a space... we need to give it - * backcolor too - */ - blank = 0x20 | (attrib << 8); - - /* Row 25 is the end, this means we need to scroll up */ - if (csr_y >= 25) { - - /* - * Move the current text chunk that makes up the screen - * - * back in the buffer by one line - */ - temp = csr_y - 25 + 1; - memcpy(textmemptr, textmemptr + temp * 80, - (25 - temp) * 80 * 2); - - /* - * Finally, we set the chunk of memory that occupies - * the last line of text to our 'blank' character - */ - memsetw(textmemptr + (25 - temp) * 80, blank, 80); - csr_y = 25 - 1; - } -} - -/* - * Updates the hardware cursor: the little blinking line - * on the screen under the last character pressed! - */ -static void move_csr(void) -{ - unsigned temp; - - /* - * The equation for finding the index in a linear - * chunk of memory can be represented by: - * Index = [(y * width) + x] */ - temp = csr_y * 80 + csr_x; - - /* - * This sends a command to indicies 14 and 15 in the - * CRT Control Register of the VGA controller. These - * are the high and low bytes of the index that show - * where the hardware cursor is to be 'blinking'. To - * learn more, you should look up some VGA specific - * programming documents. A great start to graphics: - * http://www.brackeen.com/home/vga - */ - outportb(0x3D4, 14); - outportb(0x3D5, temp >> 8); - outportb(0x3D4, 15); - outportb(0x3D5, temp); -} - -/* Clears the screen */ -void vga_clear(void) -{ - unsigned blank; - int i; - - /* - * Again, we need the 'short' that will be used to - * represent a space with color - */ - blank = 0x20 | (attrib << 8); - - /* - * Fills the entire screen with spaces in our current - * color - **/ - for (i = 0; i < 25; i++) - memsetw(textmemptr + i * 80, blank, 80); - - /* - * Update out virtual cursor, and then move the - * hardware cursor - */ - csr_x = 0; - csr_y = 0; - move_csr(); -} - -/* Puts a single character on the screen */ -int vga_putchar(unsigned char c) -{ - unsigned short *where; - unsigned att = attrib << 8; - - /* Handle a backspace by moving the cursor back one space */ - if (c == 0x08) { - if (csr_x != 0) - csr_x--; - } - - /* - * Handles a tab by incrementing the cursor's x, but only - * to a point that will make it divisible by 8 - */ - else if (c == 0x09) { - csr_x = (csr_x + 8) & ~(8 - 1); - } - - /* - * Handles a 'Carriage Return', which simply brings the - * cursor back to the margin - */ - else if (c == '\r') { - csr_x = 0; - } - - /* - * We handle our newlines the way DOS and BIOS do: we - * treat it as if a 'CR' was there also, so we bring the - * cursor to the margin and increment the 'y' value - */ - else if (c == '\n') { - csr_x = 0; - csr_y++; - } - - /* - * Any character greater than and including the space is a - * printable character. The equation for finding the index - * in a linear chunk of memory can be represented by: - * Index = [(y * width) + x] - */ - else if (c >= ' ') { - where = textmemptr + (csr_y * 80 + csr_x); - *where = c | att; /* Character AND attributes: color */ - csr_x++; - } - - /* - * If the cursor has reached the edge of the screen's width, we - * insert a new line in there - */ - if (csr_x >= 80) { - csr_x = 0; - csr_y++; - } - - /* Scroll the screen if needed, and finally move the cursor */ - scroll(); - move_csr(); - - return (int) c; -} - -/* Uses the routine above to output a string... */ -int vga_puts(const char *text) -{ - size_t i; - - for (i = 0; i < strlen(text); i++) - vga_putchar(text[i]); - - return i-1; -} - -/* Sets the forecolor and backcolor we will use */ -//void settextcolor(unsigned char forecolor, unsigned char backcolor) -//{ - - /* - * Top 4 bytes are the background, bottom 4 bytes - * are the foreground color - */ -// attrib = (backcolor << 4) | (forecolor & 0x0F); -//} - -/* Sets our text-mode VGA pointer, then clears the screen for us */ -void vga_init(void) -{ - textmemptr = (unsigned short *)VIDEO_MEM_ADDR; - vga_clear(); -} - -#endif diff --git a/arch/x86/mm/Makefile b/arch/x86/mm/Makefile deleted file mode 100644 index 2f9b1834a..000000000 --- a/arch/x86/mm/Makefile +++ /dev/null @@ -1,4 +0,0 @@ -C_source := page.c -MODULE := arch_x86_mm - -include $(TOPDIR)/Makefile.inc diff --git a/mm/hbmemory.c b/arch/x86/mm/hbmemory.c similarity index 100% rename from mm/hbmemory.c rename to arch/x86/mm/hbmemory.c diff --git a/mm/memory.c b/arch/x86/mm/memory.c similarity index 94% rename from mm/memory.c rename to arch/x86/mm/memory.c index 3bf6b945c..cda906e07 100644 --- a/mm/memory.c +++ b/arch/x86/mm/memory.c @@ -37,6 +37,8 @@ #include #include +#define GAP_BELOW 0x100000ULL + extern uint64_t base; extern uint64_t limit; @@ -51,7 +53,6 @@ typedef struct free_list { * maintaining a value, rather their address is their value. */ extern const void kernel_start; -extern const void kernel_end; static spinlock_t list_lock = SPINLOCK_INIT; @@ -245,7 +246,6 @@ void page_free(void* viraddr, size_t sz) int memory_init(void) { - size_t image_size = (size_t) &kernel_end - (size_t) &kernel_start; int ret = 0; // enable paging and map Multiboot modules etc. @@ -272,8 +272,8 @@ int memory_init(void) LOG_INFO("Free region 0x%zx - 0x%zx\n", start_addr, end_addr); - if ((start_addr <= base) && (end_addr >= PAGE_2M_FLOOR(base+image_size))) { - init_list.start = PAGE_2M_FLOOR(base+image_size); + if ((start_addr <= base) && (end_addr >= PAGE_2M_FLOOR((size_t) &kernel_start + image_size))) { + init_list.start = PAGE_2M_FLOOR((size_t) &kernel_start + image_size); init_list.end = end_addr; LOG_INFO("Add region 0x%zx - 0x%zx\n", init_list.start, init_list.end); @@ -295,7 +295,6 @@ int memory_init(void) atomic_int64_add(&total_pages, (limit-base) >> PAGE_BITS); atomic_int64_add(&total_available_pages, (limit-base) >> PAGE_BITS); - //initialize free list init_list.start = PAGE_2M_FLOOR(base + image_size); init_list.end = limit; } @@ -332,8 +331,16 @@ int memory_init(void) end_addr = base; // ignore everything below 1M => reserve for I/O devices - if ((start_addr < (size_t) 0x100000)) - start_addr = 0x100000; + if ((start_addr < GAP_BELOW)) + start_addr = GAP_BELOW; + + if (start_addr < (size_t)mb_info) + start_addr = PAGE_FLOOR((size_t)mb_info); + + if ((mb_info->flags & MULTIBOOT_INFO_CMDLINE) && cmdline) { + if (start_addr < (size_t) cmdline+cmdsize) + start_addr = PAGE_FLOOR((size_t) cmdline+cmdsize); + } if (start_addr >= end_addr) continue; @@ -351,8 +358,6 @@ int memory_init(void) last->end = end_addr; } } - - //TODO: mb_info and mb_info->cmdline should be marked as reserevd } } diff --git a/arch/x86/mm/page.c b/arch/x86/mm/page.c index ed5446ae9..f381daf46 100644 --- a/arch/x86/mm/page.c +++ b/arch/x86/mm/page.c @@ -49,7 +49,6 @@ /* Note that linker symbols are not variables, they have no memory * allocated for maintaining a value, rather their address is their value. */ extern const void kernel_start; -//extern const void kernel_end; /// This page is reserved for copying #define PAGE_TMP (PAGE_FLOOR((size_t) &kernel_start) - PAGE_SIZE) @@ -81,6 +80,7 @@ static size_t* const self[PAGE_LEVELS] = { (size_t *) 0xFFFFFFFFFFFFF000 }; +#if 0 /** An other self-reference for page_map_copy() */ static size_t * const other[PAGE_LEVELS] = { (size_t *) 0xFFFFFF0000000000, @@ -89,17 +89,30 @@ static size_t * const other[PAGE_LEVELS] = { (size_t *) 0xFFFFFFFFFFFFE000 }; #endif +#endif static uint8_t expect_zeroed_pages = 0; size_t virt_to_phys(size_t addr) { - size_t vpn = addr >> PAGE_BITS; // virtual page number - size_t entry = self[0][vpn]; // page table entry - size_t off = addr & ~PAGE_MASK; // offset within page - size_t phy = entry & PAGE_MASK; // physical page frame number + if ((addr > (size_t) &kernel_start) && + (addr <= PAGE_2M_FLOOR((size_t) &kernel_start + image_size))) + { + size_t vpn = addr >> (PAGE_2M_BITS); // virtual page number + size_t entry = self[1][vpn]; // page table entry + size_t off = addr & ~PAGE_2M_MASK; // offset within page + size_t phy = entry & PAGE_2M_MASK; // physical page frame number - return phy | off; + return phy | off; + + } else { + size_t vpn = addr >> PAGE_BITS; // virtual page number + size_t entry = self[0][vpn]; // page table entry + size_t off = addr & ~PAGE_MASK; // offset within page + size_t phy = entry & PAGE_MASK; // physical page frame number + + return phy | off; + } } /* @@ -141,15 +154,15 @@ int __page_map(size_t viraddr, size_t phyaddr, size_t npages, size_t bits, uint8 if (!(self[lvl][vpn] & PG_PRESENT)) { /* There's no table available which covers the region. * Therefore we need to create a new empty table. */ - size_t phyaddr = get_pages(1); - if (BUILTIN_EXPECT(!phyaddr, 0)) + size_t paddr = get_pages(1); + if (BUILTIN_EXPECT(!paddr, 0)) goto out; /* Reference the new table within its parent */ #if 0 - self[lvl][vpn] = phyaddr | bits | PG_PRESENT | PG_USER | PG_RW | PG_ACCESSED; + self[lvl][vpn] = paddr | bits | PG_PRESENT | PG_USER | PG_RW | PG_ACCESSED | PG_DIRTY; #else - self[lvl][vpn] = (phyaddr | bits | PG_PRESENT | PG_USER | PG_RW | PG_ACCESSED) & ~PG_XD; + self[lvl][vpn] = (paddr | bits | PG_PRESENT | PG_USER | PG_RW | PG_ACCESSED | PG_DIRTY) & ~PG_XD; #endif /* Fill new table with zeros */ @@ -165,7 +178,7 @@ int __page_map(size_t viraddr, size_t phyaddr, size_t npages, size_t bits, uint8 send_ipi = flush = 1; } - self[lvl][vpn] = phyaddr | bits | PG_PRESENT | PG_ACCESSED; + self[lvl][vpn] = phyaddr | bits | PG_PRESENT | PG_ACCESSED | PG_DIRTY; if (flush) /* There's already a page mapped at this address. @@ -312,10 +325,16 @@ int page_init(void) LOG_INFO("Detect Go runtime! Consequently, HermitCore zeroed heap.\n"); } - if (mb_info && ((mb_info->cmdline & PAGE_MASK) != ((size_t) mb_info & PAGE_MASK))) { - LOG_INFO("Map multiboot cmdline 0x%x into the virtual address space\n", mb_info->cmdline); - page_map((size_t) mb_info->cmdline & PAGE_MASK, mb_info->cmdline & PAGE_MASK, 1, PG_GLOBAL|PG_RW|PG_PRESENT); - } + if (mb_info && (mb_info->flags & MULTIBOOT_INFO_CMDLINE) && (cmdline)) + { + size_t i = 0; + + while(((size_t) cmdline + i) <= ((size_t) cmdline + cmdsize)) + { + page_map(((size_t) cmdline + i) & PAGE_MASK, ((size_t) cmdline + i) & PAGE_MASK, 1, PG_GLOBAL|PG_RW|PG_PRESENT); + i += PAGE_SIZE; + } + } else cmdline = 0; /* Replace default pagefault handler */ irq_uninstall_handler(14); diff --git a/arch/x86/mm/vma.c b/arch/x86/mm/vma.c new file mode 100644 index 000000000..ad58d1b79 --- /dev/null +++ b/arch/x86/mm/vma.c @@ -0,0 +1,61 @@ +/* + * Copyright (c) 2014, Steffen Vogel, RWTH Aachen University + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * * Neither the name of the University nor the names of its contributors + * may be used to endorse or promote products derived from this + * software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#include +#include +#include +#include + +int vma_arch_init(void) +{ + int ret = 0; + + if (mb_info) { + ret = vma_add((size_t)mb_info & PAGE_MASK, ((size_t)mb_info & PAGE_MASK) + PAGE_SIZE, VMA_READ|VMA_WRITE); + if (BUILTIN_EXPECT(ret, 0)) + goto out; + + if ((mb_info->flags & MULTIBOOT_INFO_CMDLINE) && cmdline) { + LOG_INFO("vma_arch_init: map cmdline %p (size 0x%zd)", cmdline, cmdsize); + + size_t i = 0; + while(((size_t) cmdline + i) < ((size_t) cmdline + cmdsize)) + { + if ((((size_t)cmdline + i) & PAGE_MASK) != ((size_t) mb_info & PAGE_MASK)) { + ret = vma_add(((size_t)cmdline + i) & PAGE_MASK, (((size_t)cmdline + i) & PAGE_MASK) + PAGE_SIZE, VMA_READ|VMA_WRITE); + if (BUILTIN_EXPECT(ret, 0)) + goto out; + } + + i += PAGE_SIZE; + } + } + } + +out: + return ret; +} diff --git a/cmake/HermitCore-Application.cmake b/cmake/HermitCore-Application.cmake new file mode 100644 index 000000000..a971c1cf4 --- /dev/null +++ b/cmake/HermitCore-Application.cmake @@ -0,0 +1,9 @@ +include(${CMAKE_CURRENT_LIST_DIR}/HermitCore.cmake) +include_guard() + +add_compile_options(${HERMIT_APP_FLAGS}) + +# link against and include locally built libraries instead of the ones +# supplied with the toolchain, if built from top-level +link_directories(${LOCAL_PREFIX_ARCH_LIB_DIR}) +include_directories(BEFORE ${LOCAL_PREFIX_ARCH_INCLUDE_DIR}) diff --git a/cmake/HermitCore-Configuration.cmake b/cmake/HermitCore-Configuration.cmake new file mode 100644 index 000000000..69876b157 --- /dev/null +++ b/cmake/HermitCore-Configuration.cmake @@ -0,0 +1,32 @@ +set(PACKAGE_VERSION "0.2" CACHE STRING + "HermitCore current version") + +set(MAX_CORES "512" CACHE STRING + "Maximum number of cores that can be managed") + +set(MAX_TASKS "((MAX_CORES * 2) + 2)" CACHE STRING + "Maximum number of tasks") + +set(MAX_ISLE "8" CACHE STRING + "Maximum number of NUMA isles") + +set(MAX_FNAME "128" CACHE STRING + "Define the maximum length of a file name") + +set(KERNEL_STACK_SIZE 8192 CACHE STRING + "Kernel stack size in bytes") + +set(DEFAULT_STACK_SIZE 262144 CACHE STRING + "Task stack size in bytes") + +option(DYNAMIC_TICKS + "Don't use a periodic timer event to keep track of time" ON) + +option(SAVE_FPU + "Save FPU registers on context switch" ON) + +option(HAVE_ARCH_MEMSET "Use machine specific version of memset" OFF) +option(HAVE_ARCH_MEMCPY "Use machine specific version of memcpy" OFF) +option(HAVE_ARCH_STRLEN "Use machine specific version of strlen" OFF) +option(HAVE_ARCH_STRCPY "Use machine specific version of strcpy" OFF) +option(HAVE_ARCH_STRNCPY "Use machine specific version of strncpy" OFF) diff --git a/cmake/HermitCore-Paths.cmake b/cmake/HermitCore-Paths.cmake new file mode 100644 index 000000000..da860e929 --- /dev/null +++ b/cmake/HermitCore-Paths.cmake @@ -0,0 +1,35 @@ +include(${CMAKE_CURRENT_LIST_DIR}/HermitCore-Utils.cmake) +# no include guard here because we have to include this file twice to correctly +# set CMAKE_INSTALL_PREFIX + +# root of HermitCore project +set(HERMIT_ROOT ${CMAKE_CURRENT_LIST_DIR}/..) + +# set default install prefix if user doesn't specify one +if(${CMAKE_INSTALL_PREFIX_INITIALIZED_TO_DEFAULT}) + # See CMake docs for reference: + # https://cmake.org/cmake/help/v3.7/variable/CMAKE_INSTALL_PREFIX_INITIALIZED_TO_DEFAULT.html + set(CMAKE_INSTALL_PREFIX /opt/hermit CACHE PATH "..." FORCE) +endif() + +# we install 3rd party libraries to an intermediate directory and relocate +# them here later when installing the whole project +if(NOT LOCAL_PREFIX_BASE_DIR) + # will be injected into external project because CMAKE_BINARY_DIR will be + # different there + set(LOCAL_PREFIX_BASE_DIR ${CMAKE_BINARY_DIR}/local_prefix) +endif() + +# during build process libraries and external projects will be deployed into +# this directory structure +set(LOCAL_PREFIX_DIR ${LOCAL_PREFIX_BASE_DIR}/${CMAKE_INSTALL_PREFIX}) +set(LOCAL_PREFIX_ARCH_DIR ${LOCAL_PREFIX_DIR}/${TARGET_ARCH}) +set(LOCAL_PREFIX_ARCH_INCLUDE_DIR ${LOCAL_PREFIX_ARCH_DIR}/include) + +# when building applications within the HermitCore project (tests, ...) they +# will link prefarably against libraries in this directory in order to test +# changes in the kernel +set(LOCAL_PREFIX_ARCH_LIB_DIR ${LOCAL_PREFIX_ARCH_DIR}/lib) + +# generated configs will be put here +set(GENERATED_CONFIG_DIR ${CMAKE_BINARY_DIR}/include) diff --git a/cmake/HermitCore-Toolchain-x86-bootstrap.cmake b/cmake/HermitCore-Toolchain-x86-bootstrap.cmake new file mode 100644 index 000000000..4471196e2 --- /dev/null +++ b/cmake/HermitCore-Toolchain-x86-bootstrap.cmake @@ -0,0 +1,9 @@ +include(${CMAKE_CURRENT_LIST_DIR}/HermitCore-Toolchain-x86.cmake) +include_guard() + +set(CMAKE_C_COMPILER_WORKS 1 CACHE INTERNAL "") +set(CMAKE_CXX_COMPILER_WORKS 1 CACHE INTERNAL "") + +# bootstrap toolchain cannot compile neither Go nor Fortran +unset(CMAKE_Go_COMPILER) +unset(CMAKE_Fortran_COMPILER) diff --git a/cmake/HermitCore-Toolchain-x86.cmake b/cmake/HermitCore-Toolchain-x86.cmake new file mode 100644 index 000000000..ec875cfc5 --- /dev/null +++ b/cmake/HermitCore-Toolchain-x86.cmake @@ -0,0 +1,26 @@ +include(${CMAKE_CURRENT_LIST_DIR}/HermitCore-Utils.cmake) +include_guard() + +# let user provide a different path to the toolchain +set_default(TOOLCHAIN_BIN_DIR /opt/hermit/bin) + +set(TARGET_ARCH x86_64-hermit) + +set(CMAKE_SYSTEM_NAME Generic) + +# point CMake to our toolchain +set(CMAKE_C_COMPILER ${TOOLCHAIN_BIN_DIR}/${TARGET_ARCH}-gcc) +set(CMAKE_CXX_COMPILER ${TOOLCHAIN_BIN_DIR}/${TARGET_ARCH}-g++) +set(CMAKE_Fortran_COMPILER ${TOOLCHAIN_BIN_DIR}/${TARGET_ARCH}-gfortran) +set(CMAKE_Go_COMPILER ${TOOLCHAIN_BIN_DIR}/${TARGET_ARCH}-gccgo) + +# hinting the prefix and location is needed in order to correctly detect +# binutils +set(_CMAKE_TOOLCHAIN_PREFIX "${TARGET_ARCH}-") +set(_CMAKE_TOOLCHAIN_LOCATION ${TOOLCHAIN_BIN_DIR}) + +option(HAVE_ARCH_MEMSET "Use machine specific version of memset" ON) +option(HAVE_ARCH_MEMCPY "Use machine specific version of memcpy" ON) +option(HAVE_ARCH_STRLEN "Use machine specific version of strlen" ON) +option(HAVE_ARCH_STRCPY "Use machine specific version of strcpy" ON) +option(HAVE_ARCH_STRNCPY "Use machine specific version of strncpy" ON) diff --git a/cmake/HermitCore-Utils.cmake b/cmake/HermitCore-Utils.cmake new file mode 100644 index 000000000..31c2adfb1 --- /dev/null +++ b/cmake/HermitCore-Utils.cmake @@ -0,0 +1,142 @@ +macro(include_guard) + if(DEFINED "_INCLUDE_GUARD_${CMAKE_CURRENT_LIST_FILE}") + return() + endif() + set("_INCLUDE_GUARD_${CMAKE_CURRENT_LIST_FILE}" INCLUDED) +endmacro(include_guard) + +macro(add_kernel_module_sources MODULE SOURCE_GLOB) + file(GLOB SOURCES "${SOURCE_GLOB}") + + if("${SOURCES}" STREQUAL "") + message(FATAL_ERROR "Module '${MODULE}' has no sources") + endif() + + # make sure modules are unique, this is needed of multiple sources + # are added to the same module + list(APPEND _KERNEL_MODULES "${MODULE}") + list(REMOVE_DUPLICATES _KERNEL_MODULES) + + # append sources for module + list(APPEND "_KERNEL_SOURCES_${MODULE}" "${SOURCES}") +endmacro(add_kernel_module_sources) + + +macro(get_kernel_module_sources VAR MODULE) + set(${VAR} ${_KERNEL_SOURCES_${MODULE}}) +endmacro(get_kernel_module_sources) + + +macro(get_kernel_modules VAR) + set(${VAR} ${_KERNEL_MODULES}) +endmacro(get_kernel_modules) + + +# find program in /toolchain/dir/prefix-NAME, only supply NAME +function(find_toolchain_program NAME) + + string(TOUPPER "${NAME}" NAME_UPPER) + string(TOLOWER "${NAME}" NAME_LOWER) + + set(VARNAME "CMAKE_${NAME_UPPER}") + + find_program(${VARNAME} + NAMES ${_CMAKE_TOOLCHAIN_PREFIX}${NAME_LOWER} + HINTS ${TOOLCHAIN_BIN_DIR}) + + if(NOT ${VARNAME}) + message(FATAL_ERROR + "Cannot find ${_CMAKE_TOOLCHAIN_PREFIX}${NAME_LOWER}") + endif() +endfunction(find_toolchain_program) + + +macro(set_parent VAR VALUE) + set(${VAR} ${VALUE} PARENT_SCOPE) + set(${VAR} ${VALUE}) +endmacro(set_parent) + +function(get_cmd_variables VAR) + set(_OUTPUT "") + + get_cmake_property(vs VARIABLES) + + foreach(v ${vs}) + get_property(_HELPSTRING + CACHE ${v} + PROPERTY HELPSTRING) + if("${_HELPSTRING}" STREQUAL "No help, variable specified on the command line.") + list(APPEND _OUTPUT "${v}") + endif() + endforeach() + + set(${VAR} ${_OUTPUT} PARENT_SCOPE) +endfunction(get_cmd_variables) + +# any additional parameters will be handed over to the cmake command that the +# external project is invoked with +function(build_external NAME PATH DEPENDS) + if("${NAME}" IN_LIST PROFILE_APPS) + set(DO_PROFILING "-DPROFILING=true") + endif() + + # pass through all command line variables + get_cmd_variables(CMD_VAR_NAMES) + foreach(var ${CMD_VAR_NAMES}) + set(CMD_VARS ${CMD_VARS} -D${var}=${${var}}) + endforeach() + + ExternalProject_Add(${NAME} + SOURCE_DIR ${PATH} + BUILD_ALWAYS 1 + DEPENDS ${DEPENDS} + INSTALL_COMMAND + ${CMAKE_COMMAND} --build + --target install -- + DESTDIR=${LOCAL_PREFIX_BASE_DIR} + CMAKE_ARGS + -DCMAKE_INSTALL_PREFIX=${CMAKE_INSTALL_PREFIX} + -DLOCAL_PREFIX_BASE_DIR=${LOCAL_PREFIX_BASE_DIR} + -DCMAKE_INSTALL_MESSAGE=NEVER + --no-warn-unused-cli + ${DO_PROFILING} + ${CMD_VARS} + ${ARGN}) + + ExternalProject_Add_Step(${NAME} relink + COMMAND find . -maxdepth 1 -type f -executable -exec rm {} "\\\;" + DEPENDEES configure + DEPENDERS build + WORKING_DIRECTORY ) + + ExternalProject_Add_StepDependencies(${NAME} relink ${DEPENDS}) +endfunction(build_external) + + +# additional arguments are be treated as targets that will be excluded +function(install_local_targets PATH) + get_property(_TARGETS + DIRECTORY . + PROPERTY BUILDSYSTEM_TARGETS) + + if(NOT "${ARGN}" STREQUAL "") + list(REMOVE_ITEM _TARGETS ${ARGN}) + endif() + + install(TARGETS ${_TARGETS} + DESTINATION ${TARGET_ARCH}/${PATH}) + + # if there are any .map files for profiling, install them too + foreach(TARGET ${_TARGETS}) + install(FILES $.map + DESTINATION ${TARGET_ARCH}/${PATH} + OPTIONAL) + endforeach() +endfunction(install_local_targets) + +# set variable if not yet set +macro(set_default VARNAME) + if(NOT ${VARNAME}) + set(${VARNAME} ${ARGN}) + endif() +endmacro(set_default) diff --git a/cmake/HermitCore.cmake b/cmake/HermitCore.cmake new file mode 100644 index 000000000..4d6ac9d00 --- /dev/null +++ b/cmake/HermitCore.cmake @@ -0,0 +1,90 @@ +include(${CMAKE_CURRENT_LIST_DIR}/HermitCore-Utils.cmake) +include_guard() + +include(${CMAKE_CURRENT_LIST_DIR}/HermitCore-Paths.cmake) +include(${CMAKE_CURRENT_LIST_DIR}/HermitCore-Configuration.cmake) + +# scripts to detect HermitCore Go compiler +list(APPEND CMAKE_MODULE_PATH ${CMAKE_CURRENT_LIST_DIR}/golang/) + +if(NOT HERMIT_ARCH) + set(HERMIT_ARCH x86) +endif() + +if(PROFILING) + # link everything against XRay + link_libraries(-lxray) + + # generate symbol map file for XRay to resolve function names + link_libraries(-Wl,-Map=$.map) + + # enable profiling with XRay + add_compile_options(-falign-functions=32 -finstrument-functions + -finstrument-functions-exclude-function-list=_mm_pause,_mm_setcsr,_mm_getcsr) + add_definitions(-DXRAY -DXRAY_DISABLE_BROWSER_INTEGRATION + -DXRAY_NO_DEMANGLE -DXRAY_ANNOTATE) +endif() + +# use default toolchain if not specified by user +if(NOT CMAKE_TOOLCHAIN_FILE) + if(BOOTSTRAP) + # use bootstrap toolchain if requested + set(_BOOTSTRAP_ARCH_SUFFIX -bootstrap) + endif() + set(CMAKE_TOOLCHAIN_FILE ${CMAKE_CURRENT_LIST_DIR}/HermitCore-Toolchain-${HERMIT_ARCH}${_BOOTSTRAP_ARCH_SUFFIX}.cmake) +endif() + +# NASM detection will change binary format depending on host system, but +# we only want to generate elf64 for HermitCore +# Note: Has to be set *before* ASM_NASM is enabled +set(CMAKE_ASM_NASM_OBJECT_FORMAT elf64) + +enable_language(ASM_NASM) + +# NASM hack, because it requires include paths to have a trailing /, whereas +# CMake explicitly will remove it when adding includes the usual way +# Note: Has to be set *after* ASM_NASM is enabled +set(CMAKE_ASM_NASM_FLAGS + "${CMAKE_ASM_NASM_FLAGS} -I ${CMAKE_BINARY_DIR}/include/") + +set(HERMIT_KERNEL_FLAGS + -m64 -Wall -O2 -mno-red-zone + -fno-var-tracking-assignments -fstrength-reduce + -fomit-frame-pointer -finline-functions -ffreestanding + -nostdinc -fno-stack-protector -mno-sse -mno-mmx + -mno-sse2 -mno-3dnow -mno-avx + -fno-delete-null-pointer-checks + -falign-jumps=1 -falign-loops=1 + -mno-80387 -mno-fp-ret-in-387 -mskip-rax-setup + -fno-common -Wframe-larger-than=1024 + -fno-strict-aliasing -fno-asynchronous-unwind-tables + -fno-strict-overflow -maccumulate-outgoing-args) + +set(HERMIT_APP_FLAGS + -m64 -mtls-direct-seg-refs -O3 -ftree-vectorize) + +if(MTUNE) + set(HERMIT_KERNEL_FLAGS ${HERMIT_KERNEL_FLAGS} -mtune=${MTUNE}) + set(HERMIT_APP_FLAGS ${HERMIT_APP_FLAGS} -mtune=${MTUNE}) +endif() + +set(HERMIT_KERNEL_INCLUDES + ${CMAKE_BINARY_DIR}/include + ${HERMIT_ROOT}/include + ${HERMIT_ROOT}/arch/${HERMIT_ARCH}/include + ${HERMIT_ROOT}/lwip/src/include + ${HERMIT_ROOT}/drivers) + +# HACK: when CMake detects compilers it taints CMAKE_INSTALL_PREFIX, so in +# order to rely on that variable (we redefine it), enable all languages +# here and source pathes again. +# +# Furthermore this will produce a sensible error message if the toolchain cannot +# be found. +if(NOT BOOTSTRAP) + enable_language(C CXX Fortran Go) + include(${CMAKE_CURRENT_LIST_DIR}/HermitCore-Paths.cmake) +endif() + +# find elfedit, CMake doesn't use this program, so we have to find it ourself +find_toolchain_program(elfedit) diff --git a/cmake/README.md b/cmake/README.md new file mode 100644 index 000000000..361a24f9c --- /dev/null +++ b/cmake/README.md @@ -0,0 +1,67 @@ +HermitCore CMake build system +============================= + +HermitCore requires at least CMake version `3.7`, which (at the time of +introduction) is not yet available on most Linux distributions. We therefore +provide a script `cmake/local-cmake.sh` that fetches precompiled binaries from +the CMake project and installs them locally in `cmake/cmake-3.7*`. Only when +sourced for the first time it will download CMake, on further runs it detects +the existing download and adds it to `PATH` automatically. + +```bash +$ . cmake/local-cmake.sh +-- Downloading CMake +cmake-3.7.2-Linux-x 100%[=================>] 29,26M 837KB/s in 19s +-- Unpacking CMake +-- Local CMake v3.7.2 installed to cmake/cmake-3.7.2-Linux-x86_64 +-- Next time you source this script, no download will be neccessary +$ which cmake +/home/[...]/HermitCore/cmake/cmake-3.7.2-Linux-x86_64/bin/cmake +``` + +## Directory structure + +``` +cmake/ +├── golang +│   ├── CMakeDetermineGoCompiler.cmake +│   ├── CMakeGoCompiler.cmake.in +│   ├── CMakeGoInformation.cmake +│   └── CMakeTestGoCompiler.cmake +├── HermitCore-Application.cmake +├── HermitCore.cmake +├── HermitCore-Paths.cmake +├── HermitCore-Toolchain-x86.cmake +├── HermitCore-Utils.cmake +├── local-cmake.sh +└── README.md +``` + +## Additional language support + +Currently, HermitCore supports `C, C++, Fortran, Go` through Cmake. While the +former are supported and detected by CMake out-of-the-box, Go support has been +added manually for HermitCore. + +Adding a new language requires you to provide CMake hints where to find the +toolchain and then how to compile and link binaries. The Go support in +`cmake/golang` may serve as an example on how to add a new language. + +To finally enable the language it has to be added to CMake's module path in +`cmake/HermitCore.cmake`: + +``` +# scripts to detect HermitCore Go compiler +list(APPEND CMAKE_MODULE_PATH ${CMAKE_CURRENT_LIST_DIR}/golang/) + +# scripts to detect new language +list(APPEND CMAKE_MODULE_PATH ${CMAKE_CURRENT_LIST_DIR}/new-language/) +``` + + +## User applications + +You just have to include `HermitCore-Application.cmake` before the `project()` +command in your `CMakeLists.txt` in order to build applications for HermitCore. +For configuration parameters of the project, please consult the `README.md` in +the root of this repository. diff --git a/cmake/golang/CMakeDetermineGoCompiler.cmake b/cmake/golang/CMakeDetermineGoCompiler.cmake new file mode 100644 index 000000000..ae5591881 --- /dev/null +++ b/cmake/golang/CMakeDetermineGoCompiler.cmake @@ -0,0 +1,43 @@ +# Distributed under the OSI-approved BSD 3-Clause License. See accompanying +# file Copyright.txt or https://cmake.org/licensing for details. + +# determine the compiler to use for Go programs +# NOTE, a generator may set CMAKE_Go_COMPILER before +# loading this file to force a compiler. + +if(NOT CMAKE_Go_COMPILER) + # prefer the environment variable CC + if(NOT $ENV{GO_COMPILER} STREQUAL "") + get_filename_component(CMAKE_Go_COMPILER_INIT $ENV{GO_COMPILER} PROGRAM PROGRAM_ARGS CMAKE_Go_FLAGS_ENV_INIT) + if(CMAKE_Go_FLAGS_ENV_INIT) + set(CMAKE_Go_COMPILER_ARG1 "${CMAKE_Go_FLAGS_ENV_INIT}" CACHE STRING "First argument to Go compiler") + endif() + if(NOT EXISTS ${CMAKE_Go_COMPILER_INIT}) + message(SEND_ERROR "Could not find compiler set in environment variable GO_COMPILER:\n$ENV{GO_COMPILER}.") + endif() + endif() + + set(Go_BIN_PATH + $ENV{GOPATH} + $ENV{GOROOT} + $ENV{GOROOT}/../bin + $ENV{GO_COMPILER} + /usr/bin + /usr/local/bin + ) + # if no compiler has been specified yet, then look for one + if(CMAKE_Go_COMPILER_INIT) + set(CMAKE_Go_COMPILER ${CMAKE_Go_COMPILER_INIT} CACHE PATH "Go Compiler") + else() + find_program(CMAKE_Go_COMPILER + NAMES go + PATHS ${Go_BIN_PATH} + ) + endif() +endif() +mark_as_advanced(CMAKE_Go_COMPILER) + +# configure variables set in this file for fast reload later on +configure_file(${CMAKE_CURRENT_LIST_DIR}/CMakeGoCompiler.cmake.in + ${CMAKE_PLATFORM_INFO_DIR}/CMakeGoCompiler.cmake @ONLY) +set(CMAKE_Go_COMPILER_ENV_VAR "GO_COMPILER") diff --git a/cmake/golang/CMakeGoCompiler.cmake.in b/cmake/golang/CMakeGoCompiler.cmake.in new file mode 100644 index 000000000..ece6be798 --- /dev/null +++ b/cmake/golang/CMakeGoCompiler.cmake.in @@ -0,0 +1,11 @@ +# Distributed under the OSI-approved BSD 3-Clause License. See accompanying +# file Copyright.txt or https://cmake.org/licensing for details. + +set(CMAKE_Go_COMPILER "@CMAKE_Go_COMPILER@") +set(CMAKE_Go_COMPILER_LOADED 1) + +set(CMAKE_Go_SOURCE_FILE_EXTENSIONS go) +set(CMAKE_Go_LINKER_PREFERENCE 40) +set(CMAKE_Go_OUTPUT_EXTENSION .6) +set(CMAKE_Go_OUTPUT_EXTENSION_REPLACE 1) +set(CMAKE_Go_COMPILER_ENV_VAR "GO_COMPILER") diff --git a/cmake/golang/CMakeGoInformation.cmake b/cmake/golang/CMakeGoInformation.cmake new file mode 100644 index 000000000..e53558fa7 --- /dev/null +++ b/cmake/golang/CMakeGoInformation.cmake @@ -0,0 +1,30 @@ +# Distributed under the OSI-approved BSD 3-Clause License. See accompanying +# file Copyright.txt or https://cmake.org/licensing for details. + +# This should be included before the _INIT variables are +# used to initialize the cache. Since the rule variables +# have if blocks on them, users can still define them here. +# But, it should still be after the platform file so changes can +# be made to those values. + +if(CMAKE_USER_MAKE_RULES_OVERRIDE) + # Save the full path of the file so try_compile can use it. + include(${CMAKE_USER_MAKE_RULES_OVERRIDE} RESULT_VARIABLE _override) + set(CMAKE_USER_MAKE_RULES_OVERRIDE "${_override}") +endif() + +if(CMAKE_USER_MAKE_RULES_OVERRIDE_Go) + # Save the full path of the file so try_compile can use it. + include(${CMAKE_USER_MAKE_RULES_OVERRIDE_Go} RESULT_VARIABLE _override) + set(CMAKE_USER_MAKE_RULES_OVERRIDE_Go "${_override}") +endif() + +# refer: /usr/share/cmake-3.7/Modules/CMakeCInformation.cmake + +if(NOT CMAKE_Go_COMPILE_OBJECT) + set(CMAKE_Go_COMPILE_OBJECT " -o -c ") +endif() + +if(NOT CMAKE_Go_LINK_EXECUTABLE) + set(CMAKE_Go_LINK_EXECUTABLE " -pthread -o ") +endif() diff --git a/cmake/golang/CMakeTestGoCompiler.cmake b/cmake/golang/CMakeTestGoCompiler.cmake new file mode 100644 index 000000000..d23b8b537 --- /dev/null +++ b/cmake/golang/CMakeTestGoCompiler.cmake @@ -0,0 +1,4 @@ +# Distributed under the OSI-approved BSD 3-Clause License. See accompanying +# file Copyright.txt or https://cmake.org/licensing for details. + +set(CMAKE_Go_COMPILER_WORKS 1 CACHE INTERNAL "") diff --git a/cmake/local-cmake.sh b/cmake/local-cmake.sh new file mode 100644 index 000000000..4dee60c2f --- /dev/null +++ b/cmake/local-cmake.sh @@ -0,0 +1,69 @@ +#!/bin/bash + +# which version to fetch +MAJOR="3.7" +MINOR="2" +PLATFORM="Linux-x86_64" + +# assemble url for desired version +URL="https://cmake.org/files/v${MAJOR}/cmake-${MAJOR}.${MINOR}-${PLATFORM}.tar.gz" + +ARCHIVE="$(basename ${URL})" +DIR="$(basename ${ARCHIVE} .tar.gz)" + + +relpath() { + # workaround because Ubuntu seems to use an ancient realpath version + # https://stackoverflow.com/questions/2564634/convert-absolute-path-into-relative-path-given-a-current-directory-using-bash#comment12808306_7305217 + python -c "import os.path; print(os.path.relpath('${2:-$PWD}','$1'))"; +} + +HERMIT_TOP="$(git rev-parse --show-toplevel)" +HERMIT_CMAKE="${HERMIT_TOP}/cmake" +CMAKE_DIR="${HERMIT_CMAKE}/${DIR}" +CMAKE_DIR_REL="$(relpath ${HERMIT_TOP} ${CMAKE_DIR})" + +# make sure we're sourced, not executed +if [ "$0" = "$BASH_SOURCE" ] +then + echo "You have to source this script:" + echo "\$ . $0" + exit +fi + +# quit if already in path +echo "$PATH" | grep "${CMAKE_DIR_REL}" &>/dev/null && return + +# check if already installed +if which cmake &> /dev/null ; then + if cmake --version | grep "cmake version ${MAJOR}.${MINOR}" &> /dev/null; then + echo "You already have CMake ${MAJOR}.${MINOR}" + return + fi +fi + +if [ ! -d "${CMAKE_DIR}" ] +then + echo "-- Downloading CMake" + wget "${URL}" -O "${ARCHIVE}" || + (echo "Cannot download CMake"; return) + + echo "-- Unpacking CMake" + tar -C "${HERMIT_CMAKE}" -xf "${ARCHIVE}" || + (echo "Cannot unpack CMake archive"; return) + + # delete temporary archive again + rm -f "${ARCHIVE}" + + # add cmake dir to gitignore + GITIGNORE="${HERMIT_TOP}/.gitignore" + if ! grep "${CMAKE_DIR_REL}" "${GITIGNORE}" &>/dev/null + then + echo "${CMAKE_DIR_REL}/*" >> "${GITIGNORE}" + fi + + echo "-- Local CMake v${MAJOR}.${MINOR} installed to ${CMAKE_DIR_REL}" + echo "-- Next time you source this script, no download will be neccessary" +fi + +export PATH="${CMAKE_DIR}/bin:${PATH}" diff --git a/config/bzImage b/config/bzImage index 5c991c839..14c60fd39 100644 Binary files a/config/bzImage and b/config/bzImage differ diff --git a/config/linux_config b/config/linux_config index 5613e1f79..f52a07bd5 100644 --- a/config/linux_config +++ b/config/linux_config @@ -139,7 +139,7 @@ CONFIG_ARCH_SUPPORTS_INT128=y # CONFIG_SYSFS_DEPRECATED is not set # CONFIG_RELAY is not set CONFIG_BLK_DEV_INITRD=y -CONFIG_INITRAMFS_SOURCE="../config/initrd.cpio" +CONFIG_INITRAMFS_SOURCE="/work/lankes/HermitCore/config/initrd.cpio" CONFIG_INITRAMFS_ROOT_UID=0 CONFIG_INITRAMFS_ROOT_GID=0 CONFIG_RD_GZIP=y diff --git a/configure b/configure deleted file mode 100755 index ecb4f5a1f..000000000 --- a/configure +++ /dev/null @@ -1,4144 +0,0 @@ -#! /bin/sh -# Guess values for system-dependent variables and create Makefiles. -# Generated by GNU Autoconf 2.69 for HermitCore 0.1. -# -# Report bugs to . -# -# -# Copyright (C) 1992-1996, 1998-2012 Free Software Foundation, Inc. -# -# -# This configure script is free software; the Free Software Foundation -# gives unlimited permission to copy, distribute and modify it. -## -------------------- ## -## M4sh Initialization. ## -## -------------------- ## - -# Be more Bourne compatible -DUALCASE=1; export DUALCASE # for MKS sh -if test -n "${ZSH_VERSION+set}" && (emulate sh) >/dev/null 2>&1; then : - emulate sh - NULLCMD=: - # Pre-4.2 versions of Zsh do word splitting on ${1+"$@"}, which - # is contrary to our usage. Disable this feature. - alias -g '${1+"$@"}'='"$@"' - setopt NO_GLOB_SUBST -else - case `(set -o) 2>/dev/null` in #( - *posix*) : - set -o posix ;; #( - *) : - ;; -esac -fi - - -as_nl=' -' -export as_nl -# Printing a long string crashes Solaris 7 /usr/bin/printf. -as_echo='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\' -as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo -as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo$as_echo -# Prefer a ksh shell builtin over an external printf program on Solaris, -# but without wasting forks for bash or zsh. -if test -z "$BASH_VERSION$ZSH_VERSION" \ - && (test "X`print -r -- $as_echo`" = "X$as_echo") 2>/dev/null; then - as_echo='print -r --' - as_echo_n='print -rn --' -elif (test "X`printf %s $as_echo`" = "X$as_echo") 2>/dev/null; then - as_echo='printf %s\n' - as_echo_n='printf %s' -else - if test "X`(/usr/ucb/echo -n -n $as_echo) 2>/dev/null`" = "X-n $as_echo"; then - as_echo_body='eval /usr/ucb/echo -n "$1$as_nl"' - as_echo_n='/usr/ucb/echo -n' - else - as_echo_body='eval expr "X$1" : "X\\(.*\\)"' - as_echo_n_body='eval - arg=$1; - case $arg in #( - *"$as_nl"*) - expr "X$arg" : "X\\(.*\\)$as_nl"; - arg=`expr "X$arg" : ".*$as_nl\\(.*\\)"`;; - esac; - expr "X$arg" : "X\\(.*\\)" | tr -d "$as_nl" - ' - export as_echo_n_body - as_echo_n='sh -c $as_echo_n_body as_echo' - fi - export as_echo_body - as_echo='sh -c $as_echo_body as_echo' -fi - -# The user is always right. -if test "${PATH_SEPARATOR+set}" != set; then - PATH_SEPARATOR=: - (PATH='/bin;/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 && { - (PATH='/bin:/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 || - PATH_SEPARATOR=';' - } -fi - - -# IFS -# We need space, tab and new line, in precisely that order. Quoting is -# there to prevent editors from complaining about space-tab. -# (If _AS_PATH_WALK were called with IFS unset, it would disable word -# splitting by setting IFS to empty value.) -IFS=" "" $as_nl" - -# Find who we are. Look in the path if we contain no directory separator. -as_myself= -case $0 in #(( - *[\\/]* ) as_myself=$0 ;; - *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR -for as_dir in $PATH -do - IFS=$as_save_IFS - test -z "$as_dir" && as_dir=. - test -r "$as_dir/$0" && as_myself=$as_dir/$0 && break - done -IFS=$as_save_IFS - - ;; -esac -# We did not find ourselves, most probably we were run as `sh COMMAND' -# in which case we are not to be found in the path. -if test "x$as_myself" = x; then - as_myself=$0 -fi -if test ! -f "$as_myself"; then - $as_echo "$as_myself: error: cannot find myself; rerun with an absolute file name" >&2 - exit 1 -fi - -# Unset variables that we do not need and which cause bugs (e.g. in -# pre-3.0 UWIN ksh). But do not cause bugs in bash 2.01; the "|| exit 1" -# suppresses any "Segmentation fault" message there. '((' could -# trigger a bug in pdksh 5.2.14. -for as_var in BASH_ENV ENV MAIL MAILPATH -do eval test x\${$as_var+set} = xset \ - && ( (unset $as_var) || exit 1) >/dev/null 2>&1 && unset $as_var || : -done -PS1='$ ' -PS2='> ' -PS4='+ ' - -# NLS nuisances. -LC_ALL=C -export LC_ALL -LANGUAGE=C -export LANGUAGE - -# CDPATH. -(unset CDPATH) >/dev/null 2>&1 && unset CDPATH - -# Use a proper internal environment variable to ensure we don't fall - # into an infinite loop, continuously re-executing ourselves. - if test x"${_as_can_reexec}" != xno && test "x$CONFIG_SHELL" != x; then - _as_can_reexec=no; export _as_can_reexec; - # We cannot yet assume a decent shell, so we have to provide a -# neutralization value for shells without unset; and this also -# works around shells that cannot unset nonexistent variables. -# Preserve -v and -x to the replacement shell. -BASH_ENV=/dev/null -ENV=/dev/null -(unset BASH_ENV) >/dev/null 2>&1 && unset BASH_ENV ENV -case $- in # (((( - *v*x* | *x*v* ) as_opts=-vx ;; - *v* ) as_opts=-v ;; - *x* ) as_opts=-x ;; - * ) as_opts= ;; -esac -exec $CONFIG_SHELL $as_opts "$as_myself" ${1+"$@"} -# Admittedly, this is quite paranoid, since all the known shells bail -# out after a failed `exec'. -$as_echo "$0: could not re-execute with $CONFIG_SHELL" >&2 -as_fn_exit 255 - fi - # We don't want this to propagate to other subprocesses. - { _as_can_reexec=; unset _as_can_reexec;} -if test "x$CONFIG_SHELL" = x; then - as_bourne_compatible="if test -n \"\${ZSH_VERSION+set}\" && (emulate sh) >/dev/null 2>&1; then : - emulate sh - NULLCMD=: - # Pre-4.2 versions of Zsh do word splitting on \${1+\"\$@\"}, which - # is contrary to our usage. Disable this feature. - alias -g '\${1+\"\$@\"}'='\"\$@\"' - setopt NO_GLOB_SUBST -else - case \`(set -o) 2>/dev/null\` in #( - *posix*) : - set -o posix ;; #( - *) : - ;; -esac -fi -" - as_required="as_fn_return () { (exit \$1); } -as_fn_success () { as_fn_return 0; } -as_fn_failure () { as_fn_return 1; } -as_fn_ret_success () { return 0; } -as_fn_ret_failure () { return 1; } - -exitcode=0 -as_fn_success || { exitcode=1; echo as_fn_success failed.; } -as_fn_failure && { exitcode=1; echo as_fn_failure succeeded.; } -as_fn_ret_success || { exitcode=1; echo as_fn_ret_success failed.; } -as_fn_ret_failure && { exitcode=1; echo as_fn_ret_failure succeeded.; } -if ( set x; as_fn_ret_success y && test x = \"\$1\" ); then : - -else - exitcode=1; echo positional parameters were not saved. -fi -test x\$exitcode = x0 || exit 1 -test -x / || exit 1" - as_suggested=" as_lineno_1=";as_suggested=$as_suggested$LINENO;as_suggested=$as_suggested" as_lineno_1a=\$LINENO - as_lineno_2=";as_suggested=$as_suggested$LINENO;as_suggested=$as_suggested" as_lineno_2a=\$LINENO - eval 'test \"x\$as_lineno_1'\$as_run'\" != \"x\$as_lineno_2'\$as_run'\" && - test \"x\`expr \$as_lineno_1'\$as_run' + 1\`\" = \"x\$as_lineno_2'\$as_run'\"' || exit 1" - if (eval "$as_required") 2>/dev/null; then : - as_have_required=yes -else - as_have_required=no -fi - if test x$as_have_required = xyes && (eval "$as_suggested") 2>/dev/null; then : - -else - as_save_IFS=$IFS; IFS=$PATH_SEPARATOR -as_found=false -for as_dir in /bin$PATH_SEPARATOR/usr/bin$PATH_SEPARATOR$PATH -do - IFS=$as_save_IFS - test -z "$as_dir" && as_dir=. - as_found=: - case $as_dir in #( - /*) - for as_base in sh bash ksh sh5; do - # Try only shells that exist, to save several forks. - as_shell=$as_dir/$as_base - if { test -f "$as_shell" || test -f "$as_shell.exe"; } && - { $as_echo "$as_bourne_compatible""$as_required" | as_run=a "$as_shell"; } 2>/dev/null; then : - CONFIG_SHELL=$as_shell as_have_required=yes - if { $as_echo "$as_bourne_compatible""$as_suggested" | as_run=a "$as_shell"; } 2>/dev/null; then : - break 2 -fi -fi - done;; - esac - as_found=false -done -$as_found || { if { test -f "$SHELL" || test -f "$SHELL.exe"; } && - { $as_echo "$as_bourne_compatible""$as_required" | as_run=a "$SHELL"; } 2>/dev/null; then : - CONFIG_SHELL=$SHELL as_have_required=yes -fi; } -IFS=$as_save_IFS - - - if test "x$CONFIG_SHELL" != x; then : - export CONFIG_SHELL - # We cannot yet assume a decent shell, so we have to provide a -# neutralization value for shells without unset; and this also -# works around shells that cannot unset nonexistent variables. -# Preserve -v and -x to the replacement shell. -BASH_ENV=/dev/null -ENV=/dev/null -(unset BASH_ENV) >/dev/null 2>&1 && unset BASH_ENV ENV -case $- in # (((( - *v*x* | *x*v* ) as_opts=-vx ;; - *v* ) as_opts=-v ;; - *x* ) as_opts=-x ;; - * ) as_opts= ;; -esac -exec $CONFIG_SHELL $as_opts "$as_myself" ${1+"$@"} -# Admittedly, this is quite paranoid, since all the known shells bail -# out after a failed `exec'. -$as_echo "$0: could not re-execute with $CONFIG_SHELL" >&2 -exit 255 -fi - - if test x$as_have_required = xno; then : - $as_echo "$0: This script requires a shell more modern than all" - $as_echo "$0: the shells that I found on your system." - if test x${ZSH_VERSION+set} = xset ; then - $as_echo "$0: In particular, zsh $ZSH_VERSION has bugs and should" - $as_echo "$0: be upgraded to zsh 4.3.4 or later." - else - $as_echo "$0: Please tell bug-autoconf@gnu.org and -$0: slankes@eonerc.rwth-aachen.de about your system, -$0: including any error possibly output before this -$0: message. Then install a modern shell, or manually run -$0: the script under such a shell if you do have one." - fi - exit 1 -fi -fi -fi -SHELL=${CONFIG_SHELL-/bin/sh} -export SHELL -# Unset more variables known to interfere with behavior of common tools. -CLICOLOR_FORCE= GREP_OPTIONS= -unset CLICOLOR_FORCE GREP_OPTIONS - -## --------------------- ## -## M4sh Shell Functions. ## -## --------------------- ## -# as_fn_unset VAR -# --------------- -# Portably unset VAR. -as_fn_unset () -{ - { eval $1=; unset $1;} -} -as_unset=as_fn_unset - -# as_fn_set_status STATUS -# ----------------------- -# Set $? to STATUS, without forking. -as_fn_set_status () -{ - return $1 -} # as_fn_set_status - -# as_fn_exit STATUS -# ----------------- -# Exit the shell with STATUS, even in a "trap 0" or "set -e" context. -as_fn_exit () -{ - set +e - as_fn_set_status $1 - exit $1 -} # as_fn_exit - -# as_fn_mkdir_p -# ------------- -# Create "$as_dir" as a directory, including parents if necessary. -as_fn_mkdir_p () -{ - - case $as_dir in #( - -*) as_dir=./$as_dir;; - esac - test -d "$as_dir" || eval $as_mkdir_p || { - as_dirs= - while :; do - case $as_dir in #( - *\'*) as_qdir=`$as_echo "$as_dir" | sed "s/'/'\\\\\\\\''/g"`;; #'( - *) as_qdir=$as_dir;; - esac - as_dirs="'$as_qdir' $as_dirs" - as_dir=`$as_dirname -- "$as_dir" || -$as_expr X"$as_dir" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ - X"$as_dir" : 'X\(//\)[^/]' \| \ - X"$as_dir" : 'X\(//\)$' \| \ - X"$as_dir" : 'X\(/\)' \| . 2>/dev/null || -$as_echo X"$as_dir" | - sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ - s//\1/ - q - } - /^X\(\/\/\)[^/].*/{ - s//\1/ - q - } - /^X\(\/\/\)$/{ - s//\1/ - q - } - /^X\(\/\).*/{ - s//\1/ - q - } - s/.*/./; q'` - test -d "$as_dir" && break - done - test -z "$as_dirs" || eval "mkdir $as_dirs" - } || test -d "$as_dir" || as_fn_error $? "cannot create directory $as_dir" - - -} # as_fn_mkdir_p - -# as_fn_executable_p FILE -# ----------------------- -# Test if FILE is an executable regular file. -as_fn_executable_p () -{ - test -f "$1" && test -x "$1" -} # as_fn_executable_p -# as_fn_append VAR VALUE -# ---------------------- -# Append the text in VALUE to the end of the definition contained in VAR. Take -# advantage of any shell optimizations that allow amortized linear growth over -# repeated appends, instead of the typical quadratic growth present in naive -# implementations. -if (eval "as_var=1; as_var+=2; test x\$as_var = x12") 2>/dev/null; then : - eval 'as_fn_append () - { - eval $1+=\$2 - }' -else - as_fn_append () - { - eval $1=\$$1\$2 - } -fi # as_fn_append - -# as_fn_arith ARG... -# ------------------ -# Perform arithmetic evaluation on the ARGs, and store the result in the -# global $as_val. Take advantage of shells that can avoid forks. The arguments -# must be portable across $(()) and expr. -if (eval "test \$(( 1 + 1 )) = 2") 2>/dev/null; then : - eval 'as_fn_arith () - { - as_val=$(( $* )) - }' -else - as_fn_arith () - { - as_val=`expr "$@" || test $? -eq 1` - } -fi # as_fn_arith - - -# as_fn_error STATUS ERROR [LINENO LOG_FD] -# ---------------------------------------- -# Output "`basename $0`: error: ERROR" to stderr. If LINENO and LOG_FD are -# provided, also output the error to LOG_FD, referencing LINENO. Then exit the -# script with STATUS, using 1 if that was 0. -as_fn_error () -{ - as_status=$1; test $as_status -eq 0 && as_status=1 - if test "$4"; then - as_lineno=${as_lineno-"$3"} as_lineno_stack=as_lineno_stack=$as_lineno_stack - $as_echo "$as_me:${as_lineno-$LINENO}: error: $2" >&$4 - fi - $as_echo "$as_me: error: $2" >&2 - as_fn_exit $as_status -} # as_fn_error - -if expr a : '\(a\)' >/dev/null 2>&1 && - test "X`expr 00001 : '.*\(...\)'`" = X001; then - as_expr=expr -else - as_expr=false -fi - -if (basename -- /) >/dev/null 2>&1 && test "X`basename -- / 2>&1`" = "X/"; then - as_basename=basename -else - as_basename=false -fi - -if (as_dir=`dirname -- /` && test "X$as_dir" = X/) >/dev/null 2>&1; then - as_dirname=dirname -else - as_dirname=false -fi - -as_me=`$as_basename -- "$0" || -$as_expr X/"$0" : '.*/\([^/][^/]*\)/*$' \| \ - X"$0" : 'X\(//\)$' \| \ - X"$0" : 'X\(/\)' \| . 2>/dev/null || -$as_echo X/"$0" | - sed '/^.*\/\([^/][^/]*\)\/*$/{ - s//\1/ - q - } - /^X\/\(\/\/\)$/{ - s//\1/ - q - } - /^X\/\(\/\).*/{ - s//\1/ - q - } - s/.*/./; q'` - -# Avoid depending upon Character Ranges. -as_cr_letters='abcdefghijklmnopqrstuvwxyz' -as_cr_LETTERS='ABCDEFGHIJKLMNOPQRSTUVWXYZ' -as_cr_Letters=$as_cr_letters$as_cr_LETTERS -as_cr_digits='0123456789' -as_cr_alnum=$as_cr_Letters$as_cr_digits - - - as_lineno_1=$LINENO as_lineno_1a=$LINENO - as_lineno_2=$LINENO as_lineno_2a=$LINENO - eval 'test "x$as_lineno_1'$as_run'" != "x$as_lineno_2'$as_run'" && - test "x`expr $as_lineno_1'$as_run' + 1`" = "x$as_lineno_2'$as_run'"' || { - # Blame Lee E. McMahon (1931-1989) for sed's syntax. :-) - sed -n ' - p - /[$]LINENO/= - ' <$as_myself | - sed ' - s/[$]LINENO.*/&-/ - t lineno - b - :lineno - N - :loop - s/[$]LINENO\([^'$as_cr_alnum'_].*\n\)\(.*\)/\2\1\2/ - t loop - s/-\n.*// - ' >$as_me.lineno && - chmod +x "$as_me.lineno" || - { $as_echo "$as_me: error: cannot create $as_me.lineno; rerun with a POSIX shell" >&2; as_fn_exit 1; } - - # If we had to re-execute with $CONFIG_SHELL, we're ensured to have - # already done that, so ensure we don't try to do so again and fall - # in an infinite loop. This has already happened in practice. - _as_can_reexec=no; export _as_can_reexec - # Don't try to exec as it changes $[0], causing all sort of problems - # (the dirname of $[0] is not the place where we might find the - # original and so on. Autoconf is especially sensitive to this). - . "./$as_me.lineno" - # Exit status is that of the last command. - exit -} - -ECHO_C= ECHO_N= ECHO_T= -case `echo -n x` in #((((( --n*) - case `echo 'xy\c'` in - *c*) ECHO_T=' ';; # ECHO_T is single tab character. - xy) ECHO_C='\c';; - *) echo `echo ksh88 bug on AIX 6.1` > /dev/null - ECHO_T=' ';; - esac;; -*) - ECHO_N='-n';; -esac - -rm -f conf$$ conf$$.exe conf$$.file -if test -d conf$$.dir; then - rm -f conf$$.dir/conf$$.file -else - rm -f conf$$.dir - mkdir conf$$.dir 2>/dev/null -fi -if (echo >conf$$.file) 2>/dev/null; then - if ln -s conf$$.file conf$$ 2>/dev/null; then - as_ln_s='ln -s' - # ... but there are two gotchas: - # 1) On MSYS, both `ln -s file dir' and `ln file dir' fail. - # 2) DJGPP < 2.04 has no symlinks; `ln -s' creates a wrapper executable. - # In both cases, we have to default to `cp -pR'. - ln -s conf$$.file conf$$.dir 2>/dev/null && test ! -f conf$$.exe || - as_ln_s='cp -pR' - elif ln conf$$.file conf$$ 2>/dev/null; then - as_ln_s=ln - else - as_ln_s='cp -pR' - fi -else - as_ln_s='cp -pR' -fi -rm -f conf$$ conf$$.exe conf$$.dir/conf$$.file conf$$.file -rmdir conf$$.dir 2>/dev/null - -if mkdir -p . 2>/dev/null; then - as_mkdir_p='mkdir -p "$as_dir"' -else - test -d ./-p && rmdir ./-p - as_mkdir_p=false -fi - -as_test_x='test -x' -as_executable_p=as_fn_executable_p - -# Sed expression to map a string onto a valid CPP name. -as_tr_cpp="eval sed 'y%*$as_cr_letters%P$as_cr_LETTERS%;s%[^_$as_cr_alnum]%_%g'" - -# Sed expression to map a string onto a valid variable name. -as_tr_sh="eval sed 'y%*+%pp%;s%[^_$as_cr_alnum]%_%g'" - - -test -n "$DJDIR" || exec 7<&0 &1 - -# Name of the host. -# hostname on some systems (SVR3.2, old GNU/Linux) returns a bogus exit status, -# so uname gets run too. -ac_hostname=`(hostname || uname -n) 2>/dev/null | sed 1q` - -# -# Initializations. -# -ac_default_prefix=/usr/local -ac_clean_files= -ac_config_libobj_dir=. -LIBOBJS= -cross_compiling=no -subdirs= -MFLAGS= -MAKEFLAGS= - -# Identity of this package. -PACKAGE_NAME='HermitCore' -PACKAGE_TARNAME='HermitCore' -PACKAGE_VERSION='0.1' -PACKAGE_STRING='HermitCore 0.1' -PACKAGE_BUGREPORT='slankes@eonerc.rwth-aachen.de' -PACKAGE_URL='http://www.hermitcore.org' - -ac_unique_file="kernel/main.c" -ac_subst_vars='LTLIBOBJS -LIBOBJS -TOOLCHAIN -ARCH_OPT -INSTALL_DATA -INSTALL_SCRIPT -INSTALL_PROGRAM -OBJEXT -EXEEXT -ac_ct_CC -CPPFLAGS -LDFLAGS -CFLAGS -CC -QEMU -target_alias -host_alias -build_alias -LIBS -ECHO_T -ECHO_N -ECHO_C -DEFS -mandir -localedir -libdir -psdir -pdfdir -dvidir -htmldir -infodir -docdir -oldincludedir -includedir -runstatedir -localstatedir -sharedstatedir -sysconfdir -datadir -datarootdir -libexecdir -sbindir -bindir -program_transform_name -prefix -exec_prefix -PACKAGE_URL -PACKAGE_BUGREPORT -PACKAGE_STRING -PACKAGE_VERSION -PACKAGE_TARNAME -PACKAGE_NAME -PATH_SEPARATOR -SHELL' -ac_subst_files='' -ac_user_opts=' -enable_option_checking -with_mtune -with_toolchain -with_max_cores -with_max_tasks -with_kernel_stack_size -with_default_stack_size -' - ac_precious_vars='build_alias -host_alias -target_alias -CC -CFLAGS -LDFLAGS -LIBS -CPPFLAGS' - - -# Initialize some variables set by options. -ac_init_help= -ac_init_version=false -ac_unrecognized_opts= -ac_unrecognized_sep= -# The variables have the same names as the options, with -# dashes changed to underlines. -cache_file=/dev/null -exec_prefix=NONE -no_create= -no_recursion= -prefix=NONE -program_prefix=NONE -program_suffix=NONE -program_transform_name=s,x,x, -silent= -site= -srcdir= -verbose= -x_includes=NONE -x_libraries=NONE - -# Installation directory options. -# These are left unexpanded so users can "make install exec_prefix=/foo" -# and all the variables that are supposed to be based on exec_prefix -# by default will actually change. -# Use braces instead of parens because sh, perl, etc. also accept them. -# (The list follows the same order as the GNU Coding Standards.) -bindir='${exec_prefix}/bin' -sbindir='${exec_prefix}/sbin' -libexecdir='${exec_prefix}/libexec' -datarootdir='${prefix}/share' -datadir='${datarootdir}' -sysconfdir='${prefix}/etc' -sharedstatedir='${prefix}/com' -localstatedir='${prefix}/var' -runstatedir='${localstatedir}/run' -includedir='${prefix}/include' -oldincludedir='/usr/include' -docdir='${datarootdir}/doc/${PACKAGE_TARNAME}' -infodir='${datarootdir}/info' -htmldir='${docdir}' -dvidir='${docdir}' -pdfdir='${docdir}' -psdir='${docdir}' -libdir='${exec_prefix}/lib' -localedir='${datarootdir}/locale' -mandir='${datarootdir}/man' - -ac_prev= -ac_dashdash= -for ac_option -do - # If the previous option needs an argument, assign it. - if test -n "$ac_prev"; then - eval $ac_prev=\$ac_option - ac_prev= - continue - fi - - case $ac_option in - *=?*) ac_optarg=`expr "X$ac_option" : '[^=]*=\(.*\)'` ;; - *=) ac_optarg= ;; - *) ac_optarg=yes ;; - esac - - # Accept the important Cygnus configure options, so we can diagnose typos. - - case $ac_dashdash$ac_option in - --) - ac_dashdash=yes ;; - - -bindir | --bindir | --bindi | --bind | --bin | --bi) - ac_prev=bindir ;; - -bindir=* | --bindir=* | --bindi=* | --bind=* | --bin=* | --bi=*) - bindir=$ac_optarg ;; - - -build | --build | --buil | --bui | --bu) - ac_prev=build_alias ;; - -build=* | --build=* | --buil=* | --bui=* | --bu=*) - build_alias=$ac_optarg ;; - - -cache-file | --cache-file | --cache-fil | --cache-fi \ - | --cache-f | --cache- | --cache | --cach | --cac | --ca | --c) - ac_prev=cache_file ;; - -cache-file=* | --cache-file=* | --cache-fil=* | --cache-fi=* \ - | --cache-f=* | --cache-=* | --cache=* | --cach=* | --cac=* | --ca=* | --c=*) - cache_file=$ac_optarg ;; - - --config-cache | -C) - cache_file=config.cache ;; - - -datadir | --datadir | --datadi | --datad) - ac_prev=datadir ;; - -datadir=* | --datadir=* | --datadi=* | --datad=*) - datadir=$ac_optarg ;; - - -datarootdir | --datarootdir | --datarootdi | --datarootd | --dataroot \ - | --dataroo | --dataro | --datar) - ac_prev=datarootdir ;; - -datarootdir=* | --datarootdir=* | --datarootdi=* | --datarootd=* \ - | --dataroot=* | --dataroo=* | --dataro=* | --datar=*) - datarootdir=$ac_optarg ;; - - -disable-* | --disable-*) - ac_useropt=`expr "x$ac_option" : 'x-*disable-\(.*\)'` - # Reject names that are not valid shell variable names. - expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null && - as_fn_error $? "invalid feature name: $ac_useropt" - ac_useropt_orig=$ac_useropt - ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'` - case $ac_user_opts in - *" -"enable_$ac_useropt" -"*) ;; - *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--disable-$ac_useropt_orig" - ac_unrecognized_sep=', ';; - esac - eval enable_$ac_useropt=no ;; - - -docdir | --docdir | --docdi | --doc | --do) - ac_prev=docdir ;; - -docdir=* | --docdir=* | --docdi=* | --doc=* | --do=*) - docdir=$ac_optarg ;; - - -dvidir | --dvidir | --dvidi | --dvid | --dvi | --dv) - ac_prev=dvidir ;; - -dvidir=* | --dvidir=* | --dvidi=* | --dvid=* | --dvi=* | --dv=*) - dvidir=$ac_optarg ;; - - -enable-* | --enable-*) - ac_useropt=`expr "x$ac_option" : 'x-*enable-\([^=]*\)'` - # Reject names that are not valid shell variable names. - expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null && - as_fn_error $? "invalid feature name: $ac_useropt" - ac_useropt_orig=$ac_useropt - ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'` - case $ac_user_opts in - *" -"enable_$ac_useropt" -"*) ;; - *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--enable-$ac_useropt_orig" - ac_unrecognized_sep=', ';; - esac - eval enable_$ac_useropt=\$ac_optarg ;; - - -exec-prefix | --exec_prefix | --exec-prefix | --exec-prefi \ - | --exec-pref | --exec-pre | --exec-pr | --exec-p | --exec- \ - | --exec | --exe | --ex) - ac_prev=exec_prefix ;; - -exec-prefix=* | --exec_prefix=* | --exec-prefix=* | --exec-prefi=* \ - | --exec-pref=* | --exec-pre=* | --exec-pr=* | --exec-p=* | --exec-=* \ - | --exec=* | --exe=* | --ex=*) - exec_prefix=$ac_optarg ;; - - -gas | --gas | --ga | --g) - # Obsolete; use --with-gas. - with_gas=yes ;; - - -help | --help | --hel | --he | -h) - ac_init_help=long ;; - -help=r* | --help=r* | --hel=r* | --he=r* | -hr*) - ac_init_help=recursive ;; - -help=s* | --help=s* | --hel=s* | --he=s* | -hs*) - ac_init_help=short ;; - - -host | --host | --hos | --ho) - ac_prev=host_alias ;; - -host=* | --host=* | --hos=* | --ho=*) - host_alias=$ac_optarg ;; - - -htmldir | --htmldir | --htmldi | --htmld | --html | --htm | --ht) - ac_prev=htmldir ;; - -htmldir=* | --htmldir=* | --htmldi=* | --htmld=* | --html=* | --htm=* \ - | --ht=*) - htmldir=$ac_optarg ;; - - -includedir | --includedir | --includedi | --included | --include \ - | --includ | --inclu | --incl | --inc) - ac_prev=includedir ;; - -includedir=* | --includedir=* | --includedi=* | --included=* | --include=* \ - | --includ=* | --inclu=* | --incl=* | --inc=*) - includedir=$ac_optarg ;; - - -infodir | --infodir | --infodi | --infod | --info | --inf) - ac_prev=infodir ;; - -infodir=* | --infodir=* | --infodi=* | --infod=* | --info=* | --inf=*) - infodir=$ac_optarg ;; - - -libdir | --libdir | --libdi | --libd) - ac_prev=libdir ;; - -libdir=* | --libdir=* | --libdi=* | --libd=*) - libdir=$ac_optarg ;; - - -libexecdir | --libexecdir | --libexecdi | --libexecd | --libexec \ - | --libexe | --libex | --libe) - ac_prev=libexecdir ;; - -libexecdir=* | --libexecdir=* | --libexecdi=* | --libexecd=* | --libexec=* \ - | --libexe=* | --libex=* | --libe=*) - libexecdir=$ac_optarg ;; - - -localedir | --localedir | --localedi | --localed | --locale) - ac_prev=localedir ;; - -localedir=* | --localedir=* | --localedi=* | --localed=* | --locale=*) - localedir=$ac_optarg ;; - - -localstatedir | --localstatedir | --localstatedi | --localstated \ - | --localstate | --localstat | --localsta | --localst | --locals) - ac_prev=localstatedir ;; - -localstatedir=* | --localstatedir=* | --localstatedi=* | --localstated=* \ - | --localstate=* | --localstat=* | --localsta=* | --localst=* | --locals=*) - localstatedir=$ac_optarg ;; - - -mandir | --mandir | --mandi | --mand | --man | --ma | --m) - ac_prev=mandir ;; - -mandir=* | --mandir=* | --mandi=* | --mand=* | --man=* | --ma=* | --m=*) - mandir=$ac_optarg ;; - - -nfp | --nfp | --nf) - # Obsolete; use --without-fp. - with_fp=no ;; - - -no-create | --no-create | --no-creat | --no-crea | --no-cre \ - | --no-cr | --no-c | -n) - no_create=yes ;; - - -no-recursion | --no-recursion | --no-recursio | --no-recursi \ - | --no-recurs | --no-recur | --no-recu | --no-rec | --no-re | --no-r) - no_recursion=yes ;; - - -oldincludedir | --oldincludedir | --oldincludedi | --oldincluded \ - | --oldinclude | --oldinclud | --oldinclu | --oldincl | --oldinc \ - | --oldin | --oldi | --old | --ol | --o) - ac_prev=oldincludedir ;; - -oldincludedir=* | --oldincludedir=* | --oldincludedi=* | --oldincluded=* \ - | --oldinclude=* | --oldinclud=* | --oldinclu=* | --oldincl=* | --oldinc=* \ - | --oldin=* | --oldi=* | --old=* | --ol=* | --o=*) - oldincludedir=$ac_optarg ;; - - -prefix | --prefix | --prefi | --pref | --pre | --pr | --p) - ac_prev=prefix ;; - -prefix=* | --prefix=* | --prefi=* | --pref=* | --pre=* | --pr=* | --p=*) - prefix=$ac_optarg ;; - - -program-prefix | --program-prefix | --program-prefi | --program-pref \ - | --program-pre | --program-pr | --program-p) - ac_prev=program_prefix ;; - -program-prefix=* | --program-prefix=* | --program-prefi=* \ - | --program-pref=* | --program-pre=* | --program-pr=* | --program-p=*) - program_prefix=$ac_optarg ;; - - -program-suffix | --program-suffix | --program-suffi | --program-suff \ - | --program-suf | --program-su | --program-s) - ac_prev=program_suffix ;; - -program-suffix=* | --program-suffix=* | --program-suffi=* \ - | --program-suff=* | --program-suf=* | --program-su=* | --program-s=*) - program_suffix=$ac_optarg ;; - - -program-transform-name | --program-transform-name \ - | --program-transform-nam | --program-transform-na \ - | --program-transform-n | --program-transform- \ - | --program-transform | --program-transfor \ - | --program-transfo | --program-transf \ - | --program-trans | --program-tran \ - | --progr-tra | --program-tr | --program-t) - ac_prev=program_transform_name ;; - -program-transform-name=* | --program-transform-name=* \ - | --program-transform-nam=* | --program-transform-na=* \ - | --program-transform-n=* | --program-transform-=* \ - | --program-transform=* | --program-transfor=* \ - | --program-transfo=* | --program-transf=* \ - | --program-trans=* | --program-tran=* \ - | --progr-tra=* | --program-tr=* | --program-t=*) - program_transform_name=$ac_optarg ;; - - -pdfdir | --pdfdir | --pdfdi | --pdfd | --pdf | --pd) - ac_prev=pdfdir ;; - -pdfdir=* | --pdfdir=* | --pdfdi=* | --pdfd=* | --pdf=* | --pd=*) - pdfdir=$ac_optarg ;; - - -psdir | --psdir | --psdi | --psd | --ps) - ac_prev=psdir ;; - -psdir=* | --psdir=* | --psdi=* | --psd=* | --ps=*) - psdir=$ac_optarg ;; - - -q | -quiet | --quiet | --quie | --qui | --qu | --q \ - | -silent | --silent | --silen | --sile | --sil) - silent=yes ;; - - -runstatedir | --runstatedir | --runstatedi | --runstated \ - | --runstate | --runstat | --runsta | --runst | --runs \ - | --run | --ru | --r) - ac_prev=runstatedir ;; - -runstatedir=* | --runstatedir=* | --runstatedi=* | --runstated=* \ - | --runstate=* | --runstat=* | --runsta=* | --runst=* | --runs=* \ - | --run=* | --ru=* | --r=*) - runstatedir=$ac_optarg ;; - - -sbindir | --sbindir | --sbindi | --sbind | --sbin | --sbi | --sb) - ac_prev=sbindir ;; - -sbindir=* | --sbindir=* | --sbindi=* | --sbind=* | --sbin=* \ - | --sbi=* | --sb=*) - sbindir=$ac_optarg ;; - - -sharedstatedir | --sharedstatedir | --sharedstatedi \ - | --sharedstated | --sharedstate | --sharedstat | --sharedsta \ - | --sharedst | --shareds | --shared | --share | --shar \ - | --sha | --sh) - ac_prev=sharedstatedir ;; - -sharedstatedir=* | --sharedstatedir=* | --sharedstatedi=* \ - | --sharedstated=* | --sharedstate=* | --sharedstat=* | --sharedsta=* \ - | --sharedst=* | --shareds=* | --shared=* | --share=* | --shar=* \ - | --sha=* | --sh=*) - sharedstatedir=$ac_optarg ;; - - -site | --site | --sit) - ac_prev=site ;; - -site=* | --site=* | --sit=*) - site=$ac_optarg ;; - - -srcdir | --srcdir | --srcdi | --srcd | --src | --sr) - ac_prev=srcdir ;; - -srcdir=* | --srcdir=* | --srcdi=* | --srcd=* | --src=* | --sr=*) - srcdir=$ac_optarg ;; - - -sysconfdir | --sysconfdir | --sysconfdi | --sysconfd | --sysconf \ - | --syscon | --sysco | --sysc | --sys | --sy) - ac_prev=sysconfdir ;; - -sysconfdir=* | --sysconfdir=* | --sysconfdi=* | --sysconfd=* | --sysconf=* \ - | --syscon=* | --sysco=* | --sysc=* | --sys=* | --sy=*) - sysconfdir=$ac_optarg ;; - - -target | --target | --targe | --targ | --tar | --ta | --t) - ac_prev=target_alias ;; - -target=* | --target=* | --targe=* | --targ=* | --tar=* | --ta=* | --t=*) - target_alias=$ac_optarg ;; - - -v | -verbose | --verbose | --verbos | --verbo | --verb) - verbose=yes ;; - - -version | --version | --versio | --versi | --vers | -V) - ac_init_version=: ;; - - -with-* | --with-*) - ac_useropt=`expr "x$ac_option" : 'x-*with-\([^=]*\)'` - # Reject names that are not valid shell variable names. - expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null && - as_fn_error $? "invalid package name: $ac_useropt" - ac_useropt_orig=$ac_useropt - ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'` - case $ac_user_opts in - *" -"with_$ac_useropt" -"*) ;; - *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--with-$ac_useropt_orig" - ac_unrecognized_sep=', ';; - esac - eval with_$ac_useropt=\$ac_optarg ;; - - -without-* | --without-*) - ac_useropt=`expr "x$ac_option" : 'x-*without-\(.*\)'` - # Reject names that are not valid shell variable names. - expr "x$ac_useropt" : ".*[^-+._$as_cr_alnum]" >/dev/null && - as_fn_error $? "invalid package name: $ac_useropt" - ac_useropt_orig=$ac_useropt - ac_useropt=`$as_echo "$ac_useropt" | sed 's/[-+.]/_/g'` - case $ac_user_opts in - *" -"with_$ac_useropt" -"*) ;; - *) ac_unrecognized_opts="$ac_unrecognized_opts$ac_unrecognized_sep--without-$ac_useropt_orig" - ac_unrecognized_sep=', ';; - esac - eval with_$ac_useropt=no ;; - - --x) - # Obsolete; use --with-x. - with_x=yes ;; - - -x-includes | --x-includes | --x-include | --x-includ | --x-inclu \ - | --x-incl | --x-inc | --x-in | --x-i) - ac_prev=x_includes ;; - -x-includes=* | --x-includes=* | --x-include=* | --x-includ=* | --x-inclu=* \ - | --x-incl=* | --x-inc=* | --x-in=* | --x-i=*) - x_includes=$ac_optarg ;; - - -x-libraries | --x-libraries | --x-librarie | --x-librari \ - | --x-librar | --x-libra | --x-libr | --x-lib | --x-li | --x-l) - ac_prev=x_libraries ;; - -x-libraries=* | --x-libraries=* | --x-librarie=* | --x-librari=* \ - | --x-librar=* | --x-libra=* | --x-libr=* | --x-lib=* | --x-li=* | --x-l=*) - x_libraries=$ac_optarg ;; - - -*) as_fn_error $? "unrecognized option: \`$ac_option' -Try \`$0 --help' for more information" - ;; - - *=*) - ac_envvar=`expr "x$ac_option" : 'x\([^=]*\)='` - # Reject names that are not valid shell variable names. - case $ac_envvar in #( - '' | [0-9]* | *[!_$as_cr_alnum]* ) - as_fn_error $? "invalid variable name: \`$ac_envvar'" ;; - esac - eval $ac_envvar=\$ac_optarg - export $ac_envvar ;; - - *) - # FIXME: should be removed in autoconf 3.0. - $as_echo "$as_me: WARNING: you should use --build, --host, --target" >&2 - expr "x$ac_option" : ".*[^-._$as_cr_alnum]" >/dev/null && - $as_echo "$as_me: WARNING: invalid host type: $ac_option" >&2 - : "${build_alias=$ac_option} ${host_alias=$ac_option} ${target_alias=$ac_option}" - ;; - - esac -done - -if test -n "$ac_prev"; then - ac_option=--`echo $ac_prev | sed 's/_/-/g'` - as_fn_error $? "missing argument to $ac_option" -fi - -if test -n "$ac_unrecognized_opts"; then - case $enable_option_checking in - no) ;; - fatal) as_fn_error $? "unrecognized options: $ac_unrecognized_opts" ;; - *) $as_echo "$as_me: WARNING: unrecognized options: $ac_unrecognized_opts" >&2 ;; - esac -fi - -# Check all directory arguments for consistency. -for ac_var in exec_prefix prefix bindir sbindir libexecdir datarootdir \ - datadir sysconfdir sharedstatedir localstatedir includedir \ - oldincludedir docdir infodir htmldir dvidir pdfdir psdir \ - libdir localedir mandir runstatedir -do - eval ac_val=\$$ac_var - # Remove trailing slashes. - case $ac_val in - */ ) - ac_val=`expr "X$ac_val" : 'X\(.*[^/]\)' \| "X$ac_val" : 'X\(.*\)'` - eval $ac_var=\$ac_val;; - esac - # Be sure to have absolute directory names. - case $ac_val in - [\\/$]* | ?:[\\/]* ) continue;; - NONE | '' ) case $ac_var in *prefix ) continue;; esac;; - esac - as_fn_error $? "expected an absolute directory name for --$ac_var: $ac_val" -done - -# There might be people who depend on the old broken behavior: `$host' -# used to hold the argument of --host etc. -# FIXME: To remove some day. -build=$build_alias -host=$host_alias -target=$target_alias - -# FIXME: To remove some day. -if test "x$host_alias" != x; then - if test "x$build_alias" = x; then - cross_compiling=maybe - elif test "x$build_alias" != "x$host_alias"; then - cross_compiling=yes - fi -fi - -ac_tool_prefix= -test -n "$host_alias" && ac_tool_prefix=$host_alias- - -test "$silent" = yes && exec 6>/dev/null - - -ac_pwd=`pwd` && test -n "$ac_pwd" && -ac_ls_di=`ls -di .` && -ac_pwd_ls_di=`cd "$ac_pwd" && ls -di .` || - as_fn_error $? "working directory cannot be determined" -test "X$ac_ls_di" = "X$ac_pwd_ls_di" || - as_fn_error $? "pwd does not report name of working directory" - - -# Find the source files, if location was not specified. -if test -z "$srcdir"; then - ac_srcdir_defaulted=yes - # Try the directory containing this script, then the parent directory. - ac_confdir=`$as_dirname -- "$as_myself" || -$as_expr X"$as_myself" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ - X"$as_myself" : 'X\(//\)[^/]' \| \ - X"$as_myself" : 'X\(//\)$' \| \ - X"$as_myself" : 'X\(/\)' \| . 2>/dev/null || -$as_echo X"$as_myself" | - sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ - s//\1/ - q - } - /^X\(\/\/\)[^/].*/{ - s//\1/ - q - } - /^X\(\/\/\)$/{ - s//\1/ - q - } - /^X\(\/\).*/{ - s//\1/ - q - } - s/.*/./; q'` - srcdir=$ac_confdir - if test ! -r "$srcdir/$ac_unique_file"; then - srcdir=.. - fi -else - ac_srcdir_defaulted=no -fi -if test ! -r "$srcdir/$ac_unique_file"; then - test "$ac_srcdir_defaulted" = yes && srcdir="$ac_confdir or .." - as_fn_error $? "cannot find sources ($ac_unique_file) in $srcdir" -fi -ac_msg="sources are in $srcdir, but \`cd $srcdir' does not work" -ac_abs_confdir=`( - cd "$srcdir" && test -r "./$ac_unique_file" || as_fn_error $? "$ac_msg" - pwd)` -# When building in place, set srcdir=. -if test "$ac_abs_confdir" = "$ac_pwd"; then - srcdir=. -fi -# Remove unnecessary trailing slashes from srcdir. -# Double slashes in file names in object file debugging info -# mess up M-x gdb in Emacs. -case $srcdir in -*/) srcdir=`expr "X$srcdir" : 'X\(.*[^/]\)' \| "X$srcdir" : 'X\(.*\)'`;; -esac -for ac_var in $ac_precious_vars; do - eval ac_env_${ac_var}_set=\${${ac_var}+set} - eval ac_env_${ac_var}_value=\$${ac_var} - eval ac_cv_env_${ac_var}_set=\${${ac_var}+set} - eval ac_cv_env_${ac_var}_value=\$${ac_var} -done - -# -# Report the --help message. -# -if test "$ac_init_help" = "long"; then - # Omit some internal or obsolete options to make the list less imposing. - # This message is too long to be a string in the A/UX 3.1 sh. - cat <<_ACEOF -\`configure' configures HermitCore 0.1 to adapt to many kinds of systems. - -Usage: $0 [OPTION]... [VAR=VALUE]... - -To assign environment variables (e.g., CC, CFLAGS...), specify them as -VAR=VALUE. See below for descriptions of some of the useful variables. - -Defaults for the options are specified in brackets. - -Configuration: - -h, --help display this help and exit - --help=short display options specific to this package - --help=recursive display the short help of all the included packages - -V, --version display version information and exit - -q, --quiet, --silent do not print \`checking ...' messages - --cache-file=FILE cache test results in FILE [disabled] - -C, --config-cache alias for \`--cache-file=config.cache' - -n, --no-create do not create output files - --srcdir=DIR find the sources in DIR [configure dir or \`..'] - -Installation directories: - --prefix=PREFIX install architecture-independent files in PREFIX - [$ac_default_prefix] - --exec-prefix=EPREFIX install architecture-dependent files in EPREFIX - [PREFIX] - -By default, \`make install' will install all the files in -\`$ac_default_prefix/bin', \`$ac_default_prefix/lib' etc. You can specify -an installation prefix other than \`$ac_default_prefix' using \`--prefix', -for instance \`--prefix=\$HOME'. - -For better control, use the options below. - -Fine tuning of the installation directories: - --bindir=DIR user executables [EPREFIX/bin] - --sbindir=DIR system admin executables [EPREFIX/sbin] - --libexecdir=DIR program executables [EPREFIX/libexec] - --sysconfdir=DIR read-only single-machine data [PREFIX/etc] - --sharedstatedir=DIR modifiable architecture-independent data [PREFIX/com] - --localstatedir=DIR modifiable single-machine data [PREFIX/var] - --runstatedir=DIR modifiable per-process data [LOCALSTATEDIR/run] - --libdir=DIR object code libraries [EPREFIX/lib] - --includedir=DIR C header files [PREFIX/include] - --oldincludedir=DIR C header files for non-gcc [/usr/include] - --datarootdir=DIR read-only arch.-independent data root [PREFIX/share] - --datadir=DIR read-only architecture-independent data [DATAROOTDIR] - --infodir=DIR info documentation [DATAROOTDIR/info] - --localedir=DIR locale-dependent data [DATAROOTDIR/locale] - --mandir=DIR man documentation [DATAROOTDIR/man] - --docdir=DIR documentation root [DATAROOTDIR/doc/HermitCore] - --htmldir=DIR html documentation [DOCDIR] - --dvidir=DIR dvi documentation [DOCDIR] - --pdfdir=DIR pdf documentation [DOCDIR] - --psdir=DIR ps documentation [DOCDIR] -_ACEOF - - cat <<\_ACEOF -_ACEOF -fi - -if test -n "$ac_init_help"; then - case $ac_init_help in - short | recursive ) echo "Configuration of HermitCore 0.1:";; - esac - cat <<\_ACEOF - -Optional Packages: - --with-PACKAGE[=ARG] use PACKAGE [ARG=yes] - --without-PACKAGE do not use PACKAGE (same as --with-PACKAGE=no) - --with-mtune=ARCH enable tuning for a specific architecture - --with-toolchain build also the whole HermitCore toolchain - --with-max-cores=N specify the maximum number of cores - --with-max-tasks=N specify the maximum number of running tasks - --with-kernel-stack-size=SIZE - specify the size of the kernel stack - --with-default-stack-size=SIZE - specify the default stack size - -Some influential environment variables: - CC C compiler command - CFLAGS C compiler flags - LDFLAGS linker flags, e.g. -L if you have libraries in a - nonstandard directory - LIBS libraries to pass to the linker, e.g. -l - CPPFLAGS (Objective) C/C++ preprocessor flags, e.g. -I if - you have headers in a nonstandard directory - -Use these variables to override the choices made by `configure' or to help -it to find libraries and programs with nonstandard names/locations. - -Report bugs to . -HermitCore home page: . -_ACEOF -ac_status=$? -fi - -if test "$ac_init_help" = "recursive"; then - # If there are subdirs, report their specific --help. - for ac_dir in : $ac_subdirs_all; do test "x$ac_dir" = x: && continue - test -d "$ac_dir" || - { cd "$srcdir" && ac_pwd=`pwd` && srcdir=. && test -d "$ac_dir"; } || - continue - ac_builddir=. - -case "$ac_dir" in -.) ac_dir_suffix= ac_top_builddir_sub=. ac_top_build_prefix= ;; -*) - ac_dir_suffix=/`$as_echo "$ac_dir" | sed 's|^\.[\\/]||'` - # A ".." for each directory in $ac_dir_suffix. - ac_top_builddir_sub=`$as_echo "$ac_dir_suffix" | sed 's|/[^\\/]*|/..|g;s|/||'` - case $ac_top_builddir_sub in - "") ac_top_builddir_sub=. ac_top_build_prefix= ;; - *) ac_top_build_prefix=$ac_top_builddir_sub/ ;; - esac ;; -esac -ac_abs_top_builddir=$ac_pwd -ac_abs_builddir=$ac_pwd$ac_dir_suffix -# for backward compatibility: -ac_top_builddir=$ac_top_build_prefix - -case $srcdir in - .) # We are building in place. - ac_srcdir=. - ac_top_srcdir=$ac_top_builddir_sub - ac_abs_top_srcdir=$ac_pwd ;; - [\\/]* | ?:[\\/]* ) # Absolute name. - ac_srcdir=$srcdir$ac_dir_suffix; - ac_top_srcdir=$srcdir - ac_abs_top_srcdir=$srcdir ;; - *) # Relative name. - ac_srcdir=$ac_top_build_prefix$srcdir$ac_dir_suffix - ac_top_srcdir=$ac_top_build_prefix$srcdir - ac_abs_top_srcdir=$ac_pwd/$srcdir ;; -esac -ac_abs_srcdir=$ac_abs_top_srcdir$ac_dir_suffix - - cd "$ac_dir" || { ac_status=$?; continue; } - # Check for guested configure. - if test -f "$ac_srcdir/configure.gnu"; then - echo && - $SHELL "$ac_srcdir/configure.gnu" --help=recursive - elif test -f "$ac_srcdir/configure"; then - echo && - $SHELL "$ac_srcdir/configure" --help=recursive - else - $as_echo "$as_me: WARNING: no configuration information is in $ac_dir" >&2 - fi || ac_status=$? - cd "$ac_pwd" || { ac_status=$?; break; } - done -fi - -test -n "$ac_init_help" && exit $ac_status -if $ac_init_version; then - cat <<\_ACEOF -HermitCore configure 0.1 -generated by GNU Autoconf 2.69 - -Copyright (C) 2012 Free Software Foundation, Inc. -This configure script is free software; the Free Software Foundation -gives unlimited permission to copy, distribute and modify it. -_ACEOF - exit -fi - -## ------------------------ ## -## Autoconf initialization. ## -## ------------------------ ## - -# ac_fn_c_try_compile LINENO -# -------------------------- -# Try to compile conftest.$ac_ext, and return whether this succeeded. -ac_fn_c_try_compile () -{ - as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack - rm -f conftest.$ac_objext - if { { ac_try="$ac_compile" -case "(($ac_try" in - *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; - *) ac_try_echo=$ac_try;; -esac -eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" -$as_echo "$ac_try_echo"; } >&5 - (eval "$ac_compile") 2>conftest.err - ac_status=$? - if test -s conftest.err; then - grep -v '^ *+' conftest.err >conftest.er1 - cat conftest.er1 >&5 - mv -f conftest.er1 conftest.err - fi - $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 - test $ac_status = 0; } && { - test -z "$ac_c_werror_flag" || - test ! -s conftest.err - } && test -s conftest.$ac_objext; then : - ac_retval=0 -else - $as_echo "$as_me: failed program was:" >&5 -sed 's/^/| /' conftest.$ac_ext >&5 - - ac_retval=1 -fi - eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno - as_fn_set_status $ac_retval - -} # ac_fn_c_try_compile -cat >config.log <<_ACEOF -This file contains any messages produced by compilers while -running configure, to aid debugging if configure makes a mistake. - -It was created by HermitCore $as_me 0.1, which was -generated by GNU Autoconf 2.69. Invocation command line was - - $ $0 $@ - -_ACEOF -exec 5>>config.log -{ -cat <<_ASUNAME -## --------- ## -## Platform. ## -## --------- ## - -hostname = `(hostname || uname -n) 2>/dev/null | sed 1q` -uname -m = `(uname -m) 2>/dev/null || echo unknown` -uname -r = `(uname -r) 2>/dev/null || echo unknown` -uname -s = `(uname -s) 2>/dev/null || echo unknown` -uname -v = `(uname -v) 2>/dev/null || echo unknown` - -/usr/bin/uname -p = `(/usr/bin/uname -p) 2>/dev/null || echo unknown` -/bin/uname -X = `(/bin/uname -X) 2>/dev/null || echo unknown` - -/bin/arch = `(/bin/arch) 2>/dev/null || echo unknown` -/usr/bin/arch -k = `(/usr/bin/arch -k) 2>/dev/null || echo unknown` -/usr/convex/getsysinfo = `(/usr/convex/getsysinfo) 2>/dev/null || echo unknown` -/usr/bin/hostinfo = `(/usr/bin/hostinfo) 2>/dev/null || echo unknown` -/bin/machine = `(/bin/machine) 2>/dev/null || echo unknown` -/usr/bin/oslevel = `(/usr/bin/oslevel) 2>/dev/null || echo unknown` -/bin/universe = `(/bin/universe) 2>/dev/null || echo unknown` - -_ASUNAME - -as_save_IFS=$IFS; IFS=$PATH_SEPARATOR -for as_dir in $PATH -do - IFS=$as_save_IFS - test -z "$as_dir" && as_dir=. - $as_echo "PATH: $as_dir" - done -IFS=$as_save_IFS - -} >&5 - -cat >&5 <<_ACEOF - - -## ----------- ## -## Core tests. ## -## ----------- ## - -_ACEOF - - -# Keep a trace of the command line. -# Strip out --no-create and --no-recursion so they do not pile up. -# Strip out --silent because we don't want to record it for future runs. -# Also quote any args containing shell meta-characters. -# Make two passes to allow for proper duplicate-argument suppression. -ac_configure_args= -ac_configure_args0= -ac_configure_args1= -ac_must_keep_next=false -for ac_pass in 1 2 -do - for ac_arg - do - case $ac_arg in - -no-create | --no-c* | -n | -no-recursion | --no-r*) continue ;; - -q | -quiet | --quiet | --quie | --qui | --qu | --q \ - | -silent | --silent | --silen | --sile | --sil) - continue ;; - *\'*) - ac_arg=`$as_echo "$ac_arg" | sed "s/'/'\\\\\\\\''/g"` ;; - esac - case $ac_pass in - 1) as_fn_append ac_configure_args0 " '$ac_arg'" ;; - 2) - as_fn_append ac_configure_args1 " '$ac_arg'" - if test $ac_must_keep_next = true; then - ac_must_keep_next=false # Got value, back to normal. - else - case $ac_arg in - *=* | --config-cache | -C | -disable-* | --disable-* \ - | -enable-* | --enable-* | -gas | --g* | -nfp | --nf* \ - | -q | -quiet | --q* | -silent | --sil* | -v | -verb* \ - | -with-* | --with-* | -without-* | --without-* | --x) - case "$ac_configure_args0 " in - "$ac_configure_args1"*" '$ac_arg' "* ) continue ;; - esac - ;; - -* ) ac_must_keep_next=true ;; - esac - fi - as_fn_append ac_configure_args " '$ac_arg'" - ;; - esac - done -done -{ ac_configure_args0=; unset ac_configure_args0;} -{ ac_configure_args1=; unset ac_configure_args1;} - -# When interrupted or exit'd, cleanup temporary files, and complete -# config.log. We remove comments because anyway the quotes in there -# would cause problems or look ugly. -# WARNING: Use '\'' to represent an apostrophe within the trap. -# WARNING: Do not start the trap code with a newline, due to a FreeBSD 4.0 bug. -trap 'exit_status=$? - # Save into config.log some information that might help in debugging. - { - echo - - $as_echo "## ---------------- ## -## Cache variables. ## -## ---------------- ##" - echo - # The following way of writing the cache mishandles newlines in values, -( - for ac_var in `(set) 2>&1 | sed -n '\''s/^\([a-zA-Z_][a-zA-Z0-9_]*\)=.*/\1/p'\''`; do - eval ac_val=\$$ac_var - case $ac_val in #( - *${as_nl}*) - case $ac_var in #( - *_cv_*) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: cache variable $ac_var contains a newline" >&5 -$as_echo "$as_me: WARNING: cache variable $ac_var contains a newline" >&2;} ;; - esac - case $ac_var in #( - _ | IFS | as_nl) ;; #( - BASH_ARGV | BASH_SOURCE) eval $ac_var= ;; #( - *) { eval $ac_var=; unset $ac_var;} ;; - esac ;; - esac - done - (set) 2>&1 | - case $as_nl`(ac_space='\'' '\''; set) 2>&1` in #( - *${as_nl}ac_space=\ *) - sed -n \ - "s/'\''/'\''\\\\'\'''\''/g; - s/^\\([_$as_cr_alnum]*_cv_[_$as_cr_alnum]*\\)=\\(.*\\)/\\1='\''\\2'\''/p" - ;; #( - *) - sed -n "/^[_$as_cr_alnum]*_cv_[_$as_cr_alnum]*=/p" - ;; - esac | - sort -) - echo - - $as_echo "## ----------------- ## -## Output variables. ## -## ----------------- ##" - echo - for ac_var in $ac_subst_vars - do - eval ac_val=\$$ac_var - case $ac_val in - *\'\''*) ac_val=`$as_echo "$ac_val" | sed "s/'\''/'\''\\\\\\\\'\'''\''/g"`;; - esac - $as_echo "$ac_var='\''$ac_val'\''" - done | sort - echo - - if test -n "$ac_subst_files"; then - $as_echo "## ------------------- ## -## File substitutions. ## -## ------------------- ##" - echo - for ac_var in $ac_subst_files - do - eval ac_val=\$$ac_var - case $ac_val in - *\'\''*) ac_val=`$as_echo "$ac_val" | sed "s/'\''/'\''\\\\\\\\'\'''\''/g"`;; - esac - $as_echo "$ac_var='\''$ac_val'\''" - done | sort - echo - fi - - if test -s confdefs.h; then - $as_echo "## ----------- ## -## confdefs.h. ## -## ----------- ##" - echo - cat confdefs.h - echo - fi - test "$ac_signal" != 0 && - $as_echo "$as_me: caught signal $ac_signal" - $as_echo "$as_me: exit $exit_status" - } >&5 - rm -f core *.core core.conftest.* && - rm -f -r conftest* confdefs* conf$$* $ac_clean_files && - exit $exit_status -' 0 -for ac_signal in 1 2 13 15; do - trap 'ac_signal='$ac_signal'; as_fn_exit 1' $ac_signal -done -ac_signal=0 - -# confdefs.h avoids OS command line length limits that DEFS can exceed. -rm -f -r conftest* confdefs.h - -$as_echo "/* confdefs.h */" > confdefs.h - -# Predefined preprocessor variables. - -cat >>confdefs.h <<_ACEOF -#define PACKAGE_NAME "$PACKAGE_NAME" -_ACEOF - -cat >>confdefs.h <<_ACEOF -#define PACKAGE_TARNAME "$PACKAGE_TARNAME" -_ACEOF - -cat >>confdefs.h <<_ACEOF -#define PACKAGE_VERSION "$PACKAGE_VERSION" -_ACEOF - -cat >>confdefs.h <<_ACEOF -#define PACKAGE_STRING "$PACKAGE_STRING" -_ACEOF - -cat >>confdefs.h <<_ACEOF -#define PACKAGE_BUGREPORT "$PACKAGE_BUGREPORT" -_ACEOF - -cat >>confdefs.h <<_ACEOF -#define PACKAGE_URL "$PACKAGE_URL" -_ACEOF - - -# Let the site file select an alternate cache file if it wants to. -# Prefer an explicitly selected file to automatically selected ones. -ac_site_file1=NONE -ac_site_file2=NONE -if test -n "$CONFIG_SITE"; then - # We do not want a PATH search for config.site. - case $CONFIG_SITE in #(( - -*) ac_site_file1=./$CONFIG_SITE;; - */*) ac_site_file1=$CONFIG_SITE;; - *) ac_site_file1=./$CONFIG_SITE;; - esac -elif test "x$prefix" != xNONE; then - ac_site_file1=$prefix/share/config.site - ac_site_file2=$prefix/etc/config.site -else - ac_site_file1=$ac_default_prefix/share/config.site - ac_site_file2=$ac_default_prefix/etc/config.site -fi -for ac_site_file in "$ac_site_file1" "$ac_site_file2" -do - test "x$ac_site_file" = xNONE && continue - if test /dev/null != "$ac_site_file" && test -r "$ac_site_file"; then - { $as_echo "$as_me:${as_lineno-$LINENO}: loading site script $ac_site_file" >&5 -$as_echo "$as_me: loading site script $ac_site_file" >&6;} - sed 's/^/| /' "$ac_site_file" >&5 - . "$ac_site_file" \ - || { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 -$as_echo "$as_me: error: in \`$ac_pwd':" >&2;} -as_fn_error $? "failed to load site script $ac_site_file -See \`config.log' for more details" "$LINENO" 5; } - fi -done - -if test -r "$cache_file"; then - # Some versions of bash will fail to source /dev/null (special files - # actually), so we avoid doing that. DJGPP emulates it as a regular file. - if test /dev/null != "$cache_file" && test -f "$cache_file"; then - { $as_echo "$as_me:${as_lineno-$LINENO}: loading cache $cache_file" >&5 -$as_echo "$as_me: loading cache $cache_file" >&6;} - case $cache_file in - [\\/]* | ?:[\\/]* ) . "$cache_file";; - *) . "./$cache_file";; - esac - fi -else - { $as_echo "$as_me:${as_lineno-$LINENO}: creating cache $cache_file" >&5 -$as_echo "$as_me: creating cache $cache_file" >&6;} - >$cache_file -fi - -# Check that the precious variables saved in the cache have kept the same -# value. -ac_cache_corrupted=false -for ac_var in $ac_precious_vars; do - eval ac_old_set=\$ac_cv_env_${ac_var}_set - eval ac_new_set=\$ac_env_${ac_var}_set - eval ac_old_val=\$ac_cv_env_${ac_var}_value - eval ac_new_val=\$ac_env_${ac_var}_value - case $ac_old_set,$ac_new_set in - set,) - { $as_echo "$as_me:${as_lineno-$LINENO}: error: \`$ac_var' was set to \`$ac_old_val' in the previous run" >&5 -$as_echo "$as_me: error: \`$ac_var' was set to \`$ac_old_val' in the previous run" >&2;} - ac_cache_corrupted=: ;; - ,set) - { $as_echo "$as_me:${as_lineno-$LINENO}: error: \`$ac_var' was not set in the previous run" >&5 -$as_echo "$as_me: error: \`$ac_var' was not set in the previous run" >&2;} - ac_cache_corrupted=: ;; - ,);; - *) - if test "x$ac_old_val" != "x$ac_new_val"; then - # differences in whitespace do not lead to failure. - ac_old_val_w=`echo x $ac_old_val` - ac_new_val_w=`echo x $ac_new_val` - if test "$ac_old_val_w" != "$ac_new_val_w"; then - { $as_echo "$as_me:${as_lineno-$LINENO}: error: \`$ac_var' has changed since the previous run:" >&5 -$as_echo "$as_me: error: \`$ac_var' has changed since the previous run:" >&2;} - ac_cache_corrupted=: - else - { $as_echo "$as_me:${as_lineno-$LINENO}: warning: ignoring whitespace changes in \`$ac_var' since the previous run:" >&5 -$as_echo "$as_me: warning: ignoring whitespace changes in \`$ac_var' since the previous run:" >&2;} - eval $ac_var=\$ac_old_val - fi - { $as_echo "$as_me:${as_lineno-$LINENO}: former value: \`$ac_old_val'" >&5 -$as_echo "$as_me: former value: \`$ac_old_val'" >&2;} - { $as_echo "$as_me:${as_lineno-$LINENO}: current value: \`$ac_new_val'" >&5 -$as_echo "$as_me: current value: \`$ac_new_val'" >&2;} - fi;; - esac - # Pass precious variables to config.status. - if test "$ac_new_set" = set; then - case $ac_new_val in - *\'*) ac_arg=$ac_var=`$as_echo "$ac_new_val" | sed "s/'/'\\\\\\\\''/g"` ;; - *) ac_arg=$ac_var=$ac_new_val ;; - esac - case " $ac_configure_args " in - *" '$ac_arg' "*) ;; # Avoid dups. Use of quotes ensures accuracy. - *) as_fn_append ac_configure_args " '$ac_arg'" ;; - esac - fi -done -if $ac_cache_corrupted; then - { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 -$as_echo "$as_me: error: in \`$ac_pwd':" >&2;} - { $as_echo "$as_me:${as_lineno-$LINENO}: error: changes in the environment can compromise the build" >&5 -$as_echo "$as_me: error: changes in the environment can compromise the build" >&2;} - as_fn_error $? "run \`make distclean' and/or \`rm $cache_file' and start over" "$LINENO" 5 -fi -## -------------------- ## -## Main body of script. ## -## -------------------- ## - -ac_ext=c -ac_cpp='$CPP $CPPFLAGS' -ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' -ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' -ac_compiler_gnu=$ac_cv_c_compiler_gnu - - -for ac_prog in qemu-system-x86_64 -do - # Extract the first word of "$ac_prog", so it can be a program name with args. -set dummy $ac_prog; ac_word=$2 -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 -$as_echo_n "checking for $ac_word... " >&6; } -if ${ac_cv_prog_QEMU+:} false; then : - $as_echo_n "(cached) " >&6 -else - if test -n "$QEMU"; then - ac_cv_prog_QEMU="$QEMU" # Let the user override the test. -else -as_save_IFS=$IFS; IFS=$PATH_SEPARATOR -for as_dir in $PATH -do - IFS=$as_save_IFS - test -z "$as_dir" && as_dir=. - for ac_exec_ext in '' $ac_executable_extensions; do - if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then - ac_cv_prog_QEMU="$ac_prog" - $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 - break 2 - fi -done - done -IFS=$as_save_IFS - -fi -fi -QEMU=$ac_cv_prog_QEMU -if test -n "$QEMU"; then - { $as_echo "$as_me:${as_lineno-$LINENO}: result: $QEMU" >&5 -$as_echo "$QEMU" >&6; } -else - { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 -$as_echo "no" >&6; } -fi - - - test -n "$QEMU" && break -done - - -ac_config_headers="$ac_config_headers include/hermit/config.h" - - -# Checks for programs. -ac_ext=c -ac_cpp='$CPP $CPPFLAGS' -ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' -ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' -ac_compiler_gnu=$ac_cv_c_compiler_gnu -if test -n "$ac_tool_prefix"; then - # Extract the first word of "${ac_tool_prefix}gcc", so it can be a program name with args. -set dummy ${ac_tool_prefix}gcc; ac_word=$2 -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 -$as_echo_n "checking for $ac_word... " >&6; } -if ${ac_cv_prog_CC+:} false; then : - $as_echo_n "(cached) " >&6 -else - if test -n "$CC"; then - ac_cv_prog_CC="$CC" # Let the user override the test. -else -as_save_IFS=$IFS; IFS=$PATH_SEPARATOR -for as_dir in $PATH -do - IFS=$as_save_IFS - test -z "$as_dir" && as_dir=. - for ac_exec_ext in '' $ac_executable_extensions; do - if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then - ac_cv_prog_CC="${ac_tool_prefix}gcc" - $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 - break 2 - fi -done - done -IFS=$as_save_IFS - -fi -fi -CC=$ac_cv_prog_CC -if test -n "$CC"; then - { $as_echo "$as_me:${as_lineno-$LINENO}: result: $CC" >&5 -$as_echo "$CC" >&6; } -else - { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 -$as_echo "no" >&6; } -fi - - -fi -if test -z "$ac_cv_prog_CC"; then - ac_ct_CC=$CC - # Extract the first word of "gcc", so it can be a program name with args. -set dummy gcc; ac_word=$2 -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 -$as_echo_n "checking for $ac_word... " >&6; } -if ${ac_cv_prog_ac_ct_CC+:} false; then : - $as_echo_n "(cached) " >&6 -else - if test -n "$ac_ct_CC"; then - ac_cv_prog_ac_ct_CC="$ac_ct_CC" # Let the user override the test. -else -as_save_IFS=$IFS; IFS=$PATH_SEPARATOR -for as_dir in $PATH -do - IFS=$as_save_IFS - test -z "$as_dir" && as_dir=. - for ac_exec_ext in '' $ac_executable_extensions; do - if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then - ac_cv_prog_ac_ct_CC="gcc" - $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 - break 2 - fi -done - done -IFS=$as_save_IFS - -fi -fi -ac_ct_CC=$ac_cv_prog_ac_ct_CC -if test -n "$ac_ct_CC"; then - { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_CC" >&5 -$as_echo "$ac_ct_CC" >&6; } -else - { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 -$as_echo "no" >&6; } -fi - - if test "x$ac_ct_CC" = x; then - CC="" - else - case $cross_compiling:$ac_tool_warned in -yes:) -{ $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 -$as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} -ac_tool_warned=yes ;; -esac - CC=$ac_ct_CC - fi -else - CC="$ac_cv_prog_CC" -fi - -if test -z "$CC"; then - if test -n "$ac_tool_prefix"; then - # Extract the first word of "${ac_tool_prefix}cc", so it can be a program name with args. -set dummy ${ac_tool_prefix}cc; ac_word=$2 -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 -$as_echo_n "checking for $ac_word... " >&6; } -if ${ac_cv_prog_CC+:} false; then : - $as_echo_n "(cached) " >&6 -else - if test -n "$CC"; then - ac_cv_prog_CC="$CC" # Let the user override the test. -else -as_save_IFS=$IFS; IFS=$PATH_SEPARATOR -for as_dir in $PATH -do - IFS=$as_save_IFS - test -z "$as_dir" && as_dir=. - for ac_exec_ext in '' $ac_executable_extensions; do - if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then - ac_cv_prog_CC="${ac_tool_prefix}cc" - $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 - break 2 - fi -done - done -IFS=$as_save_IFS - -fi -fi -CC=$ac_cv_prog_CC -if test -n "$CC"; then - { $as_echo "$as_me:${as_lineno-$LINENO}: result: $CC" >&5 -$as_echo "$CC" >&6; } -else - { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 -$as_echo "no" >&6; } -fi - - - fi -fi -if test -z "$CC"; then - # Extract the first word of "cc", so it can be a program name with args. -set dummy cc; ac_word=$2 -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 -$as_echo_n "checking for $ac_word... " >&6; } -if ${ac_cv_prog_CC+:} false; then : - $as_echo_n "(cached) " >&6 -else - if test -n "$CC"; then - ac_cv_prog_CC="$CC" # Let the user override the test. -else - ac_prog_rejected=no -as_save_IFS=$IFS; IFS=$PATH_SEPARATOR -for as_dir in $PATH -do - IFS=$as_save_IFS - test -z "$as_dir" && as_dir=. - for ac_exec_ext in '' $ac_executable_extensions; do - if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then - if test "$as_dir/$ac_word$ac_exec_ext" = "/usr/ucb/cc"; then - ac_prog_rejected=yes - continue - fi - ac_cv_prog_CC="cc" - $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 - break 2 - fi -done - done -IFS=$as_save_IFS - -if test $ac_prog_rejected = yes; then - # We found a bogon in the path, so make sure we never use it. - set dummy $ac_cv_prog_CC - shift - if test $# != 0; then - # We chose a different compiler from the bogus one. - # However, it has the same basename, so the bogon will be chosen - # first if we set CC to just the basename; use the full file name. - shift - ac_cv_prog_CC="$as_dir/$ac_word${1+' '}$@" - fi -fi -fi -fi -CC=$ac_cv_prog_CC -if test -n "$CC"; then - { $as_echo "$as_me:${as_lineno-$LINENO}: result: $CC" >&5 -$as_echo "$CC" >&6; } -else - { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 -$as_echo "no" >&6; } -fi - - -fi -if test -z "$CC"; then - if test -n "$ac_tool_prefix"; then - for ac_prog in cl.exe - do - # Extract the first word of "$ac_tool_prefix$ac_prog", so it can be a program name with args. -set dummy $ac_tool_prefix$ac_prog; ac_word=$2 -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 -$as_echo_n "checking for $ac_word... " >&6; } -if ${ac_cv_prog_CC+:} false; then : - $as_echo_n "(cached) " >&6 -else - if test -n "$CC"; then - ac_cv_prog_CC="$CC" # Let the user override the test. -else -as_save_IFS=$IFS; IFS=$PATH_SEPARATOR -for as_dir in $PATH -do - IFS=$as_save_IFS - test -z "$as_dir" && as_dir=. - for ac_exec_ext in '' $ac_executable_extensions; do - if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then - ac_cv_prog_CC="$ac_tool_prefix$ac_prog" - $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 - break 2 - fi -done - done -IFS=$as_save_IFS - -fi -fi -CC=$ac_cv_prog_CC -if test -n "$CC"; then - { $as_echo "$as_me:${as_lineno-$LINENO}: result: $CC" >&5 -$as_echo "$CC" >&6; } -else - { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 -$as_echo "no" >&6; } -fi - - - test -n "$CC" && break - done -fi -if test -z "$CC"; then - ac_ct_CC=$CC - for ac_prog in cl.exe -do - # Extract the first word of "$ac_prog", so it can be a program name with args. -set dummy $ac_prog; ac_word=$2 -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $ac_word" >&5 -$as_echo_n "checking for $ac_word... " >&6; } -if ${ac_cv_prog_ac_ct_CC+:} false; then : - $as_echo_n "(cached) " >&6 -else - if test -n "$ac_ct_CC"; then - ac_cv_prog_ac_ct_CC="$ac_ct_CC" # Let the user override the test. -else -as_save_IFS=$IFS; IFS=$PATH_SEPARATOR -for as_dir in $PATH -do - IFS=$as_save_IFS - test -z "$as_dir" && as_dir=. - for ac_exec_ext in '' $ac_executable_extensions; do - if as_fn_executable_p "$as_dir/$ac_word$ac_exec_ext"; then - ac_cv_prog_ac_ct_CC="$ac_prog" - $as_echo "$as_me:${as_lineno-$LINENO}: found $as_dir/$ac_word$ac_exec_ext" >&5 - break 2 - fi -done - done -IFS=$as_save_IFS - -fi -fi -ac_ct_CC=$ac_cv_prog_ac_ct_CC -if test -n "$ac_ct_CC"; then - { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_ct_CC" >&5 -$as_echo "$ac_ct_CC" >&6; } -else - { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 -$as_echo "no" >&6; } -fi - - - test -n "$ac_ct_CC" && break -done - - if test "x$ac_ct_CC" = x; then - CC="" - else - case $cross_compiling:$ac_tool_warned in -yes:) -{ $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet" >&5 -$as_echo "$as_me: WARNING: using cross tools not prefixed with host triplet" >&2;} -ac_tool_warned=yes ;; -esac - CC=$ac_ct_CC - fi -fi - -fi - - -test -z "$CC" && { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 -$as_echo "$as_me: error: in \`$ac_pwd':" >&2;} -as_fn_error $? "no acceptable C compiler found in \$PATH -See \`config.log' for more details" "$LINENO" 5; } - -# Provide some information about the compiler. -$as_echo "$as_me:${as_lineno-$LINENO}: checking for C compiler version" >&5 -set X $ac_compile -ac_compiler=$2 -for ac_option in --version -v -V -qversion; do - { { ac_try="$ac_compiler $ac_option >&5" -case "(($ac_try" in - *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; - *) ac_try_echo=$ac_try;; -esac -eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" -$as_echo "$ac_try_echo"; } >&5 - (eval "$ac_compiler $ac_option >&5") 2>conftest.err - ac_status=$? - if test -s conftest.err; then - sed '10a\ -... rest of stderr output deleted ... - 10q' conftest.err >conftest.er1 - cat conftest.er1 >&5 - fi - rm -f conftest.er1 conftest.err - $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 - test $ac_status = 0; } -done - -cat confdefs.h - <<_ACEOF >conftest.$ac_ext -/* end confdefs.h. */ - -int -main () -{ - - ; - return 0; -} -_ACEOF -ac_clean_files_save=$ac_clean_files -ac_clean_files="$ac_clean_files a.out a.out.dSYM a.exe b.out" -# Try to create an executable without -o first, disregard a.out. -# It will help us diagnose broken compilers, and finding out an intuition -# of exeext. -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether the C compiler works" >&5 -$as_echo_n "checking whether the C compiler works... " >&6; } -ac_link_default=`$as_echo "$ac_link" | sed 's/ -o *conftest[^ ]*//'` - -# The possible output files: -ac_files="a.out conftest.exe conftest a.exe a_out.exe b.out conftest.*" - -ac_rmfiles= -for ac_file in $ac_files -do - case $ac_file in - *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM | *.o | *.obj ) ;; - * ) ac_rmfiles="$ac_rmfiles $ac_file";; - esac -done -rm -f $ac_rmfiles - -if { { ac_try="$ac_link_default" -case "(($ac_try" in - *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; - *) ac_try_echo=$ac_try;; -esac -eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" -$as_echo "$ac_try_echo"; } >&5 - (eval "$ac_link_default") 2>&5 - ac_status=$? - $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 - test $ac_status = 0; }; then : - # Autoconf-2.13 could set the ac_cv_exeext variable to `no'. -# So ignore a value of `no', otherwise this would lead to `EXEEXT = no' -# in a Makefile. We should not override ac_cv_exeext if it was cached, -# so that the user can short-circuit this test for compilers unknown to -# Autoconf. -for ac_file in $ac_files '' -do - test -f "$ac_file" || continue - case $ac_file in - *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM | *.o | *.obj ) - ;; - [ab].out ) - # We found the default executable, but exeext='' is most - # certainly right. - break;; - *.* ) - if test "${ac_cv_exeext+set}" = set && test "$ac_cv_exeext" != no; - then :; else - ac_cv_exeext=`expr "$ac_file" : '[^.]*\(\..*\)'` - fi - # We set ac_cv_exeext here because the later test for it is not - # safe: cross compilers may not add the suffix if given an `-o' - # argument, so we may need to know it at that point already. - # Even if this section looks crufty: it has the advantage of - # actually working. - break;; - * ) - break;; - esac -done -test "$ac_cv_exeext" = no && ac_cv_exeext= - -else - ac_file='' -fi -if test -z "$ac_file"; then : - { $as_echo "$as_me:${as_lineno-$LINENO}: result: no" >&5 -$as_echo "no" >&6; } -$as_echo "$as_me: failed program was:" >&5 -sed 's/^/| /' conftest.$ac_ext >&5 - -{ { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 -$as_echo "$as_me: error: in \`$ac_pwd':" >&2;} -as_fn_error 77 "C compiler cannot create executables -See \`config.log' for more details" "$LINENO" 5; } -else - { $as_echo "$as_me:${as_lineno-$LINENO}: result: yes" >&5 -$as_echo "yes" >&6; } -fi -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for C compiler default output file name" >&5 -$as_echo_n "checking for C compiler default output file name... " >&6; } -{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_file" >&5 -$as_echo "$ac_file" >&6; } -ac_exeext=$ac_cv_exeext - -rm -f -r a.out a.out.dSYM a.exe conftest$ac_cv_exeext b.out -ac_clean_files=$ac_clean_files_save -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for suffix of executables" >&5 -$as_echo_n "checking for suffix of executables... " >&6; } -if { { ac_try="$ac_link" -case "(($ac_try" in - *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; - *) ac_try_echo=$ac_try;; -esac -eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" -$as_echo "$ac_try_echo"; } >&5 - (eval "$ac_link") 2>&5 - ac_status=$? - $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 - test $ac_status = 0; }; then : - # If both `conftest.exe' and `conftest' are `present' (well, observable) -# catch `conftest.exe'. For instance with Cygwin, `ls conftest' will -# work properly (i.e., refer to `conftest.exe'), while it won't with -# `rm'. -for ac_file in conftest.exe conftest conftest.*; do - test -f "$ac_file" || continue - case $ac_file in - *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM | *.o | *.obj ) ;; - *.* ) ac_cv_exeext=`expr "$ac_file" : '[^.]*\(\..*\)'` - break;; - * ) break;; - esac -done -else - { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 -$as_echo "$as_me: error: in \`$ac_pwd':" >&2;} -as_fn_error $? "cannot compute suffix of executables: cannot compile and link -See \`config.log' for more details" "$LINENO" 5; } -fi -rm -f conftest conftest$ac_cv_exeext -{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_exeext" >&5 -$as_echo "$ac_cv_exeext" >&6; } - -rm -f conftest.$ac_ext -EXEEXT=$ac_cv_exeext -ac_exeext=$EXEEXT -cat confdefs.h - <<_ACEOF >conftest.$ac_ext -/* end confdefs.h. */ -#include -int -main () -{ -FILE *f = fopen ("conftest.out", "w"); - return ferror (f) || fclose (f) != 0; - - ; - return 0; -} -_ACEOF -ac_clean_files="$ac_clean_files conftest.out" -# Check that the compiler produces executables we can run. If not, either -# the compiler is broken, or we cross compile. -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether we are cross compiling" >&5 -$as_echo_n "checking whether we are cross compiling... " >&6; } -if test "$cross_compiling" != yes; then - { { ac_try="$ac_link" -case "(($ac_try" in - *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; - *) ac_try_echo=$ac_try;; -esac -eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" -$as_echo "$ac_try_echo"; } >&5 - (eval "$ac_link") 2>&5 - ac_status=$? - $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 - test $ac_status = 0; } - if { ac_try='./conftest$ac_cv_exeext' - { { case "(($ac_try" in - *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; - *) ac_try_echo=$ac_try;; -esac -eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" -$as_echo "$ac_try_echo"; } >&5 - (eval "$ac_try") 2>&5 - ac_status=$? - $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 - test $ac_status = 0; }; }; then - cross_compiling=no - else - if test "$cross_compiling" = maybe; then - cross_compiling=yes - else - { { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 -$as_echo "$as_me: error: in \`$ac_pwd':" >&2;} -as_fn_error $? "cannot run C compiled programs. -If you meant to cross compile, use \`--host'. -See \`config.log' for more details" "$LINENO" 5; } - fi - fi -fi -{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $cross_compiling" >&5 -$as_echo "$cross_compiling" >&6; } - -rm -f conftest.$ac_ext conftest$ac_cv_exeext conftest.out -ac_clean_files=$ac_clean_files_save -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for suffix of object files" >&5 -$as_echo_n "checking for suffix of object files... " >&6; } -if ${ac_cv_objext+:} false; then : - $as_echo_n "(cached) " >&6 -else - cat confdefs.h - <<_ACEOF >conftest.$ac_ext -/* end confdefs.h. */ - -int -main () -{ - - ; - return 0; -} -_ACEOF -rm -f conftest.o conftest.obj -if { { ac_try="$ac_compile" -case "(($ac_try" in - *\"* | *\`* | *\\*) ac_try_echo=\$ac_try;; - *) ac_try_echo=$ac_try;; -esac -eval ac_try_echo="\"\$as_me:${as_lineno-$LINENO}: $ac_try_echo\"" -$as_echo "$ac_try_echo"; } >&5 - (eval "$ac_compile") 2>&5 - ac_status=$? - $as_echo "$as_me:${as_lineno-$LINENO}: \$? = $ac_status" >&5 - test $ac_status = 0; }; then : - for ac_file in conftest.o conftest.obj conftest.*; do - test -f "$ac_file" || continue; - case $ac_file in - *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM ) ;; - *) ac_cv_objext=`expr "$ac_file" : '.*\.\(.*\)'` - break;; - esac -done -else - $as_echo "$as_me: failed program was:" >&5 -sed 's/^/| /' conftest.$ac_ext >&5 - -{ { $as_echo "$as_me:${as_lineno-$LINENO}: error: in \`$ac_pwd':" >&5 -$as_echo "$as_me: error: in \`$ac_pwd':" >&2;} -as_fn_error $? "cannot compute suffix of object files: cannot compile -See \`config.log' for more details" "$LINENO" 5; } -fi -rm -f conftest.$ac_cv_objext conftest.$ac_ext -fi -{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_objext" >&5 -$as_echo "$ac_cv_objext" >&6; } -OBJEXT=$ac_cv_objext -ac_objext=$OBJEXT -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether we are using the GNU C compiler" >&5 -$as_echo_n "checking whether we are using the GNU C compiler... " >&6; } -if ${ac_cv_c_compiler_gnu+:} false; then : - $as_echo_n "(cached) " >&6 -else - cat confdefs.h - <<_ACEOF >conftest.$ac_ext -/* end confdefs.h. */ - -int -main () -{ -#ifndef __GNUC__ - choke me -#endif - - ; - return 0; -} -_ACEOF -if ac_fn_c_try_compile "$LINENO"; then : - ac_compiler_gnu=yes -else - ac_compiler_gnu=no -fi -rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext -ac_cv_c_compiler_gnu=$ac_compiler_gnu - -fi -{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_c_compiler_gnu" >&5 -$as_echo "$ac_cv_c_compiler_gnu" >&6; } -if test $ac_compiler_gnu = yes; then - GCC=yes -else - GCC= -fi -ac_test_CFLAGS=${CFLAGS+set} -ac_save_CFLAGS=$CFLAGS -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking whether $CC accepts -g" >&5 -$as_echo_n "checking whether $CC accepts -g... " >&6; } -if ${ac_cv_prog_cc_g+:} false; then : - $as_echo_n "(cached) " >&6 -else - ac_save_c_werror_flag=$ac_c_werror_flag - ac_c_werror_flag=yes - ac_cv_prog_cc_g=no - CFLAGS="-g" - cat confdefs.h - <<_ACEOF >conftest.$ac_ext -/* end confdefs.h. */ - -int -main () -{ - - ; - return 0; -} -_ACEOF -if ac_fn_c_try_compile "$LINENO"; then : - ac_cv_prog_cc_g=yes -else - CFLAGS="" - cat confdefs.h - <<_ACEOF >conftest.$ac_ext -/* end confdefs.h. */ - -int -main () -{ - - ; - return 0; -} -_ACEOF -if ac_fn_c_try_compile "$LINENO"; then : - -else - ac_c_werror_flag=$ac_save_c_werror_flag - CFLAGS="-g" - cat confdefs.h - <<_ACEOF >conftest.$ac_ext -/* end confdefs.h. */ - -int -main () -{ - - ; - return 0; -} -_ACEOF -if ac_fn_c_try_compile "$LINENO"; then : - ac_cv_prog_cc_g=yes -fi -rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext -fi -rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext -fi -rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext - ac_c_werror_flag=$ac_save_c_werror_flag -fi -{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_prog_cc_g" >&5 -$as_echo "$ac_cv_prog_cc_g" >&6; } -if test "$ac_test_CFLAGS" = set; then - CFLAGS=$ac_save_CFLAGS -elif test $ac_cv_prog_cc_g = yes; then - if test "$GCC" = yes; then - CFLAGS="-g -O2" - else - CFLAGS="-g" - fi -else - if test "$GCC" = yes; then - CFLAGS="-O2" - else - CFLAGS= - fi -fi -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $CC option to accept ISO C89" >&5 -$as_echo_n "checking for $CC option to accept ISO C89... " >&6; } -if ${ac_cv_prog_cc_c89+:} false; then : - $as_echo_n "(cached) " >&6 -else - ac_cv_prog_cc_c89=no -ac_save_CC=$CC -cat confdefs.h - <<_ACEOF >conftest.$ac_ext -/* end confdefs.h. */ -#include -#include -struct stat; -/* Most of the following tests are stolen from RCS 5.7's src/conf.sh. */ -struct buf { int x; }; -FILE * (*rcsopen) (struct buf *, struct stat *, int); -static char *e (p, i) - char **p; - int i; -{ - return p[i]; -} -static char *f (char * (*g) (char **, int), char **p, ...) -{ - char *s; - va_list v; - va_start (v,p); - s = g (p, va_arg (v,int)); - va_end (v); - return s; -} - -/* OSF 4.0 Compaq cc is some sort of almost-ANSI by default. It has - function prototypes and stuff, but not '\xHH' hex character constants. - These don't provoke an error unfortunately, instead are silently treated - as 'x'. The following induces an error, until -std is added to get - proper ANSI mode. Curiously '\x00'!='x' always comes out true, for an - array size at least. It's necessary to write '\x00'==0 to get something - that's true only with -std. */ -int osf4_cc_array ['\x00' == 0 ? 1 : -1]; - -/* IBM C 6 for AIX is almost-ANSI by default, but it replaces macro parameters - inside strings and character constants. */ -#define FOO(x) 'x' -int xlc6_cc_array[FOO(a) == 'x' ? 1 : -1]; - -int test (int i, double x); -struct s1 {int (*f) (int a);}; -struct s2 {int (*f) (double a);}; -int pairnames (int, char **, FILE *(*)(struct buf *, struct stat *, int), int, int); -int argc; -char **argv; -int -main () -{ -return f (e, argv, 0) != argv[0] || f (e, argv, 1) != argv[1]; - ; - return 0; -} -_ACEOF -for ac_arg in '' -qlanglvl=extc89 -qlanglvl=ansi -std \ - -Ae "-Aa -D_HPUX_SOURCE" "-Xc -D__EXTENSIONS__" -do - CC="$ac_save_CC $ac_arg" - if ac_fn_c_try_compile "$LINENO"; then : - ac_cv_prog_cc_c89=$ac_arg -fi -rm -f core conftest.err conftest.$ac_objext - test "x$ac_cv_prog_cc_c89" != "xno" && break -done -rm -f conftest.$ac_ext -CC=$ac_save_CC - -fi -# AC_CACHE_VAL -case "x$ac_cv_prog_cc_c89" in - x) - { $as_echo "$as_me:${as_lineno-$LINENO}: result: none needed" >&5 -$as_echo "none needed" >&6; } ;; - xno) - { $as_echo "$as_me:${as_lineno-$LINENO}: result: unsupported" >&5 -$as_echo "unsupported" >&6; } ;; - *) - CC="$CC $ac_cv_prog_cc_c89" - { $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_cv_prog_cc_c89" >&5 -$as_echo "$ac_cv_prog_cc_c89" >&6; } ;; -esac -if test "x$ac_cv_prog_cc_c89" != xno; then : - -fi - -ac_ext=c -ac_cpp='$CPP $CPPFLAGS' -ac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5' -ac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5' -ac_compiler_gnu=$ac_cv_c_compiler_gnu - -ac_aux_dir= -for ac_dir in "$srcdir" "$srcdir/.." "$srcdir/../.."; do - if test -f "$ac_dir/install-sh"; then - ac_aux_dir=$ac_dir - ac_install_sh="$ac_aux_dir/install-sh -c" - break - elif test -f "$ac_dir/install.sh"; then - ac_aux_dir=$ac_dir - ac_install_sh="$ac_aux_dir/install.sh -c" - break - elif test -f "$ac_dir/shtool"; then - ac_aux_dir=$ac_dir - ac_install_sh="$ac_aux_dir/shtool install -c" - break - fi -done -if test -z "$ac_aux_dir"; then - as_fn_error $? "cannot find install-sh, install.sh, or shtool in \"$srcdir\" \"$srcdir/..\" \"$srcdir/../..\"" "$LINENO" 5 -fi - -# These three variables are undocumented and unsupported, -# and are intended to be withdrawn in a future Autoconf release. -# They can cause serious problems if a builder's source tree is in a directory -# whose full name contains unusual characters. -ac_config_guess="$SHELL $ac_aux_dir/config.guess" # Please don't use this var. -ac_config_sub="$SHELL $ac_aux_dir/config.sub" # Please don't use this var. -ac_configure="$SHELL $ac_aux_dir/configure" # Please don't use this var. - - -# Find a good install program. We prefer a C program (faster), -# so one script is as good as another. But avoid the broken or -# incompatible versions: -# SysV /etc/install, /usr/sbin/install -# SunOS /usr/etc/install -# IRIX /sbin/install -# AIX /bin/install -# AmigaOS /C/install, which installs bootblocks on floppy discs -# AIX 4 /usr/bin/installbsd, which doesn't work without a -g flag -# AFS /usr/afsws/bin/install, which mishandles nonexistent args -# SVR4 /usr/ucb/install, which tries to use the nonexistent group "staff" -# OS/2's system install, which has a completely different semantic -# ./install, which can be erroneously created by make from ./install.sh. -# Reject install programs that cannot install multiple files. -{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for a BSD-compatible install" >&5 -$as_echo_n "checking for a BSD-compatible install... " >&6; } -if test -z "$INSTALL"; then -if ${ac_cv_path_install+:} false; then : - $as_echo_n "(cached) " >&6 -else - as_save_IFS=$IFS; IFS=$PATH_SEPARATOR -for as_dir in $PATH -do - IFS=$as_save_IFS - test -z "$as_dir" && as_dir=. - # Account for people who put trailing slashes in PATH elements. -case $as_dir/ in #(( - ./ | .// | /[cC]/* | \ - /etc/* | /usr/sbin/* | /usr/etc/* | /sbin/* | /usr/afsws/bin/* | \ - ?:[\\/]os2[\\/]install[\\/]* | ?:[\\/]OS2[\\/]INSTALL[\\/]* | \ - /usr/ucb/* ) ;; - *) - # OSF1 and SCO ODT 3.0 have their own names for install. - # Don't use installbsd from OSF since it installs stuff as root - # by default. - for ac_prog in ginstall scoinst install; do - for ac_exec_ext in '' $ac_executable_extensions; do - if as_fn_executable_p "$as_dir/$ac_prog$ac_exec_ext"; then - if test $ac_prog = install && - grep dspmsg "$as_dir/$ac_prog$ac_exec_ext" >/dev/null 2>&1; then - # AIX install. It has an incompatible calling convention. - : - elif test $ac_prog = install && - grep pwplus "$as_dir/$ac_prog$ac_exec_ext" >/dev/null 2>&1; then - # program-specific install script used by HP pwplus--don't use. - : - else - rm -rf conftest.one conftest.two conftest.dir - echo one > conftest.one - echo two > conftest.two - mkdir conftest.dir - if "$as_dir/$ac_prog$ac_exec_ext" -c conftest.one conftest.two "`pwd`/conftest.dir" && - test -s conftest.one && test -s conftest.two && - test -s conftest.dir/conftest.one && - test -s conftest.dir/conftest.two - then - ac_cv_path_install="$as_dir/$ac_prog$ac_exec_ext -c" - break 3 - fi - fi - fi - done - done - ;; -esac - - done -IFS=$as_save_IFS - -rm -rf conftest.one conftest.two conftest.dir - -fi - if test "${ac_cv_path_install+set}" = set; then - INSTALL=$ac_cv_path_install - else - # As a last resort, use the slow shell script. Don't cache a - # value for INSTALL within a source directory, because that will - # break other packages using the cache if that directory is - # removed, or if the value is a relative name. - INSTALL=$ac_install_sh - fi -fi -{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $INSTALL" >&5 -$as_echo "$INSTALL" >&6; } - -# Use test -z because SunOS4 sh mishandles braces in ${var-val}. -# It thinks the first close brace ends the variable substitution. -test -z "$INSTALL_PROGRAM" && INSTALL_PROGRAM='${INSTALL}' - -test -z "$INSTALL_SCRIPT" && INSTALL_SCRIPT='${INSTALL}' - -test -z "$INSTALL_DATA" && INSTALL_DATA='${INSTALL} -m 644' - - -# Checks for libraries. - -# Checks for header files. - -# Checks for typedefs, structures, and compiler characteristics. - -# Checks for library functions. - -# define eduOS specific constants - -$as_echo "#define HAVE_ARCH_MEMSET 1" >>confdefs.h - - -$as_echo "#define HAVE_ARCH_MEMCPY 1" >>confdefs.h - - -$as_echo "#define HAVE_ARCH_STRLEN 1" >>confdefs.h - - -$as_echo "#define HAVE_ARCH_STRCPY 1" >>confdefs.h - - -$as_echo "#define HAVE_ARCH_STRNCPY 1" >>confdefs.h - - -$as_echo "#define MAX_ISLE 8" >>confdefs.h - - -$as_echo "#define MAX_FNAME 128" >>confdefs.h - - -$as_echo "#define VIDEO_MEM_ADDR 0xB8000" >>confdefs.h - -#AC_DEFINE(CONFIG_VGA, 1, Use the VGA interface as output device) - -$as_echo "#define DYNAMIC_TICKS 1" >>confdefs.h - -#AC_DEFINE(SAVE_FPU, 1, Set task switched flag during a context switch); - - -# Check whether --with-mtune was given. -if test "${with_mtune+set}" = set; then : - withval=$with_mtune; if test x"$withval" != x ; then - ARCH_OPT="-mtune=$withval -march=$withval" - fi -else - ARCH_OPT= -fi - - - - -# Check whether --with-toolchain was given. -if test "${with_toolchain+set}" = set; then : - withval=$with_toolchain; TOOLCHAIN=1 -else - TOOLCHAIN=0 -fi - - - - -# Check whether --with-max-cores was given. -if test "${with_max_cores+set}" = set; then : - withval=$with_max_cores; -fi - -if test "x$with_max_cores" != x; then - -cat >>confdefs.h <<_ACEOF -#define MAX_CORES $with_max_tasks -_ACEOF - -else - -$as_echo "#define MAX_CORES 512" >>confdefs.h - -fi - - -# Check whether --with-max-tasks was given. -if test "${with_max_tasks+set}" = set; then : - withval=$with_max_tasks; -fi - -if test "x$with_max_tasks" != x; then - -cat >>confdefs.h <<_ACEOF -#define MAX_TASKS $with_max_tasks -_ACEOF - -else - -$as_echo "#define MAX_TASKS (MAX_CORES*2+2)" >>confdefs.h - -fi - - -# Check whether --with-kernel-stack-size was given. -if test "${with_kernel_stack_size+set}" = set; then : - withval=$with_kernel_stack_size; -fi - -if test "x$with_kernel_stack_size" != x; then - -cat >>confdefs.h <<_ACEOF -#define KERNEL_STACK_SIZE $with_stack_size -_ACEOF - -else - -$as_echo "#define KERNEL_STACK_SIZE 8192" >>confdefs.h - -fi - - - -# Check whether --with-default-stack-size was given. -if test "${with_default_stack_size+set}" = set; then : - withval=$with_default_stack_size; -fi - -if test "x$with_default_stack_size" != x; then - -cat >>confdefs.h <<_ACEOF -#define DEFAULT_STACK_SIZE $with_default_stack_size -_ACEOF - -else - -$as_echo "#define DEFAULT_STACK_SIZE 262144" >>confdefs.h - -fi - -ac_config_files="$ac_config_files Makefile tools/Makefile usr/ircce/Makefile usr/xray/Makefile usr/libomp/Makefile" - -cat >confcache <<\_ACEOF -# This file is a shell script that caches the results of configure -# tests run on this system so they can be shared between configure -# scripts and configure runs, see configure's option --config-cache. -# It is not useful on other systems. If it contains results you don't -# want to keep, you may remove or edit it. -# -# config.status only pays attention to the cache file if you give it -# the --recheck option to rerun configure. -# -# `ac_cv_env_foo' variables (set or unset) will be overridden when -# loading this file, other *unset* `ac_cv_foo' will be assigned the -# following values. - -_ACEOF - -# The following way of writing the cache mishandles newlines in values, -# but we know of no workaround that is simple, portable, and efficient. -# So, we kill variables containing newlines. -# Ultrix sh set writes to stderr and can't be redirected directly, -# and sets the high bit in the cache file unless we assign to the vars. -( - for ac_var in `(set) 2>&1 | sed -n 's/^\([a-zA-Z_][a-zA-Z0-9_]*\)=.*/\1/p'`; do - eval ac_val=\$$ac_var - case $ac_val in #( - *${as_nl}*) - case $ac_var in #( - *_cv_*) { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: cache variable $ac_var contains a newline" >&5 -$as_echo "$as_me: WARNING: cache variable $ac_var contains a newline" >&2;} ;; - esac - case $ac_var in #( - _ | IFS | as_nl) ;; #( - BASH_ARGV | BASH_SOURCE) eval $ac_var= ;; #( - *) { eval $ac_var=; unset $ac_var;} ;; - esac ;; - esac - done - - (set) 2>&1 | - case $as_nl`(ac_space=' '; set) 2>&1` in #( - *${as_nl}ac_space=\ *) - # `set' does not quote correctly, so add quotes: double-quote - # substitution turns \\\\ into \\, and sed turns \\ into \. - sed -n \ - "s/'/'\\\\''/g; - s/^\\([_$as_cr_alnum]*_cv_[_$as_cr_alnum]*\\)=\\(.*\\)/\\1='\\2'/p" - ;; #( - *) - # `set' quotes correctly as required by POSIX, so do not add quotes. - sed -n "/^[_$as_cr_alnum]*_cv_[_$as_cr_alnum]*=/p" - ;; - esac | - sort -) | - sed ' - /^ac_cv_env_/b end - t clear - :clear - s/^\([^=]*\)=\(.*[{}].*\)$/test "${\1+set}" = set || &/ - t end - s/^\([^=]*\)=\(.*\)$/\1=${\1=\2}/ - :end' >>confcache -if diff "$cache_file" confcache >/dev/null 2>&1; then :; else - if test -w "$cache_file"; then - if test "x$cache_file" != "x/dev/null"; then - { $as_echo "$as_me:${as_lineno-$LINENO}: updating cache $cache_file" >&5 -$as_echo "$as_me: updating cache $cache_file" >&6;} - if test ! -f "$cache_file" || test -h "$cache_file"; then - cat confcache >"$cache_file" - else - case $cache_file in #( - */* | ?:*) - mv -f confcache "$cache_file"$$ && - mv -f "$cache_file"$$ "$cache_file" ;; #( - *) - mv -f confcache "$cache_file" ;; - esac - fi - fi - else - { $as_echo "$as_me:${as_lineno-$LINENO}: not updating unwritable cache $cache_file" >&5 -$as_echo "$as_me: not updating unwritable cache $cache_file" >&6;} - fi -fi -rm -f confcache - -test "x$prefix" = xNONE && prefix=$ac_default_prefix -# Let make expand exec_prefix. -test "x$exec_prefix" = xNONE && exec_prefix='${prefix}' - -DEFS=-DHAVE_CONFIG_H - -ac_libobjs= -ac_ltlibobjs= -U= -for ac_i in : $LIBOBJS; do test "x$ac_i" = x: && continue - # 1. Remove the extension, and $U if already installed. - ac_script='s/\$U\././;s/\.o$//;s/\.obj$//' - ac_i=`$as_echo "$ac_i" | sed "$ac_script"` - # 2. Prepend LIBOBJDIR. When used with automake>=1.10 LIBOBJDIR - # will be set to the directory where LIBOBJS objects are built. - as_fn_append ac_libobjs " \${LIBOBJDIR}$ac_i\$U.$ac_objext" - as_fn_append ac_ltlibobjs " \${LIBOBJDIR}$ac_i"'$U.lo' -done -LIBOBJS=$ac_libobjs - -LTLIBOBJS=$ac_ltlibobjs - - - -: "${CONFIG_STATUS=./config.status}" -ac_write_fail=0 -ac_clean_files_save=$ac_clean_files -ac_clean_files="$ac_clean_files $CONFIG_STATUS" -{ $as_echo "$as_me:${as_lineno-$LINENO}: creating $CONFIG_STATUS" >&5 -$as_echo "$as_me: creating $CONFIG_STATUS" >&6;} -as_write_fail=0 -cat >$CONFIG_STATUS <<_ASEOF || as_write_fail=1 -#! $SHELL -# Generated by $as_me. -# Run this file to recreate the current configuration. -# Compiler output produced by configure, useful for debugging -# configure, is in config.log if it exists. - -debug=false -ac_cs_recheck=false -ac_cs_silent=false - -SHELL=\${CONFIG_SHELL-$SHELL} -export SHELL -_ASEOF -cat >>$CONFIG_STATUS <<\_ASEOF || as_write_fail=1 -## -------------------- ## -## M4sh Initialization. ## -## -------------------- ## - -# Be more Bourne compatible -DUALCASE=1; export DUALCASE # for MKS sh -if test -n "${ZSH_VERSION+set}" && (emulate sh) >/dev/null 2>&1; then : - emulate sh - NULLCMD=: - # Pre-4.2 versions of Zsh do word splitting on ${1+"$@"}, which - # is contrary to our usage. Disable this feature. - alias -g '${1+"$@"}'='"$@"' - setopt NO_GLOB_SUBST -else - case `(set -o) 2>/dev/null` in #( - *posix*) : - set -o posix ;; #( - *) : - ;; -esac -fi - - -as_nl=' -' -export as_nl -# Printing a long string crashes Solaris 7 /usr/bin/printf. -as_echo='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\' -as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo -as_echo=$as_echo$as_echo$as_echo$as_echo$as_echo$as_echo -# Prefer a ksh shell builtin over an external printf program on Solaris, -# but without wasting forks for bash or zsh. -if test -z "$BASH_VERSION$ZSH_VERSION" \ - && (test "X`print -r -- $as_echo`" = "X$as_echo") 2>/dev/null; then - as_echo='print -r --' - as_echo_n='print -rn --' -elif (test "X`printf %s $as_echo`" = "X$as_echo") 2>/dev/null; then - as_echo='printf %s\n' - as_echo_n='printf %s' -else - if test "X`(/usr/ucb/echo -n -n $as_echo) 2>/dev/null`" = "X-n $as_echo"; then - as_echo_body='eval /usr/ucb/echo -n "$1$as_nl"' - as_echo_n='/usr/ucb/echo -n' - else - as_echo_body='eval expr "X$1" : "X\\(.*\\)"' - as_echo_n_body='eval - arg=$1; - case $arg in #( - *"$as_nl"*) - expr "X$arg" : "X\\(.*\\)$as_nl"; - arg=`expr "X$arg" : ".*$as_nl\\(.*\\)"`;; - esac; - expr "X$arg" : "X\\(.*\\)" | tr -d "$as_nl" - ' - export as_echo_n_body - as_echo_n='sh -c $as_echo_n_body as_echo' - fi - export as_echo_body - as_echo='sh -c $as_echo_body as_echo' -fi - -# The user is always right. -if test "${PATH_SEPARATOR+set}" != set; then - PATH_SEPARATOR=: - (PATH='/bin;/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 && { - (PATH='/bin:/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 || - PATH_SEPARATOR=';' - } -fi - - -# IFS -# We need space, tab and new line, in precisely that order. Quoting is -# there to prevent editors from complaining about space-tab. -# (If _AS_PATH_WALK were called with IFS unset, it would disable word -# splitting by setting IFS to empty value.) -IFS=" "" $as_nl" - -# Find who we are. Look in the path if we contain no directory separator. -as_myself= -case $0 in #(( - *[\\/]* ) as_myself=$0 ;; - *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR -for as_dir in $PATH -do - IFS=$as_save_IFS - test -z "$as_dir" && as_dir=. - test -r "$as_dir/$0" && as_myself=$as_dir/$0 && break - done -IFS=$as_save_IFS - - ;; -esac -# We did not find ourselves, most probably we were run as `sh COMMAND' -# in which case we are not to be found in the path. -if test "x$as_myself" = x; then - as_myself=$0 -fi -if test ! -f "$as_myself"; then - $as_echo "$as_myself: error: cannot find myself; rerun with an absolute file name" >&2 - exit 1 -fi - -# Unset variables that we do not need and which cause bugs (e.g. in -# pre-3.0 UWIN ksh). But do not cause bugs in bash 2.01; the "|| exit 1" -# suppresses any "Segmentation fault" message there. '((' could -# trigger a bug in pdksh 5.2.14. -for as_var in BASH_ENV ENV MAIL MAILPATH -do eval test x\${$as_var+set} = xset \ - && ( (unset $as_var) || exit 1) >/dev/null 2>&1 && unset $as_var || : -done -PS1='$ ' -PS2='> ' -PS4='+ ' - -# NLS nuisances. -LC_ALL=C -export LC_ALL -LANGUAGE=C -export LANGUAGE - -# CDPATH. -(unset CDPATH) >/dev/null 2>&1 && unset CDPATH - - -# as_fn_error STATUS ERROR [LINENO LOG_FD] -# ---------------------------------------- -# Output "`basename $0`: error: ERROR" to stderr. If LINENO and LOG_FD are -# provided, also output the error to LOG_FD, referencing LINENO. Then exit the -# script with STATUS, using 1 if that was 0. -as_fn_error () -{ - as_status=$1; test $as_status -eq 0 && as_status=1 - if test "$4"; then - as_lineno=${as_lineno-"$3"} as_lineno_stack=as_lineno_stack=$as_lineno_stack - $as_echo "$as_me:${as_lineno-$LINENO}: error: $2" >&$4 - fi - $as_echo "$as_me: error: $2" >&2 - as_fn_exit $as_status -} # as_fn_error - - -# as_fn_set_status STATUS -# ----------------------- -# Set $? to STATUS, without forking. -as_fn_set_status () -{ - return $1 -} # as_fn_set_status - -# as_fn_exit STATUS -# ----------------- -# Exit the shell with STATUS, even in a "trap 0" or "set -e" context. -as_fn_exit () -{ - set +e - as_fn_set_status $1 - exit $1 -} # as_fn_exit - -# as_fn_unset VAR -# --------------- -# Portably unset VAR. -as_fn_unset () -{ - { eval $1=; unset $1;} -} -as_unset=as_fn_unset -# as_fn_append VAR VALUE -# ---------------------- -# Append the text in VALUE to the end of the definition contained in VAR. Take -# advantage of any shell optimizations that allow amortized linear growth over -# repeated appends, instead of the typical quadratic growth present in naive -# implementations. -if (eval "as_var=1; as_var+=2; test x\$as_var = x12") 2>/dev/null; then : - eval 'as_fn_append () - { - eval $1+=\$2 - }' -else - as_fn_append () - { - eval $1=\$$1\$2 - } -fi # as_fn_append - -# as_fn_arith ARG... -# ------------------ -# Perform arithmetic evaluation on the ARGs, and store the result in the -# global $as_val. Take advantage of shells that can avoid forks. The arguments -# must be portable across $(()) and expr. -if (eval "test \$(( 1 + 1 )) = 2") 2>/dev/null; then : - eval 'as_fn_arith () - { - as_val=$(( $* )) - }' -else - as_fn_arith () - { - as_val=`expr "$@" || test $? -eq 1` - } -fi # as_fn_arith - - -if expr a : '\(a\)' >/dev/null 2>&1 && - test "X`expr 00001 : '.*\(...\)'`" = X001; then - as_expr=expr -else - as_expr=false -fi - -if (basename -- /) >/dev/null 2>&1 && test "X`basename -- / 2>&1`" = "X/"; then - as_basename=basename -else - as_basename=false -fi - -if (as_dir=`dirname -- /` && test "X$as_dir" = X/) >/dev/null 2>&1; then - as_dirname=dirname -else - as_dirname=false -fi - -as_me=`$as_basename -- "$0" || -$as_expr X/"$0" : '.*/\([^/][^/]*\)/*$' \| \ - X"$0" : 'X\(//\)$' \| \ - X"$0" : 'X\(/\)' \| . 2>/dev/null || -$as_echo X/"$0" | - sed '/^.*\/\([^/][^/]*\)\/*$/{ - s//\1/ - q - } - /^X\/\(\/\/\)$/{ - s//\1/ - q - } - /^X\/\(\/\).*/{ - s//\1/ - q - } - s/.*/./; q'` - -# Avoid depending upon Character Ranges. -as_cr_letters='abcdefghijklmnopqrstuvwxyz' -as_cr_LETTERS='ABCDEFGHIJKLMNOPQRSTUVWXYZ' -as_cr_Letters=$as_cr_letters$as_cr_LETTERS -as_cr_digits='0123456789' -as_cr_alnum=$as_cr_Letters$as_cr_digits - -ECHO_C= ECHO_N= ECHO_T= -case `echo -n x` in #((((( --n*) - case `echo 'xy\c'` in - *c*) ECHO_T=' ';; # ECHO_T is single tab character. - xy) ECHO_C='\c';; - *) echo `echo ksh88 bug on AIX 6.1` > /dev/null - ECHO_T=' ';; - esac;; -*) - ECHO_N='-n';; -esac - -rm -f conf$$ conf$$.exe conf$$.file -if test -d conf$$.dir; then - rm -f conf$$.dir/conf$$.file -else - rm -f conf$$.dir - mkdir conf$$.dir 2>/dev/null -fi -if (echo >conf$$.file) 2>/dev/null; then - if ln -s conf$$.file conf$$ 2>/dev/null; then - as_ln_s='ln -s' - # ... but there are two gotchas: - # 1) On MSYS, both `ln -s file dir' and `ln file dir' fail. - # 2) DJGPP < 2.04 has no symlinks; `ln -s' creates a wrapper executable. - # In both cases, we have to default to `cp -pR'. - ln -s conf$$.file conf$$.dir 2>/dev/null && test ! -f conf$$.exe || - as_ln_s='cp -pR' - elif ln conf$$.file conf$$ 2>/dev/null; then - as_ln_s=ln - else - as_ln_s='cp -pR' - fi -else - as_ln_s='cp -pR' -fi -rm -f conf$$ conf$$.exe conf$$.dir/conf$$.file conf$$.file -rmdir conf$$.dir 2>/dev/null - - -# as_fn_mkdir_p -# ------------- -# Create "$as_dir" as a directory, including parents if necessary. -as_fn_mkdir_p () -{ - - case $as_dir in #( - -*) as_dir=./$as_dir;; - esac - test -d "$as_dir" || eval $as_mkdir_p || { - as_dirs= - while :; do - case $as_dir in #( - *\'*) as_qdir=`$as_echo "$as_dir" | sed "s/'/'\\\\\\\\''/g"`;; #'( - *) as_qdir=$as_dir;; - esac - as_dirs="'$as_qdir' $as_dirs" - as_dir=`$as_dirname -- "$as_dir" || -$as_expr X"$as_dir" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ - X"$as_dir" : 'X\(//\)[^/]' \| \ - X"$as_dir" : 'X\(//\)$' \| \ - X"$as_dir" : 'X\(/\)' \| . 2>/dev/null || -$as_echo X"$as_dir" | - sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ - s//\1/ - q - } - /^X\(\/\/\)[^/].*/{ - s//\1/ - q - } - /^X\(\/\/\)$/{ - s//\1/ - q - } - /^X\(\/\).*/{ - s//\1/ - q - } - s/.*/./; q'` - test -d "$as_dir" && break - done - test -z "$as_dirs" || eval "mkdir $as_dirs" - } || test -d "$as_dir" || as_fn_error $? "cannot create directory $as_dir" - - -} # as_fn_mkdir_p -if mkdir -p . 2>/dev/null; then - as_mkdir_p='mkdir -p "$as_dir"' -else - test -d ./-p && rmdir ./-p - as_mkdir_p=false -fi - - -# as_fn_executable_p FILE -# ----------------------- -# Test if FILE is an executable regular file. -as_fn_executable_p () -{ - test -f "$1" && test -x "$1" -} # as_fn_executable_p -as_test_x='test -x' -as_executable_p=as_fn_executable_p - -# Sed expression to map a string onto a valid CPP name. -as_tr_cpp="eval sed 'y%*$as_cr_letters%P$as_cr_LETTERS%;s%[^_$as_cr_alnum]%_%g'" - -# Sed expression to map a string onto a valid variable name. -as_tr_sh="eval sed 'y%*+%pp%;s%[^_$as_cr_alnum]%_%g'" - - -exec 6>&1 -## ----------------------------------- ## -## Main body of $CONFIG_STATUS script. ## -## ----------------------------------- ## -_ASEOF -test $as_write_fail = 0 && chmod +x $CONFIG_STATUS || ac_write_fail=1 - -cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 -# Save the log message, to keep $0 and so on meaningful, and to -# report actual input values of CONFIG_FILES etc. instead of their -# values after options handling. -ac_log=" -This file was extended by HermitCore $as_me 0.1, which was -generated by GNU Autoconf 2.69. Invocation command line was - - CONFIG_FILES = $CONFIG_FILES - CONFIG_HEADERS = $CONFIG_HEADERS - CONFIG_LINKS = $CONFIG_LINKS - CONFIG_COMMANDS = $CONFIG_COMMANDS - $ $0 $@ - -on `(hostname || uname -n) 2>/dev/null | sed 1q` -" - -_ACEOF - -case $ac_config_files in *" -"*) set x $ac_config_files; shift; ac_config_files=$*;; -esac - -case $ac_config_headers in *" -"*) set x $ac_config_headers; shift; ac_config_headers=$*;; -esac - - -cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 -# Files that config.status was made for. -config_files="$ac_config_files" -config_headers="$ac_config_headers" - -_ACEOF - -cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 -ac_cs_usage="\ -\`$as_me' instantiates files and other configuration actions -from templates according to the current configuration. Unless the files -and actions are specified as TAGs, all are instantiated by default. - -Usage: $0 [OPTION]... [TAG]... - - -h, --help print this help, then exit - -V, --version print version number and configuration settings, then exit - --config print configuration, then exit - -q, --quiet, --silent - do not print progress messages - -d, --debug don't remove temporary files - --recheck update $as_me by reconfiguring in the same conditions - --file=FILE[:TEMPLATE] - instantiate the configuration file FILE - --header=FILE[:TEMPLATE] - instantiate the configuration header FILE - -Configuration files: -$config_files - -Configuration headers: -$config_headers - -Report bugs to . -HermitCore home page: ." - -_ACEOF -cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 -ac_cs_config="`$as_echo "$ac_configure_args" | sed 's/^ //; s/[\\""\`\$]/\\\\&/g'`" -ac_cs_version="\\ -HermitCore config.status 0.1 -configured by $0, generated by GNU Autoconf 2.69, - with options \\"\$ac_cs_config\\" - -Copyright (C) 2012 Free Software Foundation, Inc. -This config.status script is free software; the Free Software Foundation -gives unlimited permission to copy, distribute and modify it." - -ac_pwd='$ac_pwd' -srcdir='$srcdir' -INSTALL='$INSTALL' -test -n "\$AWK" || AWK=awk -_ACEOF - -cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 -# The default lists apply if the user does not specify any file. -ac_need_defaults=: -while test $# != 0 -do - case $1 in - --*=?*) - ac_option=`expr "X$1" : 'X\([^=]*\)='` - ac_optarg=`expr "X$1" : 'X[^=]*=\(.*\)'` - ac_shift=: - ;; - --*=) - ac_option=`expr "X$1" : 'X\([^=]*\)='` - ac_optarg= - ac_shift=: - ;; - *) - ac_option=$1 - ac_optarg=$2 - ac_shift=shift - ;; - esac - - case $ac_option in - # Handling of the options. - -recheck | --recheck | --rechec | --reche | --rech | --rec | --re | --r) - ac_cs_recheck=: ;; - --version | --versio | --versi | --vers | --ver | --ve | --v | -V ) - $as_echo "$ac_cs_version"; exit ;; - --config | --confi | --conf | --con | --co | --c ) - $as_echo "$ac_cs_config"; exit ;; - --debug | --debu | --deb | --de | --d | -d ) - debug=: ;; - --file | --fil | --fi | --f ) - $ac_shift - case $ac_optarg in - *\'*) ac_optarg=`$as_echo "$ac_optarg" | sed "s/'/'\\\\\\\\''/g"` ;; - '') as_fn_error $? "missing file argument" ;; - esac - as_fn_append CONFIG_FILES " '$ac_optarg'" - ac_need_defaults=false;; - --header | --heade | --head | --hea ) - $ac_shift - case $ac_optarg in - *\'*) ac_optarg=`$as_echo "$ac_optarg" | sed "s/'/'\\\\\\\\''/g"` ;; - esac - as_fn_append CONFIG_HEADERS " '$ac_optarg'" - ac_need_defaults=false;; - --he | --h) - # Conflict between --help and --header - as_fn_error $? "ambiguous option: \`$1' -Try \`$0 --help' for more information.";; - --help | --hel | -h ) - $as_echo "$ac_cs_usage"; exit ;; - -q | -quiet | --quiet | --quie | --qui | --qu | --q \ - | -silent | --silent | --silen | --sile | --sil | --si | --s) - ac_cs_silent=: ;; - - # This is an error. - -*) as_fn_error $? "unrecognized option: \`$1' -Try \`$0 --help' for more information." ;; - - *) as_fn_append ac_config_targets " $1" - ac_need_defaults=false ;; - - esac - shift -done - -ac_configure_extra_args= - -if $ac_cs_silent; then - exec 6>/dev/null - ac_configure_extra_args="$ac_configure_extra_args --silent" -fi - -_ACEOF -cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 -if \$ac_cs_recheck; then - set X $SHELL '$0' $ac_configure_args \$ac_configure_extra_args --no-create --no-recursion - shift - \$as_echo "running CONFIG_SHELL=$SHELL \$*" >&6 - CONFIG_SHELL='$SHELL' - export CONFIG_SHELL - exec "\$@" -fi - -_ACEOF -cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 -exec 5>>config.log -{ - echo - sed 'h;s/./-/g;s/^.../## /;s/...$/ ##/;p;x;p;x' <<_ASBOX -## Running $as_me. ## -_ASBOX - $as_echo "$ac_log" -} >&5 - -_ACEOF -cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 -_ACEOF - -cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 - -# Handling of arguments. -for ac_config_target in $ac_config_targets -do - case $ac_config_target in - "include/hermit/config.h") CONFIG_HEADERS="$CONFIG_HEADERS include/hermit/config.h" ;; - "Makefile") CONFIG_FILES="$CONFIG_FILES Makefile" ;; - "tools/Makefile") CONFIG_FILES="$CONFIG_FILES tools/Makefile" ;; - "usr/ircce/Makefile") CONFIG_FILES="$CONFIG_FILES usr/ircce/Makefile" ;; - "usr/xray/Makefile") CONFIG_FILES="$CONFIG_FILES usr/xray/Makefile" ;; - "usr/libomp/Makefile") CONFIG_FILES="$CONFIG_FILES usr/libomp/Makefile" ;; - - *) as_fn_error $? "invalid argument: \`$ac_config_target'" "$LINENO" 5;; - esac -done - - -# If the user did not use the arguments to specify the items to instantiate, -# then the envvar interface is used. Set only those that are not. -# We use the long form for the default assignment because of an extremely -# bizarre bug on SunOS 4.1.3. -if $ac_need_defaults; then - test "${CONFIG_FILES+set}" = set || CONFIG_FILES=$config_files - test "${CONFIG_HEADERS+set}" = set || CONFIG_HEADERS=$config_headers -fi - -# Have a temporary directory for convenience. Make it in the build tree -# simply because there is no reason against having it here, and in addition, -# creating and moving files from /tmp can sometimes cause problems. -# Hook for its removal unless debugging. -# Note that there is a small window in which the directory will not be cleaned: -# after its creation but before its name has been assigned to `$tmp'. -$debug || -{ - tmp= ac_tmp= - trap 'exit_status=$? - : "${ac_tmp:=$tmp}" - { test ! -d "$ac_tmp" || rm -fr "$ac_tmp"; } && exit $exit_status -' 0 - trap 'as_fn_exit 1' 1 2 13 15 -} -# Create a (secure) tmp directory for tmp files. - -{ - tmp=`(umask 077 && mktemp -d "./confXXXXXX") 2>/dev/null` && - test -d "$tmp" -} || -{ - tmp=./conf$$-$RANDOM - (umask 077 && mkdir "$tmp") -} || as_fn_error $? "cannot create a temporary directory in ." "$LINENO" 5 -ac_tmp=$tmp - -# Set up the scripts for CONFIG_FILES section. -# No need to generate them if there are no CONFIG_FILES. -# This happens for instance with `./config.status config.h'. -if test -n "$CONFIG_FILES"; then - - -ac_cr=`echo X | tr X '\015'` -# On cygwin, bash can eat \r inside `` if the user requested igncr. -# But we know of no other shell where ac_cr would be empty at this -# point, so we can use a bashism as a fallback. -if test "x$ac_cr" = x; then - eval ac_cr=\$\'\\r\' -fi -ac_cs_awk_cr=`$AWK 'BEGIN { print "a\rb" }' /dev/null` -if test "$ac_cs_awk_cr" = "a${ac_cr}b"; then - ac_cs_awk_cr='\\r' -else - ac_cs_awk_cr=$ac_cr -fi - -echo 'BEGIN {' >"$ac_tmp/subs1.awk" && -_ACEOF - - -{ - echo "cat >conf$$subs.awk <<_ACEOF" && - echo "$ac_subst_vars" | sed 's/.*/&!$&$ac_delim/' && - echo "_ACEOF" -} >conf$$subs.sh || - as_fn_error $? "could not make $CONFIG_STATUS" "$LINENO" 5 -ac_delim_num=`echo "$ac_subst_vars" | grep -c '^'` -ac_delim='%!_!# ' -for ac_last_try in false false false false false :; do - . ./conf$$subs.sh || - as_fn_error $? "could not make $CONFIG_STATUS" "$LINENO" 5 - - ac_delim_n=`sed -n "s/.*$ac_delim\$/X/p" conf$$subs.awk | grep -c X` - if test $ac_delim_n = $ac_delim_num; then - break - elif $ac_last_try; then - as_fn_error $? "could not make $CONFIG_STATUS" "$LINENO" 5 - else - ac_delim="$ac_delim!$ac_delim _$ac_delim!! " - fi -done -rm -f conf$$subs.sh - -cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 -cat >>"\$ac_tmp/subs1.awk" <<\\_ACAWK && -_ACEOF -sed -n ' -h -s/^/S["/; s/!.*/"]=/ -p -g -s/^[^!]*!// -:repl -t repl -s/'"$ac_delim"'$// -t delim -:nl -h -s/\(.\{148\}\)..*/\1/ -t more1 -s/["\\]/\\&/g; s/^/"/; s/$/\\n"\\/ -p -n -b repl -:more1 -s/["\\]/\\&/g; s/^/"/; s/$/"\\/ -p -g -s/.\{148\}// -t nl -:delim -h -s/\(.\{148\}\)..*/\1/ -t more2 -s/["\\]/\\&/g; s/^/"/; s/$/"/ -p -b -:more2 -s/["\\]/\\&/g; s/^/"/; s/$/"\\/ -p -g -s/.\{148\}// -t delim -' >$CONFIG_STATUS || ac_write_fail=1 -rm -f conf$$subs.awk -cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 -_ACAWK -cat >>"\$ac_tmp/subs1.awk" <<_ACAWK && - for (key in S) S_is_set[key] = 1 - FS = "" - -} -{ - line = $ 0 - nfields = split(line, field, "@") - substed = 0 - len = length(field[1]) - for (i = 2; i < nfields; i++) { - key = field[i] - keylen = length(key) - if (S_is_set[key]) { - value = S[key] - line = substr(line, 1, len) "" value "" substr(line, len + keylen + 3) - len += length(value) + length(field[++i]) - substed = 1 - } else - len += 1 + keylen - } - - print line -} - -_ACAWK -_ACEOF -cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 -if sed "s/$ac_cr//" < /dev/null > /dev/null 2>&1; then - sed "s/$ac_cr\$//; s/$ac_cr/$ac_cs_awk_cr/g" -else - cat -fi < "$ac_tmp/subs1.awk" > "$ac_tmp/subs.awk" \ - || as_fn_error $? "could not setup config files machinery" "$LINENO" 5 -_ACEOF - -# VPATH may cause trouble with some makes, so we remove sole $(srcdir), -# ${srcdir} and @srcdir@ entries from VPATH if srcdir is ".", strip leading and -# trailing colons and then remove the whole line if VPATH becomes empty -# (actually we leave an empty line to preserve line numbers). -if test "x$srcdir" = x.; then - ac_vpsub='/^[ ]*VPATH[ ]*=[ ]*/{ -h -s/// -s/^/:/ -s/[ ]*$/:/ -s/:\$(srcdir):/:/g -s/:\${srcdir}:/:/g -s/:@srcdir@:/:/g -s/^:*// -s/:*$// -x -s/\(=[ ]*\).*/\1/ -G -s/\n// -s/^[^=]*=[ ]*$// -}' -fi - -cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 -fi # test -n "$CONFIG_FILES" - -# Set up the scripts for CONFIG_HEADERS section. -# No need to generate them if there are no CONFIG_HEADERS. -# This happens for instance with `./config.status Makefile'. -if test -n "$CONFIG_HEADERS"; then -cat >"$ac_tmp/defines.awk" <<\_ACAWK || -BEGIN { -_ACEOF - -# Transform confdefs.h into an awk script `defines.awk', embedded as -# here-document in config.status, that substitutes the proper values into -# config.h.in to produce config.h. - -# Create a delimiter string that does not exist in confdefs.h, to ease -# handling of long lines. -ac_delim='%!_!# ' -for ac_last_try in false false :; do - ac_tt=`sed -n "/$ac_delim/p" confdefs.h` - if test -z "$ac_tt"; then - break - elif $ac_last_try; then - as_fn_error $? "could not make $CONFIG_HEADERS" "$LINENO" 5 - else - ac_delim="$ac_delim!$ac_delim _$ac_delim!! " - fi -done - -# For the awk script, D is an array of macro values keyed by name, -# likewise P contains macro parameters if any. Preserve backslash -# newline sequences. - -ac_word_re=[_$as_cr_Letters][_$as_cr_alnum]* -sed -n ' -s/.\{148\}/&'"$ac_delim"'/g -t rset -:rset -s/^[ ]*#[ ]*define[ ][ ]*/ / -t def -d -:def -s/\\$// -t bsnl -s/["\\]/\\&/g -s/^ \('"$ac_word_re"'\)\(([^()]*)\)[ ]*\(.*\)/P["\1"]="\2"\ -D["\1"]=" \3"/p -s/^ \('"$ac_word_re"'\)[ ]*\(.*\)/D["\1"]=" \2"/p -d -:bsnl -s/["\\]/\\&/g -s/^ \('"$ac_word_re"'\)\(([^()]*)\)[ ]*\(.*\)/P["\1"]="\2"\ -D["\1"]=" \3\\\\\\n"\\/p -t cont -s/^ \('"$ac_word_re"'\)[ ]*\(.*\)/D["\1"]=" \2\\\\\\n"\\/p -t cont -d -:cont -n -s/.\{148\}/&'"$ac_delim"'/g -t clear -:clear -s/\\$// -t bsnlc -s/["\\]/\\&/g; s/^/"/; s/$/"/p -d -:bsnlc -s/["\\]/\\&/g; s/^/"/; s/$/\\\\\\n"\\/p -b cont -' >$CONFIG_STATUS || ac_write_fail=1 - -cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 - for (key in D) D_is_set[key] = 1 - FS = "" -} -/^[\t ]*#[\t ]*(define|undef)[\t ]+$ac_word_re([\t (]|\$)/ { - line = \$ 0 - split(line, arg, " ") - if (arg[1] == "#") { - defundef = arg[2] - mac1 = arg[3] - } else { - defundef = substr(arg[1], 2) - mac1 = arg[2] - } - split(mac1, mac2, "(") #) - macro = mac2[1] - prefix = substr(line, 1, index(line, defundef) - 1) - if (D_is_set[macro]) { - # Preserve the white space surrounding the "#". - print prefix "define", macro P[macro] D[macro] - next - } else { - # Replace #undef with comments. This is necessary, for example, - # in the case of _POSIX_SOURCE, which is predefined and required - # on some systems where configure will not decide to define it. - if (defundef == "undef") { - print "/*", prefix defundef, macro, "*/" - next - } - } -} -{ print } -_ACAWK -_ACEOF -cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 - as_fn_error $? "could not setup config headers machinery" "$LINENO" 5 -fi # test -n "$CONFIG_HEADERS" - - -eval set X " :F $CONFIG_FILES :H $CONFIG_HEADERS " -shift -for ac_tag -do - case $ac_tag in - :[FHLC]) ac_mode=$ac_tag; continue;; - esac - case $ac_mode$ac_tag in - :[FHL]*:*);; - :L* | :C*:*) as_fn_error $? "invalid tag \`$ac_tag'" "$LINENO" 5;; - :[FH]-) ac_tag=-:-;; - :[FH]*) ac_tag=$ac_tag:$ac_tag.in;; - esac - ac_save_IFS=$IFS - IFS=: - set x $ac_tag - IFS=$ac_save_IFS - shift - ac_file=$1 - shift - - case $ac_mode in - :L) ac_source=$1;; - :[FH]) - ac_file_inputs= - for ac_f - do - case $ac_f in - -) ac_f="$ac_tmp/stdin";; - *) # Look for the file first in the build tree, then in the source tree - # (if the path is not absolute). The absolute path cannot be DOS-style, - # because $ac_f cannot contain `:'. - test -f "$ac_f" || - case $ac_f in - [\\/$]*) false;; - *) test -f "$srcdir/$ac_f" && ac_f="$srcdir/$ac_f";; - esac || - as_fn_error 1 "cannot find input file: \`$ac_f'" "$LINENO" 5;; - esac - case $ac_f in *\'*) ac_f=`$as_echo "$ac_f" | sed "s/'/'\\\\\\\\''/g"`;; esac - as_fn_append ac_file_inputs " '$ac_f'" - done - - # Let's still pretend it is `configure' which instantiates (i.e., don't - # use $as_me), people would be surprised to read: - # /* config.h. Generated by config.status. */ - configure_input='Generated from '` - $as_echo "$*" | sed 's|^[^:]*/||;s|:[^:]*/|, |g' - `' by configure.' - if test x"$ac_file" != x-; then - configure_input="$ac_file. $configure_input" - { $as_echo "$as_me:${as_lineno-$LINENO}: creating $ac_file" >&5 -$as_echo "$as_me: creating $ac_file" >&6;} - fi - # Neutralize special characters interpreted by sed in replacement strings. - case $configure_input in #( - *\&* | *\|* | *\\* ) - ac_sed_conf_input=`$as_echo "$configure_input" | - sed 's/[\\\\&|]/\\\\&/g'`;; #( - *) ac_sed_conf_input=$configure_input;; - esac - - case $ac_tag in - *:-:* | *:-) cat >"$ac_tmp/stdin" \ - || as_fn_error $? "could not create $ac_file" "$LINENO" 5 ;; - esac - ;; - esac - - ac_dir=`$as_dirname -- "$ac_file" || -$as_expr X"$ac_file" : 'X\(.*[^/]\)//*[^/][^/]*/*$' \| \ - X"$ac_file" : 'X\(//\)[^/]' \| \ - X"$ac_file" : 'X\(//\)$' \| \ - X"$ac_file" : 'X\(/\)' \| . 2>/dev/null || -$as_echo X"$ac_file" | - sed '/^X\(.*[^/]\)\/\/*[^/][^/]*\/*$/{ - s//\1/ - q - } - /^X\(\/\/\)[^/].*/{ - s//\1/ - q - } - /^X\(\/\/\)$/{ - s//\1/ - q - } - /^X\(\/\).*/{ - s//\1/ - q - } - s/.*/./; q'` - as_dir="$ac_dir"; as_fn_mkdir_p - ac_builddir=. - -case "$ac_dir" in -.) ac_dir_suffix= ac_top_builddir_sub=. ac_top_build_prefix= ;; -*) - ac_dir_suffix=/`$as_echo "$ac_dir" | sed 's|^\.[\\/]||'` - # A ".." for each directory in $ac_dir_suffix. - ac_top_builddir_sub=`$as_echo "$ac_dir_suffix" | sed 's|/[^\\/]*|/..|g;s|/||'` - case $ac_top_builddir_sub in - "") ac_top_builddir_sub=. ac_top_build_prefix= ;; - *) ac_top_build_prefix=$ac_top_builddir_sub/ ;; - esac ;; -esac -ac_abs_top_builddir=$ac_pwd -ac_abs_builddir=$ac_pwd$ac_dir_suffix -# for backward compatibility: -ac_top_builddir=$ac_top_build_prefix - -case $srcdir in - .) # We are building in place. - ac_srcdir=. - ac_top_srcdir=$ac_top_builddir_sub - ac_abs_top_srcdir=$ac_pwd ;; - [\\/]* | ?:[\\/]* ) # Absolute name. - ac_srcdir=$srcdir$ac_dir_suffix; - ac_top_srcdir=$srcdir - ac_abs_top_srcdir=$srcdir ;; - *) # Relative name. - ac_srcdir=$ac_top_build_prefix$srcdir$ac_dir_suffix - ac_top_srcdir=$ac_top_build_prefix$srcdir - ac_abs_top_srcdir=$ac_pwd/$srcdir ;; -esac -ac_abs_srcdir=$ac_abs_top_srcdir$ac_dir_suffix - - - case $ac_mode in - :F) - # - # CONFIG_FILE - # - - case $INSTALL in - [\\/$]* | ?:[\\/]* ) ac_INSTALL=$INSTALL ;; - *) ac_INSTALL=$ac_top_build_prefix$INSTALL ;; - esac -_ACEOF - -cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 -# If the template does not know about datarootdir, expand it. -# FIXME: This hack should be removed a few years after 2.60. -ac_datarootdir_hack=; ac_datarootdir_seen= -ac_sed_dataroot=' -/datarootdir/ { - p - q -} -/@datadir@/p -/@docdir@/p -/@infodir@/p -/@localedir@/p -/@mandir@/p' -case `eval "sed -n \"\$ac_sed_dataroot\" $ac_file_inputs"` in -*datarootdir*) ac_datarootdir_seen=yes;; -*@datadir@*|*@docdir@*|*@infodir@*|*@localedir@*|*@mandir@*) - { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $ac_file_inputs seems to ignore the --datarootdir setting" >&5 -$as_echo "$as_me: WARNING: $ac_file_inputs seems to ignore the --datarootdir setting" >&2;} -_ACEOF -cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 - ac_datarootdir_hack=' - s&@datadir@&$datadir&g - s&@docdir@&$docdir&g - s&@infodir@&$infodir&g - s&@localedir@&$localedir&g - s&@mandir@&$mandir&g - s&\\\${datarootdir}&$datarootdir&g' ;; -esac -_ACEOF - -# Neutralize VPATH when `$srcdir' = `.'. -# Shell code in configure.ac might set extrasub. -# FIXME: do we really want to maintain this feature? -cat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1 -ac_sed_extra="$ac_vpsub -$extrasub -_ACEOF -cat >>$CONFIG_STATUS <<\_ACEOF || ac_write_fail=1 -:t -/@[a-zA-Z_][a-zA-Z_0-9]*@/!b -s|@configure_input@|$ac_sed_conf_input|;t t -s&@top_builddir@&$ac_top_builddir_sub&;t t -s&@top_build_prefix@&$ac_top_build_prefix&;t t -s&@srcdir@&$ac_srcdir&;t t -s&@abs_srcdir@&$ac_abs_srcdir&;t t -s&@top_srcdir@&$ac_top_srcdir&;t t -s&@abs_top_srcdir@&$ac_abs_top_srcdir&;t t -s&@builddir@&$ac_builddir&;t t -s&@abs_builddir@&$ac_abs_builddir&;t t -s&@abs_top_builddir@&$ac_abs_top_builddir&;t t -s&@INSTALL@&$ac_INSTALL&;t t -$ac_datarootdir_hack -" -eval sed \"\$ac_sed_extra\" "$ac_file_inputs" | $AWK -f "$ac_tmp/subs.awk" \ - >$ac_tmp/out || as_fn_error $? "could not create $ac_file" "$LINENO" 5 - -test -z "$ac_datarootdir_hack$ac_datarootdir_seen" && - { ac_out=`sed -n '/\${datarootdir}/p' "$ac_tmp/out"`; test -n "$ac_out"; } && - { ac_out=`sed -n '/^[ ]*datarootdir[ ]*:*=/p' \ - "$ac_tmp/out"`; test -z "$ac_out"; } && - { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $ac_file contains a reference to the variable \`datarootdir' -which seems to be undefined. Please make sure it is defined" >&5 -$as_echo "$as_me: WARNING: $ac_file contains a reference to the variable \`datarootdir' -which seems to be undefined. Please make sure it is defined" >&2;} - - rm -f "$ac_tmp/stdin" - case $ac_file in - -) cat "$ac_tmp/out" && rm -f "$ac_tmp/out";; - *) rm -f "$ac_file" && mv "$ac_tmp/out" "$ac_file";; - esac \ - || as_fn_error $? "could not create $ac_file" "$LINENO" 5 - ;; - :H) - # - # CONFIG_HEADER - # - if test x"$ac_file" != x-; then - { - $as_echo "/* $configure_input */" \ - && eval '$AWK -f "$ac_tmp/defines.awk"' "$ac_file_inputs" - } >"$ac_tmp/config.h" \ - || as_fn_error $? "could not create $ac_file" "$LINENO" 5 - if diff "$ac_file" "$ac_tmp/config.h" >/dev/null 2>&1; then - { $as_echo "$as_me:${as_lineno-$LINENO}: $ac_file is unchanged" >&5 -$as_echo "$as_me: $ac_file is unchanged" >&6;} - else - rm -f "$ac_file" - mv "$ac_tmp/config.h" "$ac_file" \ - || as_fn_error $? "could not create $ac_file" "$LINENO" 5 - fi - else - $as_echo "/* $configure_input */" \ - && eval '$AWK -f "$ac_tmp/defines.awk"' "$ac_file_inputs" \ - || as_fn_error $? "could not create -" "$LINENO" 5 - fi - ;; - - - esac - -done # for ac_tag - - -as_fn_exit 0 -_ACEOF -ac_clean_files=$ac_clean_files_save - -test $ac_write_fail = 0 || - as_fn_error $? "write failure creating $CONFIG_STATUS" "$LINENO" 5 - - -# configure is writing to config.log, and then calls config.status. -# config.status does its own redirection, appending to config.log. -# Unfortunately, on DOS this fails, as config.log is still kept open -# by configure, so config.status won't be able to write to it; its -# output is simply discarded. So we exec the FD to /dev/null, -# effectively closing config.log, so it can be properly (re)opened and -# appended to by config.status. When coming back to configure, we -# need to make the FD available again. -if test "$no_create" != yes; then - ac_cs_success=: - ac_config_status_args= - test "$silent" = yes && - ac_config_status_args="$ac_config_status_args --quiet" - exec 5>/dev/null - $SHELL $CONFIG_STATUS $ac_config_status_args || ac_cs_success=false - exec 5>>config.log - # Use ||, not &&, to avoid exiting from the if with $? = 1, which - # would make configure fail if this is the last instruction. - $ac_cs_success || as_fn_exit 1 -fi -if test -n "$ac_unrecognized_opts" && test "$enable_option_checking" != no; then - { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: unrecognized options: $ac_unrecognized_opts" >&5 -$as_echo "$as_me: WARNING: unrecognized options: $ac_unrecognized_opts" >&2;} -fi - diff --git a/configure.ac b/configure.ac deleted file mode 100644 index 0034a434e..000000000 --- a/configure.ac +++ /dev/null @@ -1,77 +0,0 @@ -# -*- Autoconf -*- -# Process this file with autoconf to produce a configure script. - -AC_PREREQ(2.69) -AC_INIT(HermitCore, 0.1, slankes@eonerc.rwth-aachen.de, HermitCore, http://www.hermitcore.org) -AC_CHECK_PROGS(QEMU, qemu-system-x86_64) -AC_CONFIG_SRCDIR(kernel/main.c) -AC_CONFIG_HEADERS(include/hermit/config.h) - -# Checks for programs. -AC_PROG_CC -AC_PROG_INSTALL - -# Checks for libraries. - -# Checks for header files. - -# Checks for typedefs, structures, and compiler characteristics. - -# Checks for library functions. - -# define eduOS specific constants -AC_DEFINE(HAVE_ARCH_MEMSET, 1, Define to use machine specific version of memset) -AC_DEFINE(HAVE_ARCH_MEMCPY, 1, Define to use machine specific version of memcpy) -AC_DEFINE(HAVE_ARCH_STRLEN, 1, Define to use machine specific version of strlen) -AC_DEFINE(HAVE_ARCH_STRCPY, 1, Define to use machine specific version of strcpy) -AC_DEFINE(HAVE_ARCH_STRNCPY, 1, Define to use machine specific version of strncpy) -AC_DEFINE(MAX_ISLE, 8, Define the maximum number of isles / numa nodes) -AC_DEFINE(MAX_FNAME, 128, Define the maximum length of a file name) -AC_DEFINE(VIDEO_MEM_ADDR, 0xB8000, Definition of the VGA address) -#AC_DEFINE(CONFIG_VGA, 1, Use the VGA interface as output device) -AC_DEFINE(DYNAMIC_TICKS, 1, Use a dynamic tick instead of a static) -#AC_DEFINE(SAVE_FPU, 1, Set task switched flag during a context switch); - -AC_ARG_WITH([mtune], - [AS_HELP_STRING([--with-mtune=ARCH], - [enable tuning for a specific architecture])], - [if test x"$withval" != x ; then - ARCH_OPT="-mtune=$withval -march=$withval" - fi], - [ARCH_OPT=]) -AC_SUBST(ARCH_OPT) - -AC_ARG_WITH([toolchain], [AS_HELP_STRING([--with-toolchain], [build also the whole HermitCore toolchain])], [TOOLCHAIN=1], [TOOLCHAIN=0]) -AC_SUBST(TOOLCHAIN) - -AC_ARG_WITH(max-cores, [AS_HELP_STRING([--with-max-cores=N], [specify the maximum number of cores])]) -if test "x$with_max_cores" != x; then -AC_DEFINE_UNQUOTED(MAX_CORES, $with_max_tasks, Define the maximum number of cores) -else -AC_DEFINE(MAX_CORES, 512, Define the maximum number of cores) -fi - -AC_ARG_WITH(max-tasks, [AS_HELP_STRING([--with-max-tasks=N], [specify the maximum number of running tasks])]) -if test "x$with_max_tasks" != x; then -AC_DEFINE_UNQUOTED(MAX_TASKS, $with_max_tasks, Define the maximum number of running tasks) -else -AC_DEFINE(MAX_TASKS, (MAX_CORES*2+2), Define the maximum number of running tasks) -fi - -AC_ARG_WITH(kernel-stack-size, [AS_HELP_STRING([--with-kernel-stack-size=SIZE], [specify the size of the kernel stack])]) -if test "x$with_kernel_stack_size" != x; then -AC_DEFINE_UNQUOTED(KERNEL_STACK_SIZE, $with_stack_size, Define the size of the kernel stack) -else -AC_DEFINE(KERNEL_STACK_SIZE, 8192, Define the size of the kernel stack) -fi - - -AC_ARG_WITH(default-stack-size, [AS_HELP_STRING([--with-default-stack-size=SIZE], [specify the default stack size])]) -if test "x$with_default_stack_size" != x; then -AC_DEFINE_UNQUOTED(DEFAULT_STACK_SIZE, $with_default_stack_size, Define the default stack size) -else -AC_DEFINE(DEFAULT_STACK_SIZE, 262144, Define the default stack size) -fi - -AC_CONFIG_FILES(Makefile tools/Makefile usr/ircce/Makefile usr/xray/Makefile usr/libomp/Makefile) -AC_OUTPUT diff --git a/debian/README.Debian b/debian/README.Debian deleted file mode 100644 index 93b6f3f4f..000000000 --- a/debian/README.Debian +++ /dev/null @@ -1,6 +0,0 @@ -libhermit for Debian -------------------- - - - - -- Stefan Lankes Sun, 08 Jan 2017 19:14:48 +0100 diff --git a/debian/README.source b/debian/README.source deleted file mode 100644 index 16fea0edf..000000000 --- a/debian/README.source +++ /dev/null @@ -1,10 +0,0 @@ -libhermit for Debian -------------------- - - - - - - -- Stefan Lankes Sun, 08 Jan 2017 19:14:48 +0100 - diff --git a/debian/changelog b/debian/changelog deleted file mode 100644 index ea118c685..000000000 --- a/debian/changelog +++ /dev/null @@ -1,5 +0,0 @@ -libhermit (0.1-1) unstable; urgency=medium - - * Initial release (Closes: #nnnn) - - -- Stefan Lankes Sun, 08 Jan 2017 19:14:48 +0100 diff --git a/debian/compat b/debian/compat deleted file mode 100644 index ec635144f..000000000 --- a/debian/compat +++ /dev/null @@ -1 +0,0 @@ -9 diff --git a/debian/control b/debian/control deleted file mode 100644 index d53090e2a..000000000 --- a/debian/control +++ /dev/null @@ -1,15 +0,0 @@ -Source: libhermit -Section: devel -Priority: optional -Maintainer: Stefan Lankes -Build-Depends: debhelper (>=9),autotools-dev -Standards-Version: 3.9.6 -Homepage: http://www.hermitcore.org -#Vcs-Git: git://anonscm.debian.org/collab-maint/libhermit.git -#Vcs-Browser: https://anonscm.debian.org/cgit/collab-maint/libhermit.git - -Package: libhermit -Architecture: any -Depends: ${shlibs:Depends}, ${misc:Depends} -Description: A Unikernel for Extreme-Scale Computing - diff --git a/debian/copyright b/debian/copyright deleted file mode 100644 index 402cae500..000000000 --- a/debian/copyright +++ /dev/null @@ -1,54 +0,0 @@ -Format: https://www.debian.org/doc/packaging-manuals/copyright-format/1.0/ -Upstream-Name: libhermit -Source: http://www.hermitcore.org - -Files: * -Copyright: 2010-2017 Stefan Lankes -License: Revised BSD License - Redistribution and use in source and binary forms, with or without - modification, are permitted provided that the following conditions are met: - * Redistributions of source code must retain the above copyright - notice, this list of conditions and the following disclaimer. - * Redistributions in binary form must reproduce the above copyright - notice, this list of conditions and the following disclaimer in the - documentation and/or other materials provided with the distribution. - * Neither the name of the University nor the names of its contributors - may be used to endorse or promote products derived from this - software without specific prior written permission. - . - THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND - ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED - WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE - DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE FOR ANY - DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES - (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; - LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND - ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT - (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS - SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - -# If you want to use GPL v2 or later for the /debian/* files use -# the following clauses, or change it to suit. Delete these two lines -Files: debian/* -Copyright: 2017 Stefan Lankes -License: GPL-2+ - This package is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - . - This package is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - . - You should have received a copy of the GNU General Public License - along with this program. If not, see - . - On Debian systems, the complete text of the GNU General - Public License version 2 can be found in "/usr/share/common-licenses/GPL-2". - -# Please also look if there are files or directories which have a -# different copyright/license attached and list them here. -# Please avoid picking licenses with terms that are more restrictive than the -# packaged work, as it may make Debian's contributions unacceptable upstream. diff --git a/debian/init.d.ex b/debian/init.d.ex deleted file mode 100644 index c78626002..000000000 --- a/debian/init.d.ex +++ /dev/null @@ -1,26 +0,0 @@ -#!/bin/sh -# kFreeBSD do not accept scripts as interpreters, using #!/bin/sh and sourcing. -if [ true != "$INIT_D_SCRIPT_SOURCED" ] ; then - set "$0" "$@"; INIT_D_SCRIPT_SOURCED=true . /lib/init/init-d-script -fi -### BEGIN INIT INFO -# Provides: libhermit -# Required-Start: $remote_fs $syslog -# Required-Stop: $remote_fs $syslog -# Default-Start: 2 3 4 5 -# Default-Stop: 0 1 6 -# Short-Description: -# Description: -# <...> -# <...> -### END INIT INFO - -# Author: Stefan Lankes - -DESC="libhermit" -DAEMON=/usr/bin/libhermit - -# This is an example to start a single forking daemon capable of writing -# a pid file. To get other behaviors, implement do_start(), do_stop() or -# other functions to override the defaults in /lib/init/init-d-script. -# See also init-d-script(5) diff --git a/debian/libhermit-docs.docs b/debian/libhermit-docs.docs deleted file mode 100644 index efea0a6a2..000000000 --- a/debian/libhermit-docs.docs +++ /dev/null @@ -1,2 +0,0 @@ -README.Debian -README.source diff --git a/debian/libhermit.cron.d.ex b/debian/libhermit.cron.d.ex deleted file mode 100644 index 7b16d8228..000000000 --- a/debian/libhermit.cron.d.ex +++ /dev/null @@ -1,4 +0,0 @@ -# -# Regular cron jobs for the libhermit package -# -0 4 * * * root [ -x /usr/bin/libhermit_maintenance ] && /usr/bin/libhermit_maintenance diff --git a/debian/libhermit.default.ex b/debian/libhermit.default.ex deleted file mode 100644 index 112ad9b7d..000000000 --- a/debian/libhermit.default.ex +++ /dev/null @@ -1,10 +0,0 @@ -# Defaults for libhermit initscript -# sourced by /etc/init.d/libhermit -# installed at /etc/default/libhermit by the maintainer scripts - -# -# This is a POSIX shell fragment -# - -# Additional options that are passed to the Daemon. -DAEMON_OPTS="" diff --git a/debian/libhermit.doc-base.EX b/debian/libhermit.doc-base.EX deleted file mode 100644 index 98a0769f9..000000000 --- a/debian/libhermit.doc-base.EX +++ /dev/null @@ -1,20 +0,0 @@ -Document: libhermit -Title: Debian libhermit Manual -Author: -Abstract: This manual describes what libhermit is - and how it can be used to - manage online manuals on Debian systems. -Section: unknown - -Format: debiandoc-sgml -Files: /usr/share/doc/libhermit/libhermit.sgml.gz - -Format: postscript -Files: /usr/share/doc/libhermit/libhermit.ps.gz - -Format: text -Files: /usr/share/doc/libhermit/libhermit.text.gz - -Format: HTML -Index: /usr/share/doc/libhermit/html/index.html -Files: /usr/share/doc/libhermit/html/*.html diff --git a/debian/manpage.1.ex b/debian/manpage.1.ex deleted file mode 100644 index 9f73ea22f..000000000 --- a/debian/manpage.1.ex +++ /dev/null @@ -1,56 +0,0 @@ -.\" Hey, EMACS: -*- nroff -*- -.\" (C) Copyright 2017 Stefan Lankes , -.\" -.\" First parameter, NAME, should be all caps -.\" Second parameter, SECTION, should be 1-8, maybe w/ subsection -.\" other parameters are allowed: see man(7), man(1) -.TH Libhermit SECTION "January 8 2017" -.\" Please adjust this date whenever revising the manpage. -.\" -.\" Some roff macros, for reference: -.\" .nh disable hyphenation -.\" .hy enable hyphenation -.\" .ad l left justify -.\" .ad b justify to both left and right margins -.\" .nf disable filling -.\" .fi enable filling -.\" .br insert line break -.\" .sp insert n+1 empty lines -.\" for manpage-specific macros, see man(7) -.SH NAME -libhermit \- program to do something -.SH SYNOPSIS -.B libhermit -.RI [ options ] " files" ... -.br -.B bar -.RI [ options ] " files" ... -.SH DESCRIPTION -This manual page documents briefly the -.B libhermit -and -.B bar -commands. -.PP -.\" TeX users may be more comfortable with the \fB\fP and -.\" \fI\fP escape sequences to invode bold face and italics, -.\" respectively. -\fBlibhermit\fP is a program that... -.SH OPTIONS -These programs follow the usual GNU command line syntax, with long -options starting with two dashes (`-'). -A summary of options is included below. -For a complete description, see the Info files. -.TP -.B \-h, \-\-help -Show summary of options. -.TP -.B \-v, \-\-version -Show version of program. -.SH SEE ALSO -.BR bar (1), -.BR baz (1). -.br -The programs are documented fully by -.IR "The Rise and Fall of a Fooish Bar" , -available via the Info system. diff --git a/debian/manpage.sgml.ex b/debian/manpage.sgml.ex deleted file mode 100644 index ed5de58e1..000000000 --- a/debian/manpage.sgml.ex +++ /dev/null @@ -1,154 +0,0 @@ - manpage.1'. You may view - the manual page with: `docbook-to-man manpage.sgml | nroff -man | - less'. A typical entry in a Makefile or Makefile.am is: - -manpage.1: manpage.sgml - docbook-to-man $< > $@ - - - The docbook-to-man binary is found in the docbook-to-man package. - Please remember that if you create the nroff version in one of the - debian/rules file targets (such as build), you will need to include - docbook-to-man in your Build-Depends control field. - - --> - - - FIRSTNAME"> - SURNAME"> - - January 8 2017"> - - SECTION"> - slankes@eonerc.rwth-aachen.de"> - - Libhermit"> - - - Debian"> - GNU"> - GPL"> -]> - - - -
- &dhemail; -
- - &dhfirstname; - &dhsurname; - - - 2003 - &dhusername; - - &dhdate; -
- - &dhucpackage; - - &dhsection; - - - &dhpackage; - - program to do something - - - - &dhpackage; - - - - - - - - DESCRIPTION - - This manual page documents briefly the - &dhpackage; and bar - commands. - - This manual page was written for the &debian; distribution - because the original program does not have a manual page. - Instead, it has documentation in the &gnu; - Info format; see below. - - &dhpackage; is a program that... - - - - OPTIONS - - These programs follow the usual &gnu; command line syntax, - with long options starting with two dashes (`-'). A summary of - options is included below. For a complete description, see the - Info files. - - - - - - - - Show summary of options. - - - - - - - - Show version of program. - - - - - - SEE ALSO - - bar (1), baz (1). - - The programs are documented fully by The Rise and - Fall of a Fooish Bar available via the - Info system. - - - AUTHOR - - This manual page was written by &dhusername; &dhemail; for - the &debian; system (and may be used by others). Permission is - granted to copy, distribute and/or modify this document under - the terms of the &gnu; General Public License, Version 2 any - later version published by the Free Software Foundation. - - - On Debian systems, the complete text of the GNU General Public - License can be found in /usr/share/common-licenses/GPL. - - - -
- - diff --git a/debian/manpage.xml.ex b/debian/manpage.xml.ex deleted file mode 100644 index 5f9bc4015..000000000 --- a/debian/manpage.xml.ex +++ /dev/null @@ -1,291 +0,0 @@ - -.
will be generated. You may view the -manual page with: nroff -man .
| less'. A typical entry -in a Makefile or Makefile.am is: - -DB2MAN = /usr/share/sgml/docbook/stylesheet/xsl/docbook-xsl/manpages/docbook.xsl -XP = xsltproc -''-nonet -''-param man.charmap.use.subset "0" - -manpage.1: manpage.xml - $(XP) $(DB2MAN) $< - -The xsltproc binary is found in the xsltproc package. The XSL files are in -docbook-xsl. A description of the parameters you can use can be found in the -docbook-xsl-doc-* packages. Please remember that if you create the nroff -version in one of the debian/rules file targets (such as build), you will need -to include xsltproc and docbook-xsl in your Build-Depends control field. -Alternatively use the xmlto command/package. That will also automatically -pull in xsltproc and docbook-xsl. - -Notes for using docbook2x: docbook2x-man does not automatically create the -AUTHOR(S) and COPYRIGHT sections. In this case, please add them manually as - ... . - -To disable the automatic creation of the AUTHOR(S) and COPYRIGHT sections -read /usr/share/doc/docbook-xsl/doc/manpages/authors.html. This file can be -found in the docbook-xsl-doc-html package. - -Validation can be done using: `xmllint -''-noout -''-valid manpage.xml` - -General documentation about man-pages and man-page-formatting: -man(1), man(7), http://www.tldp.org/HOWTO/Man-Page/ - ---> - - - - - - - - - - - - - -]> - - - - &dhtitle; - &dhpackage; - - - &dhfirstname; - &dhsurname; - Wrote this manpage for the Debian system. -
- &dhemail; -
-
-
- - 2007 - &dhusername; - - - This manual page was written for the Debian system - (and may be used by others). - Permission is granted to copy, distribute and/or modify this - document under the terms of the GNU General Public License, - Version 2 or (at your option) any later version published by - the Free Software Foundation. - On Debian systems, the complete text of the GNU General Public - License can be found in - /usr/share/common-licenses/GPL. - -
- - &dhucpackage; - &dhsection; - - - &dhpackage; - program to do something - - - - &dhpackage; - - - - - - - - - this - - - - - - - - this - that - - - - - &dhpackage; - - - - - - - - - - - - - - - - - - - DESCRIPTION - This manual page documents briefly the - &dhpackage; and bar - commands. - This manual page was written for the Debian distribution - because the original program does not have a manual page. - Instead, it has documentation in the GNU - info - 1 - format; see below. - &dhpackage; is a program that... - - - OPTIONS - The program follows the usual GNU command line syntax, - with long options starting with two dashes (`-'). A summary of - options is included below. For a complete description, see the - - info - 1 - files. - - - - - - - Does this and that. - - - - - - - Show summary of options. - - - - - - - Show version of program. - - - - - - FILES - - - /etc/foo.conf - - The system-wide configuration file to control the - behaviour of &dhpackage;. See - - foo.conf - 5 - for further details. - - - - ${HOME}/.foo.conf - - The per-user configuration file to control the - behaviour of &dhpackage;. See - - foo.conf - 5 - for further details. - - - - - - ENVIRONMENT - - - FOO_CONF - - If used, the defined file is used as configuration - file (see also ). - - - - - - DIAGNOSTICS - The following diagnostics may be issued - on stderr: - - - Bad configuration file. Exiting. - - The configuration file seems to contain a broken configuration - line. Use the option, to get more info. - - - - - &dhpackage; provides some return codes, that can - be used in scripts: - - Code - Diagnostic - - 0 - Program exited successfully. - - - 1 - The configuration file seems to be broken. - - - - - - BUGS - The program is currently limited to only work - with the foobar library. - The upstreams BTS can be found - at . - - - SEE ALSO - - - bar - 1 - , - baz - 1 - , - foo.conf - 5 - - The programs are documented fully by The Rise and - Fall of a Fooish Bar available via the - info - 1 - system. - -
- diff --git a/debian/menu.ex b/debian/menu.ex deleted file mode 100644 index bfe8b672d..000000000 --- a/debian/menu.ex +++ /dev/null @@ -1,2 +0,0 @@ -?package(libhermit):needs="X11|text|vc|wm" section="Applications/see-menu-manual"\ - title="libhermit" command="/usr/bin/libhermit" diff --git a/debian/postinst.ex b/debian/postinst.ex deleted file mode 100644 index 35db68281..000000000 --- a/debian/postinst.ex +++ /dev/null @@ -1,39 +0,0 @@ -#!/bin/sh -# postinst script for libhermit -# -# see: dh_installdeb(1) - -set -e - -# summary of how this script can be called: -# * `configure' -# * `abort-upgrade' -# * `abort-remove' `in-favour' -# -# * `abort-remove' -# * `abort-deconfigure' `in-favour' -# `removing' -# -# for details, see https://www.debian.org/doc/debian-policy/ or -# the debian-policy package - - -case "$1" in - configure) - ;; - - abort-upgrade|abort-remove|abort-deconfigure) - ;; - - *) - echo "postinst called with unknown argument \`$1'" >&2 - exit 1 - ;; -esac - -# dh_installdeb will replace this with shell code automatically -# generated by other debhelper scripts. - -#DEBHELPER# - -exit 0 diff --git a/debian/postrm.ex b/debian/postrm.ex deleted file mode 100644 index 9b1da3ff0..000000000 --- a/debian/postrm.ex +++ /dev/null @@ -1,37 +0,0 @@ -#!/bin/sh -# postrm script for libhermit -# -# see: dh_installdeb(1) - -set -e - -# summary of how this script can be called: -# * `remove' -# * `purge' -# * `upgrade' -# * `failed-upgrade' -# * `abort-install' -# * `abort-install' -# * `abort-upgrade' -# * `disappear' -# -# for details, see https://www.debian.org/doc/debian-policy/ or -# the debian-policy package - - -case "$1" in - purge|remove|upgrade|failed-upgrade|abort-install|abort-upgrade|disappear) - ;; - - *) - echo "postrm called with unknown argument \`$1'" >&2 - exit 1 - ;; -esac - -# dh_installdeb will replace this with shell code automatically -# generated by other debhelper scripts. - -#DEBHELPER# - -exit 0 diff --git a/debian/preinst.ex b/debian/preinst.ex deleted file mode 100644 index 32decc7b5..000000000 --- a/debian/preinst.ex +++ /dev/null @@ -1,35 +0,0 @@ -#!/bin/sh -# preinst script for libhermit -# -# see: dh_installdeb(1) - -set -e - -# summary of how this script can be called: -# * `install' -# * `install' -# * `upgrade' -# * `abort-upgrade' -# for details, see https://www.debian.org/doc/debian-policy/ or -# the debian-policy package - - -case "$1" in - install|upgrade) - ;; - - abort-upgrade) - ;; - - *) - echo "preinst called with unknown argument \`$1'" >&2 - exit 1 - ;; -esac - -# dh_installdeb will replace this with shell code automatically -# generated by other debhelper scripts. - -#DEBHELPER# - -exit 0 diff --git a/debian/prerm.ex b/debian/prerm.ex deleted file mode 100644 index 3a5533780..000000000 --- a/debian/prerm.ex +++ /dev/null @@ -1,38 +0,0 @@ -#!/bin/sh -# prerm script for libhermit -# -# see: dh_installdeb(1) - -set -e - -# summary of how this script can be called: -# * `remove' -# * `upgrade' -# * `failed-upgrade' -# * `remove' `in-favour' -# * `deconfigure' `in-favour' -# `removing' -# -# for details, see https://www.debian.org/doc/debian-policy/ or -# the debian-policy package - - -case "$1" in - remove|upgrade|deconfigure) - ;; - - failed-upgrade) - ;; - - *) - echo "prerm called with unknown argument \`$1'" >&2 - exit 1 - ;; -esac - -# dh_installdeb will replace this with shell code automatically -# generated by other debhelper scripts. - -#DEBHELPER# - -exit 0 diff --git a/debian/rules b/debian/rules deleted file mode 100755 index 9f0e5f692..000000000 --- a/debian/rules +++ /dev/null @@ -1,36 +0,0 @@ -#!/usr/bin/make -f -# See debhelper(7) (uncomment to enable) -# output every command that modifies files on the build system. -#export DH_VERBOSE = 1 - -# see FEATURE AREAS in dpkg-buildflags(1) -#export DEB_BUILD_MAINT_OPTIONS = hardening=+all -export DEB_BUILD_OPTS = nocheck - -%: - dh $@ #--parallel - -override_dh_auto_configure: - ./configure --prefix=`pwd`/debian/libhermit/opt/hermit - -override_dh_auto_build: - # this target is somehow not executed by dh_auto_build and thus the build fails - make arch/x86/kernel/boot.h - - dh_auto_build - make libs - -override_dh_auto_test: - @echo "tests are disabled" - -override_dh_auto_install: - #make install_libhermit - make install - - # delete unneded files that would cause conflicts - rm -rf `-pwd`/debian/libhermit/opt/hermit/share/info/dir - -override_dh_strip: - # stripping will incorrectly use system tools for stripping, generating - # wrong binary format, i.e. not for HermitCore - @echo "No stripping" diff --git a/debian/source/format b/debian/source/format deleted file mode 100644 index 163aaf8d8..000000000 --- a/debian/source/format +++ /dev/null @@ -1 +0,0 @@ -3.0 (quilt) diff --git a/debian/watch.ex b/debian/watch.ex deleted file mode 100644 index 8dac5167c..000000000 --- a/debian/watch.ex +++ /dev/null @@ -1,39 +0,0 @@ -# Example watch control file for uscan -# Rename this file to "watch" and then you can run the "uscan" command -# to check for upstream updates and more. -# See uscan(1) for format - -# Compulsory line, this is a version 4 file -version=4 - -# PGP signature mangle, so foo.tar.gz has foo.tar.gz.sig -#opts="pgpsigurlmangle=s%$%.sig%" - -# HTTP site (basic) -#http://example.com/downloads.html \ -# files/libhermit-([\d\.]+)\.tar\.gz debian uupdate - -# Uncommment to examine a FTP server -#ftp://ftp.example.com/pub/libhermit-(.*)\.tar\.gz debian uupdate - -# SourceForge hosted projects -# http://sf.net/libhermit/ libhermit-(.*)\.tar\.gz debian uupdate - -# GitHub hosted projects -#opts="filenamemangle="s%(?:.*?)?v?(\d[\d.]*)\.tar\.gz%-$1.tar.gz%" \ -# https://github.com//libhermit/tags \ -# (?:.*?/)?v?(\d[\d.]*)\.tar\.gz debian uupdate - -# PyPI -# https://pypi.python.org/packages/source//libhermit/ \ -# libhermit-(.+)\.tar\.gz debian uupdate - -# Direct Git -# opts="mode=git" http://git.example.com/libhermit.git \ -# refs/tags/v([\d\.]+) debian uupdate - - - - -# Uncomment to find new files on GooglePages -# http://example.googlepages.com/foo.html libhermit-(.*)\.tar\.gz diff --git a/drivers/net/Makefile b/drivers/net/Makefile deleted file mode 100644 index e7dbc74a4..000000000 --- a/drivers/net/Makefile +++ /dev/null @@ -1,4 +0,0 @@ -C_source := mmnif.c util.c e1000.c rtl8139.c -MODULE := drivers_net - -include $(TOPDIR)/Makefile.inc diff --git a/drivers/net/e1000.c b/drivers/net/e1000.c index 8fb4f4b57..852cc97fa 100644 --- a/drivers/net/e1000.c +++ b/drivers/net/e1000.c @@ -1,4 +1,4 @@ -/* +/* * Copyright 2012 Stefan Lankes, Chair for Operating Systems, * RWTH Aachen University * @@ -58,7 +58,7 @@ typedef struct { uint32_t device; } board_t; -static board_t board_tbl[] = +static board_t board_tbl[] = { {"Intel", "Intel E1000 (82542)", 0x8086, 0x1000}, {"Intel", "Intel E1000 (82543GC FIBER)", 0x8086, 0x1001}, @@ -67,7 +67,7 @@ static board_t board_tbl[] = {"Intel", "Intel E1000 (82544EI FIBER)", 0x8086, 0x1009}, {"Intel", "Intel E1000 (82544GC COPPER)", 0x8086, 0x100C}, {"Intel", "Intel E1000 (82544GC LOM)", 0x8086, 0x100D}, - {"Intel", "Intel E1000 (82540EM)", 0x8086, 0x100E}, + {"Intel", "Intel E1000 (82540EM)", 0x8086, 0x100E}, {"Intel", "Intel E1000 (82540EM LOM)", 0x8086, 0x1015}, {"Intel", "Intel E1000 (82540EP LOM)", 0x8086, 0x1016}, {"Intel", "Intel E1000 (82540EP)", 0x8086, 0x1017}, @@ -132,7 +132,7 @@ static uint16_t eeprom_read(volatile uint8_t* base, uint8_t addr) e1000_write(base, E1000_EERD, 1 | ((uint32_t)(addr) << 8)); - while(!((tmp = e1000_read(base, E1000_EERD)) & (1 << 4))) + while(!((tmp = e1000_read(base, E1000_EERD)) & (1 << 4))) udelay(1); data = (uint16_t)((tmp >> 16) & 0xFFFF); @@ -148,7 +148,7 @@ static uint16_t eeprom_read(uint8_t* base, uint8_t addr) e1000_write(base, E1000_EERD, 1 | ((uint32_t)(addr) << 2)); - while(!((tmp = e1000_read(base, E1000_EERD)) & (1 << 1))) + while(!((tmp = e1000_read(base, E1000_EERD)) & (1 << 1))) udelay(1); data = (uint16_t)((tmp >> 16) & 0xFFFF); @@ -198,7 +198,7 @@ static err_t e1000if_output(struct netif* netif, struct pbuf* p) // update the tail so the hardware knows it's ready e1000if->tx_tail = (e1000if->tx_tail + 1) % NUM_TX_DESCRIPTORS; - e1000_write(e1000if->bar0, E1000_TDT, e1000if->tx_tail); + e1000_write(e1000if->bar0, E1000_TDT, e1000if->tx_tail); #if ETH_PAD_SIZE pbuf_header(p, ETH_PAD_SIZE); /* reclaim the padding word */ @@ -256,7 +256,7 @@ static void e1000_rx_inthandler(struct netif* netif) LINK_STATS_INC(link.drop); } -no_eop: +no_eop: e1000if->rx_desc[e1000if->rx_tail].status = 0; // update tail and write the value to the device @@ -333,12 +333,12 @@ err_t e1000if_init(struct netif* netif) uint16_t tmp16, speed, cold = 0x40; uint8_t tmp8, is64bit, mem_type, prefetch; static uint8_t num = 0; - + LWIP_ASSERT("netif != NULL", (netif != NULL)); tmp8 = 0; while (board_tbl[tmp8].vendor_str) { - if (pci_get_device_info(board_tbl[tmp8].vendor, board_tbl[tmp8].device, &pci_info, 1) == 0) + if (pci_get_device_info(board_tbl[tmp8].vendor, board_tbl[tmp8].device, PCI_IGNORE_SUBID, &pci_info, 1) == 0) break; tmp8++; } @@ -394,7 +394,7 @@ err_t e1000if_init(struct netif* netif) goto oom; memset((void*) e1000if->tx_desc, 0x00, NUM_TX_DESCRIPTORS*sizeof(tx_desc_t)); - LWIP_DEBUGF(NETIF_DEBUG, ("e1000if_init: Found %s at mmio 0x%x (size 0x%x), irq %u\n", board_tbl[tmp8].device_str, + LWIP_DEBUGF(NETIF_DEBUG, ("e1000if_init: Found %s at mmio 0x%x (size 0x%x), irq %u\n", board_tbl[tmp8].device_str, pci_info.base[0] & ~0xF, pci_info.size[0], e1000if->irq)); //LWIP_DEBUGF(NETIF_DEBUG, ("e1000if_init: Map iobase to %p\n", e1000if->bar0)); LWIP_DEBUGF(NETIF_DEBUG, ("e1000if_init: is64bit %u, prefetch %u\n", is64bit, prefetch)); @@ -439,7 +439,7 @@ err_t e1000if_init(struct netif* netif) // transmit buffer length; NUM_TX_DESCRIPTORS 16-byte descriptors e1000_write(e1000if->bar0, E1000_TDLEN , (uint32_t)(NUM_TX_DESCRIPTORS * sizeof(tx_desc_t))); - + // setup head and tail pointers e1000_write(e1000if->bar0, E1000_TDH, 0); e1000_write(e1000if->bar0, E1000_TDT, 0); @@ -472,7 +472,7 @@ err_t e1000if_init(struct netif* netif) tmp32 = 0; for(tmp8=0; tmp8<2; tmp8++) ((uint8_t*) &tmp32)[tmp8] = netif->hwaddr[tmp8+4]; - e1000_write(e1000if->bar0, E1000_RA+4, tmp32 | (1 << 31)); // set also AV bit to check incoming packets + e1000_write(e1000if->bar0, E1000_RA+4, tmp32 | (1 << 31)); // set also AV bit to check incoming packets /* Zero out the other receive addresses. */ for (tmp8=1; tmp8<16; tmp8++) { diff --git a/drivers/net/mmnif.c b/drivers/net/mmnif.c index 524e2edbd..29e8034cf 100644 --- a/drivers/net/mmnif.c +++ b/drivers/net/mmnif.c @@ -678,7 +678,7 @@ err_t mmnif_init(struct netif *netif) num++; /* downward functions */ - netif->output = mmnif_link_layer; + netif->output = (netif_output_fn) mmnif_link_layer; /* there is no special link layer just the ip layer */ netif->linkoutput = mmnif_tx; @@ -686,8 +686,6 @@ err_t mmnif_init(struct netif *netif) /* maximum transfer unit */ netif->mtu = 1500; - /* broadcast capability, keep all default flags */ - //netif->flags |= NETIF_FLAG_BROADCAST; /* set link up */ netif->flags |= NETIF_FLAG_LINK_UP; diff --git a/drivers/net/rtl8139.c b/drivers/net/rtl8139.c index e3e5bd0e0..3358cfbcf 100644 --- a/drivers/net/rtl8139.c +++ b/drivers/net/rtl8139.c @@ -1,4 +1,4 @@ -/* +/* * Copyright 2010 Stefan Lankes, Chair for Operating Systems, * RWTH Aachen University * @@ -68,7 +68,7 @@ typedef struct { uint32_t device; } board_t; -static board_t board_tbl[] = +static board_t board_tbl[] = { {"RealTek", "RealTek RTL8139", 0x10ec, 0x8139}, {"RealTek", "RealTek RTL8129 Fast Ethernet", 0x10ec, 0x8129}, @@ -307,7 +307,7 @@ err_t rtl8139if_init(struct netif* netif) tmp8 = 0; while (board_tbl[tmp8].vendor_str) { - if (pci_get_device_info(board_tbl[tmp8].vendor, board_tbl[tmp8].device, &pci_info, 1) == 0) + if (pci_get_device_info(board_tbl[tmp8].vendor, board_tbl[tmp8].device, PCI_IGNORE_SUBID, &pci_info, 1) == 0) break; tmp8++; } @@ -388,8 +388,8 @@ err_t rtl8139if_init(struct netif* netif) outportb(rtl8139if->iobase + CR, CR_RST); /* - * The RST bit must be checked to make sure that the chip has finished the reset. - * If the RST bit is high (1), then the reset is still in operation. + * The RST bit must be checked to make sure that the chip has finished the reset. + * If the RST bit is high (1), then the reset is still in operation. */ udelay(10000); tmp16 = 10000; @@ -419,7 +419,7 @@ err_t rtl8139if_init(struct netif* netif) outportb(rtl8139if->iobase + CONFIG1, 0); // disable driver loaded and lanwake bits, turn driver loaded bit back on - outportb(rtl8139if->iobase + CONFIG1, + outportb(rtl8139if->iobase + CONFIG1, (inportb(rtl8139if->iobase + CONFIG1) & ~(CONFIG1_DVRLOAD | CONFIG1_LWACT)) | CONFIG1_DVRLOAD); // unlock config register @@ -430,7 +430,7 @@ err_t rtl8139if_init(struct netif* netif) * AB - Accept Broadcast: Accept broadcast packets sent to mac ff:ff:ff:ff:ff:ff * AM - Accept Multicast: Accept multicast packets. * APM - Accept Physical Match: Accept packets send to NIC's MAC address. - * AAP - Accept All Packets. Accept all packets (run in promiscuous mode). + * AAP - Accept All Packets. Accept all packets (run in promiscuous mode). */ outportl(rtl8139if->iobase + RCR, RCR_MXDMA2|RCR_MXDMA1|RCR_MXDMA0|RCR_AB|RCR_AM|RCR_APM|RCR_AAP); // The WRAP bit isn't set! @@ -456,7 +456,7 @@ err_t rtl8139if_init(struct netif* netif) if (tmp16 & BMCR_SPD1000) speed = 1000; else if (tmp16 & BMCR_SPD100) - speed = 100; + speed = 100; else speed = 10; // Enable Receive and Transmitter diff --git a/drivers/net/vioif.c b/drivers/net/vioif.c new file mode 100644 index 000000000..fc37eaaed --- /dev/null +++ b/drivers/net/vioif.c @@ -0,0 +1,458 @@ +/* + * Copyright (c) 2017, Stefan Lankes, RWTH Aachen University + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * * Neither the name of the University nor the names of its contributors + * may be used to endorse or promote products derived from this + * software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#define VENDOR_ID 0x1AF4 +#define VIOIF_BUFFER_SIZE 0x2048 +#define MIN(a, b) (a) < (b) ? (a) : (b) +#define QUEUE_LIMIT 256 + +/* NOTE: RX queue is 0, TX queue is 1 - Virtio Std. §5.1.2 */ +#define TX_NUM 1 +#define RX_NUM 0 + +static struct netif* mynetif = NULL; + +static inline void vioif_enable_interrupts(virt_queue_t* vq) +{ + vq->vring.used->flags = 0; +} + +static inline void vioif_disable_interrupts(virt_queue_t* vq) +{ + vq->vring.used->flags = 1; +} + +/* + * @return error code + * - ERR_OK: packet transferred to hardware + * - ERR_CONN: no link or link failure + * - ERR_IF: could not transfer to link (hardware buffer full?) + */ +static err_t vioif_output(struct netif* netif, struct pbuf* p) +{ + vioif_t* vioif = netif->state; + virt_queue_t* vq = &vioif->queues[TX_NUM]; + struct pbuf *q; + uint32_t i; + uint16_t buffer_index; + + if (BUILTIN_EXPECT(p->tot_len > 1792, 0)) { + LOG_ERROR("vioif_output: packet is longer than 1792 bytes\n"); + return ERR_IF; + } + + for(buffer_index=0; buffer_indexvring.num; buffer_index++) { + if (!vq->vring.desc[buffer_index].len) { + LOG_DEBUG("vioif_output: buffer %u is free\n", buffer_index); + break; + } + } + LOG_DEBUG("vioif: found free buffer %d\n", buffer_index); + + if (BUILTIN_EXPECT(buffer_index >= vq->vring.num, 0)) { + LOG_ERROR("vioif_output: too many packets at once\n"); + return ERR_IF; + } + +#if ETH_PAD_SIZE + pbuf_header(p, -ETH_PAD_SIZE); /* drop the padding word */ +#endif + + const size_t hdr_sz = sizeof(struct virtio_net_hdr); + // NOTE: packet is fully checksummed => all flags are set to zero + memset((void*) (vq->virt_buffer + buffer_index * VIOIF_BUFFER_SIZE), 0x00, hdr_sz); + + vq->vring.desc[buffer_index].addr = vq->phys_buffer + buffer_index * VIOIF_BUFFER_SIZE; + vq->vring.desc[buffer_index].len = p->tot_len + hdr_sz; + vq->vring.desc[buffer_index].flags = 0; + // we send only one buffer because it is large enough for our packet + vq->vring.desc[buffer_index].next = 0; //(buffer_index+1) % vq->vring.num; + + + /* + * q traverses through linked list of pbuf's + * This list MUST consist of a single packet ONLY + */ + for (q = p, i = 0; q != 0; q = q->next) { + memcpy((void*) (vq->virt_buffer + hdr_sz + buffer_index * VIOIF_BUFFER_SIZE + i), q->payload, q->len); + i += q->len; + } + + // Add it in the available ring + uint16_t index = vq->vring.avail->idx % vq->vring.num; + vq->vring.avail->ring[index] = buffer_index; + + // besure that everything is written + mb(); + + vq->vring.avail->idx++; + + // besure that everything is written + mb(); + + /* + * Notify the changes + * NOTE: RX queue is 0, TX queue is 1 - Virtio Std. §5.1.2 + */ + outportw(vioif->iobase+VIRTIO_PCI_QUEUE_NOTIFY, TX_NUM); + +#if ETH_PAD_SIZE + pbuf_header(p, ETH_PAD_SIZE); /* reclaim the padding word */ +#endif + + LINK_STATS_INC(link.xmit); + + return ERR_OK; +} + +static void vioif_rx_inthandler(struct netif* netif) +{ + vioif_t* vioif = mynetif->state; + virt_queue_t* vq = &vioif->queues[RX_NUM]; + + while(vq->last_seen_used != vq->vring.used->idx) + { + const size_t hdr_sz = sizeof(struct virtio_net_hdr); + struct vring_used_elem* used = &vq->vring.used->ring[vq->last_seen_used % vq->vring.num]; + struct virtio_net_hdr* hdr = (struct virtio_net_hdr*) (vq->virt_buffer + used->id * VIOIF_BUFFER_SIZE); + + LOG_DEBUG("vq->vring.used->idx %d, vq->vring.used->flags %d, vq->last_seen_used %d\n", vq->vring.used->idx, vq->vring.used->flags, vq->last_seen_used); + LOG_DEBUG("used id %d, len %d\n", used->id, used->len); + LOG_DEBUG("hdr len %d, flags %d\n", hdr->hdr_len, hdr->flags); + + struct pbuf* p = pbuf_alloc(PBUF_RAW, used->len, PBUF_POOL); + if (p) { + uint16_t pos; + struct pbuf* q; + +#if ETH_PAD_SIZE + pbuf_header(p, -ETH_PAD_SIZE); /* drop the padding word */ +#endif + for(q=p, pos=0; q!=NULL; q=q->next) { + memcpy((uint8_t*) q->payload, + (uint8_t*) (vq->virt_buffer + hdr_sz + used->id * VIOIF_BUFFER_SIZE + pos), + q->len); + pos += q->len; + } +#if ETH_PAD_SIZE + pbuf_header(p, ETH_PAD_SIZE); /* reclaim the padding word */ +#endif + LINK_STATS_INC(link.recv); + + // forward packet to LwIP + netif->input(p, netif); + } else { + LOG_ERROR("vioif_rx_inthandler: not enough memory!\n"); + LINK_STATS_INC(link.memerr); + LINK_STATS_INC(link.drop); + goto oom; + } + + vq->vring.avail->ring[vq->vring.avail->idx % vq->vring.num] = used->id; + vq->vring.avail->idx++; + vq->last_seen_used++; + } + +oom: + vioif->polling = 0; + vioif_enable_interrupts(vq); + mb(); +} + + +/* this function is called in the context of the tcpip thread or the irq handler (by using NO_SYS) */ +static void vioif_poll(void* ctx) +{ + vioif_rx_inthandler(mynetif); +} + +static void vioif_handler(struct state* s) +{ + vioif_t* vioif = mynetif->state; + + LOG_DEBUG("vioif: receive interrupt\n"); + + // reset interrupt by reading the isr port + uint8_t isr = inportb(vioif->iobase+VIRTIO_PCI_ISR); + + // do we receiven an interrupt for this device? + if (!(isr & 0x01)) + return; + + // free TX queue + virt_queue_t* vq = &vioif->queues[1]; + + vioif_disable_interrupts(vq); + while(vq->last_seen_used != vq->vring.used->idx) + { + struct vring_used_elem* used = &vq->vring.used->ring[vq->last_seen_used % vq->vring.num]; + LOG_DEBUG("consumed TX elements: index %u, len %u\n", used->id, used->len); + // mark as free + vq->vring.desc[used->id].len = 0; + vq->last_seen_used++; + } + vioif_enable_interrupts(vq); + mb(); + + // check RX qeueue + vq = &vioif->queues[0]; + vioif_disable_interrupts(vq); + if (!vioif->polling && (vq->last_seen_used != vq->vring.used->idx)) + { +#if NO_SYS + vioif_poll(NULL); +#else + if (tcpip_callback_with_block(vioif_poll, NULL, 0) == ERR_OK) { + vioif->polling = 1; + } else { + LOG_ERROR("rtl8139if_handler: unable to send a poll request to the tcpip thread\n"); + } +#endif + } else vioif_enable_interrupts(vq); + mb(); +} + +static int vioif_queue_setup(vioif_t* dev) +{ + virt_queue_t* vq; + uint32_t total_size; + unsigned int num; + + for (uint32_t index=0; indexqueues[index]; + + memset(vq, 0x00, sizeof(virt_queue_t)); + + // determine queue size + outportw(dev->iobase+VIRTIO_PCI_QUEUE_SEL, index); + num = inportw(dev->iobase+VIRTIO_PCI_QUEUE_NUM); + if (!num) return -1; + + LOG_INFO("vioif: queue_size %u (index %u)\n", num, index); + + total_size = vring_size(num, PAGE_SIZE); + + // allocate and init memory for the virtual queue + void* vring_base = page_alloc(total_size, VMA_READ|VMA_WRITE|VMA_CACHEABLE); + if (BUILTIN_EXPECT(!vring_base, 0)) { + LOG_INFO("Not enough memory to create queue %u\n", index); + return -1; + } + memset((void*)vring_base, 0x00, total_size); + vring_init(&vq->vring, num, vring_base, PAGE_SIZE); + + if (num > QUEUE_LIMIT) { + vq->vring.num = num = QUEUE_LIMIT; + LOG_INFO("vioif: set queue limit to %u (index %u)\n", vq->vring.num, index); + } + + vq->virt_buffer = (uint64_t) page_alloc(num*VIOIF_BUFFER_SIZE, VMA_READ|VMA_WRITE|VMA_CACHEABLE); + if (BUILTIN_EXPECT(!vq->virt_buffer, 0)) { + LOG_INFO("Not enough memory to create buffer %u\n", index); + return -1; + } + vq->phys_buffer = virt_to_phys(vq->virt_buffer); + + for(int i=0; ivring.desc[i].addr = vq->phys_buffer + i * VIOIF_BUFFER_SIZE; + if (index == RX_NUM) { + /* NOTE: RX queue is 0, TX queue is 1 - Virtio Std. §5.1.2 */ + vq->vring.desc[i].len = VIOIF_BUFFER_SIZE; + vq->vring.desc[i].flags = VRING_DESC_F_WRITE; + vq->vring.avail->ring[vq->vring.avail->idx % num] = i; + vq->vring.avail->idx++; + } + } + + // register buffer + outportw(dev->iobase+VIRTIO_PCI_QUEUE_SEL, index); + outportl(dev->iobase+VIRTIO_PCI_QUEUE_PFN, virt_to_phys((size_t) vring_base) >> PAGE_BITS); + } + + return 0; +} + +err_t vioif_init(struct netif* netif) +{ + static uint8_t num = 0; + vioif_t* vioif; + pci_info_t pci_info; + int i; + + LWIP_ASSERT("netif != NULL", (netif != NULL)); + + for(i=0x100; i<=0x103F; i++) { + if ((pci_get_device_info(VENDOR_ID, i, 1, &pci_info, 1) == 0)) { + LOG_INFO("Found vioif (Vendor ID 0x%x, Device Id 0x%x)\n", VENDOR_ID, i); + break; + } + } + + if (i > 0x103F) + return ERR_ARG; + + vioif = kmalloc(sizeof(vioif_t)); + if (!vioif) { + LOG_ERROR("virtioif_init: out of memory\n"); + return ERR_MEM; + } + memset(vioif, 0x00, sizeof(vioif_t)); + + vioif->iomem = pci_info.base[1]; + vioif->iobase = pci_info.base[0]; + vioif->irq = pci_info.irq; + LOG_INFO("vioif uses IRQ %d and IO port 0x%x, IO men 0x%x\n", (int32_t) vioif->irq, vioif->iobase, vioif->iomem); + + // reset interface + outportb(vioif->iobase + VIRTIO_PCI_STATUS, 0); + LOG_INFO("vioif status: 0x%x\n", (uint32_t) inportb(vioif->iobase + VIRTIO_PCI_STATUS)); + + // tell the device that we have noticed it + outportb(vioif->iobase + VIRTIO_PCI_STATUS, VIRTIO_CONFIG_S_ACKNOWLEDGE); + // tell the device that we will support it. + outportb(vioif->iobase + VIRTIO_PCI_STATUS, VIRTIO_CONFIG_S_ACKNOWLEDGE|VIRTIO_CONFIG_S_DRIVER); + + LOG_INFO("host features 0x%x\n", inportl(vioif->iobase + VIRTIO_PCI_HOST_FEATURES)); + + uint32_t features = inportl(vioif->iobase + VIRTIO_PCI_HOST_FEATURES); + uint32_t required = (1UL << VIRTIO_NET_F_MAC) | (1UL << VIRTIO_NET_F_STATUS); + + if ((features & required) != required) { + LOG_ERROR("Host isn't able to fulfill HermireCore's requirements\n"); + outportb(vioif->iobase + VIRTIO_PCI_STATUS, VIRTIO_CONFIG_S_FAILED); + kfree(vioif); + return ERR_ARG; + } + + required = features; + required &= ~(1UL << VIRTIO_NET_F_CTRL_VQ); + required &= ~(1UL << VIRTIO_NET_F_GUEST_TSO4); + required &= ~(1UL << VIRTIO_NET_F_GUEST_TSO6); + required &= ~(1UL << VIRTIO_NET_F_GUEST_UFO); + required &= ~(1UL << VIRTIO_RING_F_EVENT_IDX); + required &= ~(1UL << VIRTIO_NET_F_MRG_RXBUF); + required &= ~(1UL << VIRTIO_NET_F_MQ); + + LOG_INFO("wanted guest features 0x%x\n", required); + outportl(vioif->iobase + VIRTIO_PCI_GUEST_FEATURES, required); + vioif->features = inportl(vioif->iobase + VIRTIO_PCI_GUEST_FEATURES); + LOG_INFO("current guest features 0x%x\n", vioif->features); + + // tell the device that the features are OK + outportb(vioif->iobase + VIRTIO_PCI_STATUS, VIRTIO_CONFIG_S_ACKNOWLEDGE|VIRTIO_CONFIG_S_DRIVER|VIRTIO_CONFIG_S_FEATURES_OK); + + // check if the host accept these features + uint8_t status = inportb(vioif->iobase + VIRTIO_PCI_STATUS); + if (!(status & VIRTIO_CONFIG_S_FEATURES_OK)) { + LOG_ERROR("device features are ignored: status 0x%x\n", (uint32_t) status); + outportb(vioif->iobase + VIRTIO_PCI_STATUS, VIRTIO_CONFIG_S_FAILED); + kfree(vioif); + return ERR_ARG; + } + + /* hardware address length */ + netif->hwaddr_len = ETHARP_HWADDR_LEN; + + // determine the mac address of this card + LWIP_DEBUGF(NETIF_DEBUG, ("vioif_init: MAC address ")); + for (uint8_t tmp8=0; tmp8hwaddr[tmp8] = inportb(vioif->iobase + VIRTIO_PCI_CONFIG_OFF(vioif->msix_enabled) + tmp8); + LWIP_DEBUGF(NETIF_DEBUG, ("%02x ", netif->hwaddr[tmp8])); + } + LWIP_DEBUGF(NETIF_DEBUG, ("\n")); + + // Setup virt queues + if (BUILTIN_EXPECT(vioif_queue_setup(vioif) < 0, 0)) { + outportb(vioif->iobase + VIRTIO_PCI_STATUS, VIRTIO_CONFIG_S_FAILED); + kfree(vioif); + return ERR_ARG; + } + + netif->state = vioif; + mynetif = netif; + + irq_install_handler(vioif->irq+32, vioif_handler); + + /* + * Initialize the snmp variables and counters inside the struct netif. + * The last argument should be replaced with your link speed, in units + * of bits per second. + */ + NETIF_INIT_SNMP(netif, snmp_ifType_ethernet_csmacd, 1000); + + /* administrative details */ + netif->name[0] = 'e'; + netif->name[1] = 'n'; + netif->num = num; + num++; + /* downward functions */ + netif->output = etharp_output; + netif->linkoutput = vioif_output; + /* set maximum transfer unit + * Google Compute Platform supports only a MTU from 1460 + */ + netif->mtu = 1460; + /* broadcast capability */ + netif->flags |= NETIF_FLAG_BROADCAST | NETIF_FLAG_ETHARP | NETIF_FLAG_IGMP | NETIF_FLAG_LINK_UP | NETIF_FLAG_MLD6; +#if LWIP_IPV6 + netif->output_ip6 = ethip6_output; + netif_create_ip6_linklocal_address(netif, 1); + netif->ip6_autoconfig_enabled = 1; +#endif + + // tell the device that the drivers is initialized + outportb(vioif->iobase + VIRTIO_PCI_STATUS, VIRTIO_CONFIG_S_ACKNOWLEDGE|VIRTIO_CONFIG_S_DRIVER|VIRTIO_CONFIG_S_DRIVER_OK|VIRTIO_CONFIG_S_FEATURES_OK); + + LOG_INFO("vioif status: 0x%x\n", (uint32_t) inportb(vioif->iobase + VIRTIO_PCI_STATUS)); + LOG_INFO("vioif link is %s\n", + inportl(vioif->iobase + VIRTIO_PCI_CONFIG_OFF(vioif->msix_enabled) + ETHARP_HWADDR_LEN) & VIRTIO_NET_S_LINK_UP ? "up" : "down"); + + return ERR_OK; +} diff --git a/drivers/net/vioif.h b/drivers/net/vioif.h new file mode 100644 index 000000000..20dc9e82d --- /dev/null +++ b/drivers/net/vioif.h @@ -0,0 +1,64 @@ +/* + * Copyright (c) 2017, Stefan Lankes, RWTH Aachen University + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * * Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * * Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * * Neither the name of the University nor the names of its contributors + * may be used to endorse or promote products derived from this + * software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE + * DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE FOR ANY + * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES + * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; + * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND + * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT + * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS + * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + */ + +#ifndef __NET_VIOIF_H__ +#define __NET_VIOIF_H__ + +#include +#include + +#define VIOIF_NUM_QUEUES 2 + +typedef struct +{ + struct vring vring; + uint64_t virt_buffer; + uint64_t phys_buffer; + uint16_t last_seen_used; +} virt_queue_t; + +/* + * Helper struct to hold private data used to operate your ethernet interface. + */ +typedef struct vioif { + struct eth_addr *ethaddr; + /* Add whatever per-interface state that is needed here. */ + uint32_t iomem; + uint32_t iobase; + uint32_t features; + uint8_t msix_enabled; + uint8_t irq; + uint8_t polling; + virt_queue_t queues[VIOIF_NUM_QUEUES]; +} vioif_t; + +/* + * Initialize the network driver for the virtio network interface + */ +err_t vioif_init(struct netif* netif); + +#endif diff --git a/img/demo.gif b/img/demo.gif new file mode 100644 index 000000000..83d900526 Binary files /dev/null and b/img/demo.gif differ diff --git a/img/hermitcore_logo.png b/img/hermitcore_logo.png new file mode 100755 index 000000000..7d578afb4 Binary files /dev/null and b/img/hermitcore_logo.png differ diff --git a/img/hermitcore_logo.svg b/img/hermitcore_logo.svg new file mode 100755 index 000000000..1f7936f4a --- /dev/null +++ b/img/hermitcore_logo.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/include/hermit/CMakeLists.txt b/include/hermit/CMakeLists.txt new file mode 100644 index 000000000..5f4dee9b4 --- /dev/null +++ b/include/hermit/CMakeLists.txt @@ -0,0 +1,15 @@ +cmake_minimum_required(VERSION 3.7) + +configure_file(config.h.in config.h) +configure_file(config.asm.in config.asm) + +# Show include files in IDE +file(GLOB_RECURSE HERMIT_INCLUDES "*") +add_custom_target(hermit_includes_ide SOURCES ${HERMIT_INCLUDES}) + +# install generated config files when building libhermit for bootstrapping +install(FILES + ${GENERATED_CONFIG_DIR}/hermit/config.h + ${GENERATED_CONFIG_DIR}/hermit/config.asm + DESTINATION ${TARGET_ARCH}/include/hermit/ + COMPONENT bootstrap) diff --git a/include/hermit/config.asm.in b/include/hermit/config.asm.in new file mode 100644 index 000000000..15211359e --- /dev/null +++ b/include/hermit/config.asm.in @@ -0,0 +1,3 @@ +%define MAX_CORES @MAX_CORES@ +%define KERNEL_STACK_SIZE @KERNEL_STACK_SIZE@ +%define SAVE_FPU @SAVE_FPU@ diff --git a/include/hermit/config.h.in b/include/hermit/config.h.in old mode 100755 new mode 100644 index 56a39a7bb..2c9e9c9ec --- a/include/hermit/config.h.in +++ b/include/hermit/config.h.in @@ -1,51 +1,26 @@ -/* include/hermit/config.h.in. Generated from configure.ac by autoheader. */ +#cmakedefine MAX_CORES (@MAX_CORES@) +#cmakedefine MAX_TASKS (@MAX_TASKS@) +#cmakedefine MAX_ISLE (@MAX_ISLE@) +#cmakedefine KERNEL_STACK_SIZE (@KERNEL_STACK_SIZE@) +#cmakedefine DEFAULT_STACK_SIZE (@DEFAULT_STACK_SIZE@) +#cmakedefine PACKAGE_VERSION "@PACKAGE_VERSION@" +#cmakedefine MAX_FNAME (@MAX_FNAME@) -#undef MAX_CORES -#undef MAX_TASKS -#undef MAX_ISLE -#undef MAX_FNAME -#undef SAVE_FPU -#undef CONFIG_VGA -#undef VIDEO_MEM_ADDR +#cmakedefine SAVE_FPU + +#cmakedefine DYNAMIC_TICKS /* Define to use machine specific version of memcpy */ -#undef HAVE_ARCH_MEMCPY +#cmakedefine HAVE_ARCH_MEMCPY /* Define to use machine specific version of memset */ -#undef HAVE_ARCH_MEMSET +#cmakedefine HAVE_ARCH_MEMSET /* Define to use machine specific version of strcpy */ -#undef HAVE_ARCH_STRCPY +#cmakedefine HAVE_ARCH_STRCPY /* Define to use machine specific version of strlen */ -#undef HAVE_ARCH_STRLEN +#cmakedefine HAVE_ARCH_STRLEN /* Define to use machine specific version of strncpy */ -#undef HAVE_ARCH_STRNCPY - -/* Define the stack size of the idle task */ -#undef KERNEL_STACK_SIZE - -/* Define the default stack size */ -#undef DEFAULT_STACK_SIZE - -/* Define the maximum number of running tasks */ -#undef MAX_TASKS - -/* Define to the address where bug reports for this package should be sent. */ -#undef PACKAGE_BUGREPORT - -/* Define to the full name of this package. */ -#undef PACKAGE_NAME - -/* Define to the full name and version of this package. */ -#undef PACKAGE_STRING - -/* Define to the one symbol short name of this package. */ -#undef PACKAGE_TARNAME - -/* Define to the home page for this package. */ -#undef PACKAGE_URL - -/* Define to the version of this package. */ -#undef PACKAGE_VERSION +#cmakedefine HAVE_ARCH_STRNCPY diff --git a/include/hermit/malloc.h b/include/hermit/malloc.h index 75eeef9f1..fbdf4fa98 100644 --- a/include/hermit/malloc.h +++ b/include/hermit/malloc.h @@ -54,7 +54,7 @@ union buddy; /** @brief Buddy * * Every free memory block is stored in a linked list according to its size. - * We can use this free memory to store store this buddy_t union which represents + * We can use this free memory to store this buddy_t union which represents * this block (the buddy_t union is alligned to the front). * Therefore the address of the buddy_t union is equal with the address * of the underlying free memory block. @@ -82,4 +82,3 @@ void buddy_dump(void); #endif #endif - diff --git a/include/hermit/spinlock.h b/include/hermit/spinlock.h index fbfba6519..cd44b1116 100644 --- a/include/hermit/spinlock.h +++ b/include/hermit/spinlock.h @@ -38,6 +38,7 @@ #include #include #include +#include #include #include #include @@ -59,8 +60,8 @@ inline static int spinlock_init(spinlock_t* s) { if (BUILTIN_EXPECT(!s, 0)) return -EINVAL; - atomic_int32_set(&s->queue, 0); - atomic_int32_set(&s->dequeue, 1); + atomic_int64_set(&s->queue, 0); + atomic_int64_set(&s->dequeue, 1); s->owner = MAX_TASKS; s->counter = 0; @@ -68,7 +69,7 @@ inline static int spinlock_init(spinlock_t* s) { } /** @brief Destroy spinlock after use - * @return + * @return * - 0 on success * - -EINVAL (-22) on failure */ @@ -82,13 +83,13 @@ inline static int spinlock_destroy(spinlock_t* s) { return 0; } -/** @brief Lock spinlock at entry of critical section +/** @brief Lock spinlock at entry of critical section * @return * - 0 on success * - -EINVAL (-22) on failure */ inline static int spinlock_lock(spinlock_t* s) { - int32_t ticket; + int64_t ticket; task_t* curr_task; if (BUILTIN_EXPECT(!s, 0)) @@ -100,22 +101,18 @@ inline static int spinlock_lock(spinlock_t* s) { return 0; } -#if 1 - ticket = atomic_int32_inc(&s->queue); - while(atomic_int32_read(&s->dequeue) != ticket) { + ticket = atomic_int64_inc(&s->queue); + while(atomic_int64_read(&s->dequeue) != ticket) { PAUSE; } s->owner = curr_task->id; s->counter = 1; -#else - while( atomic_int32_test_and_set(&s->dequeue,0) ); -#endif return 0; } -/** @brief Unlock spinlock on exit of critical section - * @return +/** @brief Unlock spinlock on exit of critical section + * @return * - 0 on success * - -EINVAL (-22) on failure */ @@ -126,11 +123,7 @@ inline static int spinlock_unlock(spinlock_t* s) { s->counter--; if (!s->counter) { s->owner = MAX_TASKS; -#if 1 - atomic_int32_inc(&s->dequeue); -#else - atomic_int32_set(&s->dequeue,1); -#endif + atomic_int64_inc(&s->dequeue); } return 0; @@ -140,7 +133,7 @@ inline static int spinlock_unlock(spinlock_t* s) { * * Initialize each irqsave spinlock before use! * - * @return + * @return * - 0 on success * - -EINVAL (-22) on failure */ @@ -148,8 +141,8 @@ inline static int spinlock_irqsave_init(spinlock_irqsave_t* s) { if (BUILTIN_EXPECT(!s, 0)) return -EINVAL; - atomic_int32_set(&s->queue, 0); - atomic_int32_set(&s->dequeue, 1); + atomic_int64_set(&s->queue, 0); + atomic_int64_set(&s->dequeue, 1); s->flags = 0; s->coreid = (uint32_t)-1; s->counter = 0; @@ -158,7 +151,7 @@ inline static int spinlock_irqsave_init(spinlock_irqsave_t* s) { } /** @brief Destroy irqsave spinlock after use - * @return + * @return * - 0 on success * - -EINVAL (-22) on failure */ @@ -174,13 +167,13 @@ inline static int spinlock_irqsave_destroy(spinlock_irqsave_t* s) { } /** @brief Lock spinlock on entry of critical section and disable interrupts - * @return + * @return * - 0 on success * - -EINVAL (-22) on failure */ inline static int spinlock_irqsave_lock(spinlock_irqsave_t* s) { + int64_t ticket; uint8_t flags; - int32_t ticket; if (BUILTIN_EXPECT(!s, 0)) return -EINVAL; @@ -191,8 +184,8 @@ inline static int spinlock_irqsave_lock(spinlock_irqsave_t* s) { return 0; } - ticket = atomic_int32_inc(&s->queue); - while (atomic_int32_read(&s->dequeue) != ticket) { + ticket = atomic_int64_inc(&s->queue); + while (atomic_int64_read(&s->dequeue) != ticket) { PAUSE; } @@ -204,7 +197,7 @@ inline static int spinlock_irqsave_lock(spinlock_irqsave_t* s) { } /** @brief Unlock spinlock on exit of critical section and re-enable interrupts - * @return + * @return * - 0 on success * - -EINVAL (-22) on failure */ @@ -220,7 +213,7 @@ inline static int spinlock_irqsave_unlock(spinlock_irqsave_t* s) { s->coreid = (uint32_t) -1; s->flags = 0; - atomic_int32_inc(&s->dequeue); + atomic_int64_inc(&s->dequeue); irq_nested_enable(flags); } diff --git a/include/hermit/spinlock_types.h b/include/hermit/spinlock_types.h index ba61a6a2b..dd7873fe1 100644 --- a/include/hermit/spinlock_types.h +++ b/include/hermit/spinlock_types.h @@ -44,9 +44,9 @@ extern "C" { /** @brief Spinlock structure */ typedef struct spinlock { /// Internal queue - atomic_int32_t queue; - /// Internal dequeue - atomic_int32_t dequeue; + atomic_int64_t queue; + /// Internal dequeue + atomic_int64_t dequeue; /// Owner of this spinlock structure tid_t owner; /// Internal counter var @@ -55,9 +55,9 @@ typedef struct spinlock { typedef struct spinlock_irqsave { /// Internal queue - atomic_int32_t queue; + atomic_int64_t queue; /// Internal dequeue - atomic_int32_t dequeue; + atomic_int64_t dequeue; /// Core Id of the lock owner uint32_t coreid; /// Internal counter var diff --git a/include/hermit/stddef.h b/include/hermit/stddef.h index 03899cde7..d62cab7a1 100644 --- a/include/hermit/stddef.h +++ b/include/hermit/stddef.h @@ -42,10 +42,13 @@ extern "C" { #endif +// size of the whole application +extern const size_t image_size; + #define TIMER_FREQ 100 /* in HZ */ #define CLOCK_TICK_RATE 1193182 /* 8254 chip's internal oscillator frequency */ #define CACHE_LINE 64 -#define HEAP_START (PAGE_2M_FLOOR((size_t)&kernel_end) + 4*PAGE_SIZE) +#define HEAP_START (PAGE_2M_FLOOR((size_t)&kernel_start + image_size) + 4*PAGE_SIZE) #define HEAP_SIZE (1ULL << 32) #define KMSG_SIZE 0x1000 #define INT_SYSCALL 0x80 @@ -56,6 +59,13 @@ extern "C" { #define DYNAMIC_TICKS +#define UHYVE_PORT_WRITE 0x499 +#define UHYVE_PORT_OPEN 0x500 +#define UHYVE_PORT_CLOSE 0x501 +#define UHYVE_PORT_READ 0x502 +#define UHYVE_PORT_EXIT 0x503 +#define UHYVE_PORT_LSEEK 0x504 + #define BUILTIN_EXPECT(exp, b) __builtin_expect((exp), (b)) //#define BUILTIN_EXPECT(exp, b) (exp) #define NORETURN __attribute__((noreturn)) diff --git a/include/hermit/stdlib.h b/include/hermit/stdlib.h index 9468133bd..4eadb7e99 100644 --- a/include/hermit/stdlib.h +++ b/include/hermit/stdlib.h @@ -121,13 +121,17 @@ void page_free(void* addr, size_t sz); * * @return Long value of the parsed numerical string */ -long strtol(const char* str, char** endptr, int base); +long _strtol(const char* str, char** endptr, int base); + +#define strtol(str, endptr, base) _strtol((str), (endptr), (base)) /** @brief String to unsigned long * * @return Unsigned long value of the parsed numerical string */ -unsigned long strtoul(const char* nptr, char** endptr, int base); +unsigned long _strtoul(const char* nptr, char** endptr, int base); + +#define strtoul(nptr, endptr, base) _strtoul((nptr), (endptr), (base)) /** @brief ASCII to integer * @@ -137,7 +141,7 @@ unsigned long strtoul(const char* nptr, char** endptr, int base); */ static inline int atoi(const char *str) { - return (int)strtol(str, (char **)NULL, 10); + return (int)_strtol(str, (char **)NULL, 10); } #ifdef __cplusplus diff --git a/include/hermit/string.h b/include/hermit/string.h index a93cb8976..2624f6d98 100644 --- a/include/hermit/string.h +++ b/include/hermit/string.h @@ -41,39 +41,57 @@ extern "C" { #endif -#ifndef HAVE_ARCH_MEMCPY -void *memcpy(void *dest, const void *src, size_t count); +#if !HAVE_ARCH_MEMCPY +void *_memcpy(void *dest, const void *src, size_t count); + +#define memcpy(dest, src, count) _memcpy((dest), (src), (count)) #endif -#ifndef HAVE_ARCH_MEMSET -void *memset(void *dest, int val, size_t count); +#if !HAVE_ARCH_MEMSET +void *_memset(void *dest, int val, size_t count); + +#define memset(dest, val, count) _memset((dest), (val), (count)) #endif -#ifndef HAVE_ARCH_MEMCMP -int memcmp(const void *s1, const void *s2, size_t n); +#if !HAVE_ARCH_MEMCMP +int _memcmp(const void *s1, const void *s2, size_t n); + +#define memcmp(s1, s2, n) _memcmp((s1), (s2), (n)) #endif -#ifndef HAVE_ARCH_STRLEN -size_t strlen(const char *str); +#if !HAVE_ARCH_STRLEN +size_t _strlen(const char *str); + +#define strlen(str) _strlen((str)) #endif -#ifndef HAVE_ARCH_STRNCPY -char *strncpy(char *dest, const char *src, size_t n); +#if !HAVE_ARCH_STRNCPY +char *_strncpy(char *dest, const char *src, size_t n); + +#define strncpy(dest, src, n) _strncpy((dest), (src), (n)) #endif -#ifndef HAVE_ARCH_STRCPY -char *strcpy(char *dest, const char *src); +#if !HAVE_ARCH_STRCPY +char *_strcpy(char *dest, const char *src); + +#define strcpy(dest, src) _strcpy((dest), (src)) #endif -#ifndef HAVE_ARCH_STRCMP -int strcmp(const char *s1, const char *s2); +#if !HAVE_ARCH_STRCMP +int _strcmp(const char *s1, const char *s2); + +#define strcmp(s1, s2) _strcmp((s1), (s2)) #endif -#ifndef HAVE_ARCH_STRNCMP -int strncmp(const char *s1, const char *s2, size_t n); +#if !HAVE_ARCH_STRNCMP +int _strncmp(const char *s1, const char *s2, size_t n); + +#define strncmp(s1, s2, n) _strncmp((s1), (s2), (n)) #endif -char *strstr(const char *s, const char *find); +char *_strstr(const char *s, const char *find); + +#define strstr(s, find) _strstr((s), (find)) #ifdef __cplusplus } diff --git a/include/hermit/tasks.h b/include/hermit/tasks.h index 553021618..9842bd7aa 100644 --- a/include/hermit/tasks.h +++ b/include/hermit/tasks.h @@ -133,16 +133,6 @@ int create_kernel_task(tid_t* id, entry_point_t ep, void* args, uint8_t prio); */ int create_kernel_task_on_core(tid_t* id, entry_point_t ep, void* args, uint8_t prio, uint32_t core_id); - -/** @brief Create a thread local storage for the current task - * - * @return - * - 0 on success - * - -EONMEM on failure - */ -int init_tls(void); - - /** @brief Cleanup function for the task termination * * On termination, the task call this function to cleanup its address space. @@ -176,6 +166,14 @@ void reschedule(void); */ int wakeup_task(tid_t); +/** @brief Wake up a core_id + * + * Wakeup core to be sure that + * the core isn't in halt state + * + * @param core_id Specifies the core + */ +void wakeup_core(uint32_t core_id); /** @brief Block current task * @@ -196,7 +194,7 @@ void wait_for_task(void); * * @return * - address of the readyqueue - */ + */ void* get_readyqueue(void); /** @brief Get a process control block @@ -280,6 +278,10 @@ static inline void check_workqueues(void) check_workqueues_in_irqhandler(-1); } +/** @brief check if a proxy is available + */ +int is_proxy(void); + #ifdef __cplusplus } #endif diff --git a/include/hermit/time.h b/include/hermit/time.h index 5ae042a3a..5c32cd5fe 100644 --- a/include/hermit/time.h +++ b/include/hermit/time.h @@ -34,7 +34,7 @@ #ifndef __TIME_H__ #define __TIME_H__ -#include +#include #ifdef __cplusplus extern "C" { @@ -85,12 +85,6 @@ static inline void sleep(unsigned int sec) { timer_wait(sec*TIMER_FREQ); } */ static inline uint64_t get_uptime() { return (get_clock_tick() * 1000) / TIMER_FREQ; } -static inline int timer_deadline(uint32_t t) { return apic_timer_deadline(t); } - -static inline void timer_disable(void) { apic_disable_timer(); } - -static inline int timer_is_running(void) { return apic_timer_is_running(); } - #ifdef __cplusplus } #endif diff --git a/include/hermit/virtio_config.h b/include/hermit/virtio_config.h new file mode 100644 index 000000000..203ed7878 --- /dev/null +++ b/include/hermit/virtio_config.h @@ -0,0 +1,64 @@ +#ifndef __VIRTIO_CONFIG_H +#define __VIRTIO_CONFIG_H +/* This header, excluding the #ifdef __KERNEL__ part, is BSD licensed so + * anyone can use the definitions to implement compatible drivers/servers. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of IBM nor the names of its contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL IBM OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. */ + +/* Virtio devices use a standardized configuration space to define their + * features and pass configuration information, but each implementation can + * store and access that space differently. */ +#include + +/* Status byte for guest to report progress, and synchronize features. */ +/* We have seen device and processed generic fields (VIRTIO_CONFIG_F_VIRTIO) */ +#define VIRTIO_CONFIG_S_ACKNOWLEDGE 1 +/* We have found a driver for the device. */ +#define VIRTIO_CONFIG_S_DRIVER 2 +/* Driver has used its parts of the config, and is happy */ +#define VIRTIO_CONFIG_S_DRIVER_OK 4 +/* Driver has finished configuring features */ +#define VIRTIO_CONFIG_S_FEATURES_OK 8 +/* We've given up on this device. */ +#define VIRTIO_CONFIG_S_FAILED 0x80 + +/* Some virtio feature bits (currently bits 28 through 32) are reserved for the + * transport being used (eg. virtio_ring), the rest are per-device feature + * bits. */ +#define VIRTIO_TRANSPORT_F_START 28 +#define VIRTIO_TRANSPORT_F_END 33 + +#ifndef VIRTIO_CONFIG_NO_LEGACY +/* Do we get callbacks when the ring is completely used, even if we've + * suppressed them? */ +#define VIRTIO_F_NOTIFY_ON_EMPTY 24 + +/* Can the device handle any descriptor layout? */ +#define VIRTIO_F_ANY_LAYOUT 27 +#endif /* VIRTIO_CONFIG_NO_LEGACY */ + +/* v1.0 compliant. */ +#define VIRTIO_F_VERSION_1 32 + +#endif /* _LINUX_VIRTIO_CONFIG_H */ diff --git a/include/hermit/virtio_ids.h b/include/hermit/virtio_ids.h new file mode 100644 index 000000000..4ff9b038c --- /dev/null +++ b/include/hermit/virtio_ids.h @@ -0,0 +1,45 @@ +#ifndef __VIRTIO_IDS_H +#define __VIRTIO_IDS_H +/* + * Virtio IDs + * + * This header is BSD licensed so anyone can use the definitions to implement + * compatible drivers/servers. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of IBM nor the names of its contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL IBM OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. */ + +#define VIRTIO_ID_NET 1 /* virtio net */ +#define VIRTIO_ID_BLOCK 2 /* virtio block */ +#define VIRTIO_ID_CONSOLE 3 /* virtio console */ +#define VIRTIO_ID_RNG 4 /* virtio rng */ +#define VIRTIO_ID_BALLOON 5 /* virtio balloon */ +#define VIRTIO_ID_RPMSG 7 /* virtio remote processor messaging */ +#define VIRTIO_ID_SCSI 8 /* virtio scsi */ +#define VIRTIO_ID_9P 9 /* 9p virtio console */ +#define VIRTIO_ID_RPROC_SERIAL 11 /* virtio remoteproc serial link */ +#define VIRTIO_ID_CAIF 12 /* Virtio caif */ +#define VIRTIO_ID_GPU 16 /* virtio GPU */ +#define VIRTIO_ID_INPUT 18 /* virtio input */ + +#endif /* _LINUX_VIRTIO_IDS_H */ diff --git a/include/hermit/virtio_net.h b/include/hermit/virtio_net.h new file mode 100644 index 000000000..21d2cc52c --- /dev/null +++ b/include/hermit/virtio_net.h @@ -0,0 +1,245 @@ +#ifndef __VIRTIO_NET_H +#define __VIRTIO_NET_H +/* This header is BSD licensed so anyone can use the definitions to implement + * compatible drivers/servers. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of IBM nor the names of its contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL IBM OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. */ +#include +#include +#include +#include +#include + +/* The feature bitmap for virtio net */ +#define VIRTIO_NET_F_CSUM 0 /* Host handles pkts w/ partial csum */ +#define VIRTIO_NET_F_GUEST_CSUM 1 /* Guest handles pkts w/ partial csum */ +#define VIRTIO_NET_F_CTRL_GUEST_OFFLOADS 2 /* Dynamic offload configuration. */ +#define VIRTIO_NET_F_MAC 5 /* Host has given MAC address. */ +#define VIRTIO_NET_F_GUEST_TSO4 7 /* Guest can handle TSOv4 in. */ +#define VIRTIO_NET_F_GUEST_TSO6 8 /* Guest can handle TSOv6 in. */ +#define VIRTIO_NET_F_GUEST_ECN 9 /* Guest can handle TSO[6] w/ ECN in. */ +#define VIRTIO_NET_F_GUEST_UFO 10 /* Guest can handle UFO in. */ +#define VIRTIO_NET_F_HOST_TSO4 11 /* Host can handle TSOv4 in. */ +#define VIRTIO_NET_F_HOST_TSO6 12 /* Host can handle TSOv6 in. */ +#define VIRTIO_NET_F_HOST_ECN 13 /* Host can handle TSO[6] w/ ECN in. */ +#define VIRTIO_NET_F_HOST_UFO 14 /* Host can handle UFO in. */ +#define VIRTIO_NET_F_MRG_RXBUF 15 /* Host can merge receive buffers. */ +#define VIRTIO_NET_F_STATUS 16 /* virtio_net_config.status available */ +#define VIRTIO_NET_F_CTRL_VQ 17 /* Control channel available */ +#define VIRTIO_NET_F_CTRL_RX 18 /* Control channel RX mode support */ +#define VIRTIO_NET_F_CTRL_VLAN 19 /* Control channel VLAN filtering */ +#define VIRTIO_NET_F_CTRL_RX_EXTRA 20 /* Extra RX mode control support */ +#define VIRTIO_NET_F_GUEST_ANNOUNCE 21 /* Guest can announce device on the + * network */ +#define VIRTIO_NET_F_MQ 22 /* Device supports Receive Flow + * Steering */ +#define VIRTIO_NET_F_CTRL_MAC_ADDR 23 /* Set MAC address */ + +#ifndef VIRTIO_NET_NO_LEGACY +#define VIRTIO_NET_F_GSO 6 /* Host handles pkts w/ any GSO type */ +#endif /* VIRTIO_NET_NO_LEGACY */ + +#define VIRTIO_NET_S_LINK_UP 1 /* Link is up */ +#define VIRTIO_NET_S_ANNOUNCE 2 /* Announcement is needed */ + +struct virtio_net_config { + /* The config defining mac address (if VIRTIO_NET_F_MAC) */ + __u8 mac[ETHARP_HWADDR_LEN]; + /* See VIRTIO_NET_F_STATUS and VIRTIO_NET_S_* above */ + __u16 status; + /* Maximum number of each of transmit and receive queues; + * see VIRTIO_NET_F_MQ and VIRTIO_NET_CTRL_MQ. + * Legal values are between 1 and 0x8000 + */ + __u16 max_virtqueue_pairs; +} __attribute__((packed)); + +/* + * This header comes first in the scatter-gather list. If you don't + * specify GSO or CSUM features, you can simply ignore the header. + * + * This is bitwise-equivalent to the legacy struct virtio_net_hdr_mrg_rxbuf, + * only flattened. + */ +struct virtio_net_hdr_v1 { +#define VIRTIO_NET_HDR_F_NEEDS_CSUM 1 /* Use csum_start, csum_offset */ +#define VIRTIO_NET_HDR_F_DATA_VALID 2 /* Csum is valid */ + __u8 flags; +#define VIRTIO_NET_HDR_GSO_NONE 0 /* Not a GSO frame */ +#define VIRTIO_NET_HDR_GSO_TCPV4 1 /* GSO frame, IPv4 TCP (TSO) */ +#define VIRTIO_NET_HDR_GSO_UDP 3 /* GSO frame, IPv4 UDP (UFO) */ +#define VIRTIO_NET_HDR_GSO_TCPV6 4 /* GSO frame, IPv6 TCP */ +#define VIRTIO_NET_HDR_GSO_ECN 0x80 /* TCP has ECN set */ + __u8 gso_type; + __virtio16 hdr_len; /* Ethernet + IP + tcp/udp hdrs */ + __virtio16 gso_size; /* Bytes to append to hdr_len per frame */ + __virtio16 csum_start; /* Position to start checksumming from */ + __virtio16 csum_offset; /* Offset after that to place checksum */ + __virtio16 num_buffers; /* Number of merged rx buffers */ +}; + +#ifndef VIRTIO_NET_NO_LEGACY +/* This header comes first in the scatter-gather list. + * For legacy virtio, if VIRTIO_F_ANY_LAYOUT is not negotiated, it must + * be the first element of the scatter-gather list. If you don't + * specify GSO or CSUM features, you can simply ignore the header. */ +struct virtio_net_hdr { + /* See VIRTIO_NET_HDR_F_* */ + __u8 flags; + /* See VIRTIO_NET_HDR_GSO_* */ + __u8 gso_type; + __virtio16 hdr_len; /* Ethernet + IP + tcp/udp hdrs */ + __virtio16 gso_size; /* Bytes to append to hdr_len per frame */ + __virtio16 csum_start; /* Position to start checksumming from */ + __virtio16 csum_offset; /* Offset after that to place checksum */ +}; + +/* This is the version of the header to use when the MRG_RXBUF + * feature has been negotiated. */ +struct virtio_net_hdr_mrg_rxbuf { + struct virtio_net_hdr hdr; + __virtio16 num_buffers; /* Number of merged rx buffers */ +}; +#endif /* ...VIRTIO_NET_NO_LEGACY */ + +/* + * Control virtqueue data structures + * + * The control virtqueue expects a header in the first sg entry + * and an ack/status response in the last entry. Data for the + * command goes in between. + */ +struct virtio_net_ctrl_hdr { + __u8 class; + __u8 cmd; +} __attribute__((packed)); + +typedef __u8 virtio_net_ctrl_ack; + +#define VIRTIO_NET_OK 0 +#define VIRTIO_NET_ERR 1 + +/* + * Control the RX mode, ie. promisucous, allmulti, etc... + * All commands require an "out" sg entry containing a 1 byte + * state value, zero = disable, non-zero = enable. Commands + * 0 and 1 are supported with the VIRTIO_NET_F_CTRL_RX feature. + * Commands 2-5 are added with VIRTIO_NET_F_CTRL_RX_EXTRA. + */ +#define VIRTIO_NET_CTRL_RX 0 + #define VIRTIO_NET_CTRL_RX_PROMISC 0 + #define VIRTIO_NET_CTRL_RX_ALLMULTI 1 + #define VIRTIO_NET_CTRL_RX_ALLUNI 2 + #define VIRTIO_NET_CTRL_RX_NOMULTI 3 + #define VIRTIO_NET_CTRL_RX_NOUNI 4 + #define VIRTIO_NET_CTRL_RX_NOBCAST 5 + +/* + * Control the MAC + * + * The MAC filter table is managed by the hypervisor, the guest should + * assume the size is infinite. Filtering should be considered + * non-perfect, ie. based on hypervisor resources, the guest may + * received packets from sources not specified in the filter list. + * + * In addition to the class/cmd header, the TABLE_SET command requires + * two out scatterlists. Each contains a 4 byte count of entries followed + * by a concatenated byte stream of the ETH_ALEN MAC addresses. The + * first sg list contains unicast addresses, the second is for multicast. + * This functionality is present if the VIRTIO_NET_F_CTRL_RX feature + * is available. + * + * The ADDR_SET command requests one out scatterlist, it contains a + * 6 bytes MAC address. This functionality is present if the + * VIRTIO_NET_F_CTRL_MAC_ADDR feature is available. + */ +struct virtio_net_ctrl_mac { + __virtio32 entries; + __u8 macs[][ETHARP_HWADDR_LEN]; +} __attribute__((packed)); + +#define VIRTIO_NET_CTRL_MAC 1 + #define VIRTIO_NET_CTRL_MAC_TABLE_SET 0 + #define VIRTIO_NET_CTRL_MAC_ADDR_SET 1 + +/* + * Control VLAN filtering + * + * The VLAN filter table is controlled via a simple ADD/DEL interface. + * VLAN IDs not added may be filterd by the hypervisor. Del is the + * opposite of add. Both commands expect an out entry containing a 2 + * byte VLAN ID. VLAN filterting is available with the + * VIRTIO_NET_F_CTRL_VLAN feature bit. + */ +#define VIRTIO_NET_CTRL_VLAN 2 + #define VIRTIO_NET_CTRL_VLAN_ADD 0 + #define VIRTIO_NET_CTRL_VLAN_DEL 1 + +/* + * Control link announce acknowledgement + * + * The command VIRTIO_NET_CTRL_ANNOUNCE_ACK is used to indicate that + * driver has recevied the notification; device would clear the + * VIRTIO_NET_S_ANNOUNCE bit in the status field after it receives + * this command. + */ +#define VIRTIO_NET_CTRL_ANNOUNCE 3 + #define VIRTIO_NET_CTRL_ANNOUNCE_ACK 0 + +/* + * Control Receive Flow Steering + * + * The command VIRTIO_NET_CTRL_MQ_VQ_PAIRS_SET + * enables Receive Flow Steering, specifying the number of the transmit and + * receive queues that will be used. After the command is consumed and acked by + * the device, the device will not steer new packets on receive virtqueues + * other than specified nor read from transmit virtqueues other than specified. + * Accordingly, driver should not transmit new packets on virtqueues other than + * specified. + */ +struct virtio_net_ctrl_mq { + __virtio16 virtqueue_pairs; +}; + +#define VIRTIO_NET_CTRL_MQ 4 + #define VIRTIO_NET_CTRL_MQ_VQ_PAIRS_SET 0 + #define VIRTIO_NET_CTRL_MQ_VQ_PAIRS_MIN 1 + #define VIRTIO_NET_CTRL_MQ_VQ_PAIRS_MAX 0x8000 + +/* + * Control network offloads + * + * Reconfigures the network offloads that Guest can handle. + * + * Available with the VIRTIO_NET_F_CTRL_GUEST_OFFLOADS feature bit. + * + * Command data format matches the feature bit mask exactly. + * + * See VIRTIO_NET_F_GUEST_* for the list of offloads + * that can be enabled/disabled. + */ +#define VIRTIO_NET_CTRL_GUEST_OFFLOADS 5 +#define VIRTIO_NET_CTRL_GUEST_OFFLOADS_SET 0 + +#endif /* _LINUX_VIRTIO_NET_H */ diff --git a/include/hermit/virtio_pci.h b/include/hermit/virtio_pci.h new file mode 100644 index 000000000..a210bb328 --- /dev/null +++ b/include/hermit/virtio_pci.h @@ -0,0 +1,200 @@ +/* + * Virtio PCI driver + * + * This module allows virtio devices to be used over a virtual PCI device. + * This can be used with QEMU based VMMs like KVM or Xen. + * + * Copyright IBM Corp. 2007 + * + * Authors: + * Anthony Liguori + * + * This header is BSD licensed so anyone can use the definitions to implement + * compatible drivers/servers. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of IBM nor the names of its contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL IBM OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + */ + +#ifndef __VIRTIO_PCI_H +#define __VIRTIO_PCI_Hq + +#include +#include + +#ifndef VIRTIO_PCI_NO_LEGACY + +/* A 32-bit r/o bitmask of the features supported by the host */ +#define VIRTIO_PCI_HOST_FEATURES 0 + +/* A 32-bit r/w bitmask of features activated by the guest */ +#define VIRTIO_PCI_GUEST_FEATURES 4 + +/* A 32-bit r/w PFN for the currently selected queue */ +#define VIRTIO_PCI_QUEUE_PFN 8 + +/* A 16-bit r/o queue size for the currently selected queue */ +#define VIRTIO_PCI_QUEUE_NUM 12 + +/* A 16-bit r/w queue selector */ +#define VIRTIO_PCI_QUEUE_SEL 14 + +/* A 16-bit r/w queue notifier */ +#define VIRTIO_PCI_QUEUE_NOTIFY 16 + +/* An 8-bit device status register. */ +#define VIRTIO_PCI_STATUS 18 + +/* An 8-bit r/o interrupt status register. Reading the value will return the + * current contents of the ISR and will also clear it. This is effectively + * a read-and-acknowledge. */ +#define VIRTIO_PCI_ISR 19 + +/* MSI-X registers: only enabled if MSI-X is enabled. */ +/* A 16-bit vector for configuration changes. */ +#define VIRTIO_MSI_CONFIG_VECTOR 20 +/* A 16-bit vector for selected queue notifications. */ +#define VIRTIO_MSI_QUEUE_VECTOR 22 + +/* The remaining space is defined by each driver as the per-driver + * configuration space */ +#define VIRTIO_PCI_CONFIG_OFF(msix_enabled) ((msix_enabled) ? 24 : 20) +/* Deprecated: please use VIRTIO_PCI_CONFIG_OFF instead */ +#define VIRTIO_PCI_CONFIG(dev) VIRTIO_PCI_CONFIG_OFF((dev)->msix_enabled) + +/* Virtio ABI version, this must match exactly */ +#define VIRTIO_PCI_ABI_VERSION 0 + +/* How many bits to shift physical queue address written to QUEUE_PFN. + * 12 is historical, and due to x86 page size. */ +#define VIRTIO_PCI_QUEUE_ADDR_SHIFT 12 + +/* The alignment to use between consumer and producer parts of vring. + * x86 pagesize again. */ +#define VIRTIO_PCI_VRING_ALIGN 4096 + +#endif /* VIRTIO_PCI_NO_LEGACY */ + +/* The bit of the ISR which indicates a device configuration change. */ +#define VIRTIO_PCI_ISR_CONFIG 0x2 +/* Vector value used to disable MSI for queue */ +#define VIRTIO_MSI_NO_VECTOR 0xffff + +#ifndef VIRTIO_PCI_NO_MODERN + +/* IDs for different capabilities. Must all exist. */ + +/* Common configuration */ +#define VIRTIO_PCI_CAP_COMMON_CFG 1 +/* Notifications */ +#define VIRTIO_PCI_CAP_NOTIFY_CFG 2 +/* ISR access */ +#define VIRTIO_PCI_CAP_ISR_CFG 3 +/* Device specific configuration */ +#define VIRTIO_PCI_CAP_DEVICE_CFG 4 +/* PCI configuration access */ +#define VIRTIO_PCI_CAP_PCI_CFG 5 + +/* This is the PCI capability header: */ +struct virtio_pci_cap { + __u8 cap_vndr; /* Generic PCI field: PCI_CAP_ID_VNDR */ + __u8 cap_next; /* Generic PCI field: next ptr. */ + __u8 cap_len; /* Generic PCI field: capability length */ + __u8 cfg_type; /* Identifies the structure. */ + __u8 bar; /* Where to find it. */ + __u8 padding[3]; /* Pad to full dword. */ + __le32 offset; /* Offset within bar. */ + __le32 length; /* Length of the structure, in bytes. */ +}; + +struct virtio_pci_notify_cap { + struct virtio_pci_cap cap; + __le32 notify_off_multiplier; /* Multiplier for queue_notify_off. */ +}; + +/* Fields in VIRTIO_PCI_CAP_COMMON_CFG: */ +struct virtio_pci_common_cfg { + /* About the whole device. */ + __le32 device_feature_select; /* read-write */ + __le32 device_feature; /* read-only */ + __le32 guest_feature_select; /* read-write */ + __le32 guest_feature; /* read-write */ + __le16 msix_config; /* read-write */ + __le16 num_queues; /* read-only */ + __u8 device_status; /* read-write */ + __u8 config_generation; /* read-only */ + + /* About a specific virtqueue. */ + __le16 queue_select; /* read-write */ + __le16 queue_size; /* read-write, power of 2. */ + __le16 queue_msix_vector; /* read-write */ + __le16 queue_enable; /* read-write */ + __le16 queue_notify_off; /* read-only */ + __le32 queue_desc_lo; /* read-write */ + __le32 queue_desc_hi; /* read-write */ + __le32 queue_avail_lo; /* read-write */ + __le32 queue_avail_hi; /* read-write */ + __le32 queue_used_lo; /* read-write */ + __le32 queue_used_hi; /* read-write */ +}; + +/* Fields in VIRTIO_PCI_CAP_PCI_CFG: */ +struct virtio_pci_cfg_cap { + struct virtio_pci_cap cap; + __u8 pci_cfg_data[4]; /* Data for BAR access. */ +}; + +/* Macro versions of offsets for the Old Timers! */ +#define VIRTIO_PCI_CAP_VNDR 0 +#define VIRTIO_PCI_CAP_NEXT 1 +#define VIRTIO_PCI_CAP_LEN 2 +#define VIRTIO_PCI_CAP_CFG_TYPE 3 +#define VIRTIO_PCI_CAP_BAR 4 +#define VIRTIO_PCI_CAP_OFFSET 8 +#define VIRTIO_PCI_CAP_LENGTH 12 + +#define VIRTIO_PCI_NOTIFY_CAP_MULT 16 + +#define VIRTIO_PCI_COMMON_DFSELECT 0 +#define VIRTIO_PCI_COMMON_DF 4 +#define VIRTIO_PCI_COMMON_GFSELECT 8 +#define VIRTIO_PCI_COMMON_GF 12 +#define VIRTIO_PCI_COMMON_MSIX 16 +#define VIRTIO_PCI_COMMON_NUMQ 18 +#define VIRTIO_PCI_COMMON_STATUS 20 +#define VIRTIO_PCI_COMMON_CFGGENERATION 21 +#define VIRTIO_PCI_COMMON_Q_SELECT 22 +#define VIRTIO_PCI_COMMON_Q_SIZE 24 +#define VIRTIO_PCI_COMMON_Q_MSIX 26 +#define VIRTIO_PCI_COMMON_Q_ENABLE 28 +#define VIRTIO_PCI_COMMON_Q_NOFF 30 +#define VIRTIO_PCI_COMMON_Q_DESCLO 32 +#define VIRTIO_PCI_COMMON_Q_DESCHI 36 +#define VIRTIO_PCI_COMMON_Q_AVAILLO 40 +#define VIRTIO_PCI_COMMON_Q_AVAILHI 44 +#define VIRTIO_PCI_COMMON_Q_USEDLO 48 +#define VIRTIO_PCI_COMMON_Q_USEDHI 52 + +#endif /* VIRTIO_PCI_NO_MODERN */ + +#endif diff --git a/include/hermit/virtio_ring.h b/include/hermit/virtio_ring.h new file mode 100644 index 000000000..7680935df --- /dev/null +++ b/include/hermit/virtio_ring.h @@ -0,0 +1,171 @@ +#ifndef __VIRTIO_RING_H +#define __VIRTIO_RING_H +/* An interface for efficient virtio implementation, currently for use by KVM + * and lguest, but hopefully others soon. Do NOT change this since it will + * break existing servers and clients. + * + * This header is BSD licensed so anyone can use the definitions to implement + * compatible drivers/servers. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of IBM nor the names of its contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL IBM OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * Copyright Rusty Russell IBM Corporation 2007. */ +#include +#include + +/* This marks a buffer as continuing via the next field. */ +#define VRING_DESC_F_NEXT 1 +/* This marks a buffer as write-only (otherwise read-only). */ +#define VRING_DESC_F_WRITE 2 +/* This means the buffer contains a list of buffer descriptors. */ +#define VRING_DESC_F_INDIRECT 4 + +/* The Host uses this in used->flags to advise the Guest: don't kick me when + * you add a buffer. It's unreliable, so it's simply an optimization. Guest + * will still kick if it's out of buffers. */ +#define VRING_USED_F_NO_NOTIFY 1 +/* The Guest uses this in avail->flags to advise the Host: don't interrupt me + * when you consume a buffer. It's unreliable, so it's simply an + * optimization. */ +#define VRING_AVAIL_F_NO_INTERRUPT 1 + +/* We support indirect buffer descriptors */ +#define VIRTIO_RING_F_INDIRECT_DESC 28 + +/* The Guest publishes the used index for which it expects an interrupt + * at the end of the avail ring. Host should ignore the avail->flags field. */ +/* The Host publishes the avail index for which it expects a kick + * at the end of the used ring. Guest should ignore the used->flags field. */ +#define VIRTIO_RING_F_EVENT_IDX 29 + +/* Virtio ring descriptors: 16 bytes. These can chain together via "next". */ +struct vring_desc { + /* Address (guest-physical). */ + __virtio64 addr; + /* Length. */ + __virtio32 len; + /* The flags as indicated above. */ + __virtio16 flags; + /* We chain unused descriptors via this, too */ + __virtio16 next; +}; + +struct vring_avail { + __virtio16 flags; + __virtio16 idx; + __virtio16 ring[]; +}; + +/* u32 is used here for ids for padding reasons. */ +struct vring_used_elem { + /* Index of start of used descriptor chain. */ + __virtio32 id; + /* Total length of the descriptor chain which was used (written to) */ + __virtio32 len; +}; + +struct vring_used { + __virtio16 flags; + __virtio16 idx; + struct vring_used_elem ring[]; +}; + +struct vring { + unsigned int num; + + struct vring_desc *desc; + + struct vring_avail *avail; + + struct vring_used *used; +}; + +/* Alignment requirements for vring elements. + * When using pre-virtio 1.0 layout, these fall out naturally. + */ +#define VRING_AVAIL_ALIGN_SIZE 2 +#define VRING_USED_ALIGN_SIZE 4 +#define VRING_DESC_ALIGN_SIZE 16 + +/* The standard layout for the ring is a continuous chunk of memory which looks + * like this. We assume num is a power of 2. + * + * struct vring + * { + * // The actual descriptors (16 bytes each) + * struct vring_desc desc[num]; + * + * // A ring of available descriptor heads with free-running index. + * __virtio16 avail_flags; + * __virtio16 avail_idx; + * __virtio16 available[num]; + * __virtio16 used_event_idx; + * + * // Padding to the next align boundary. + * char pad[]; + * + * // A ring of used descriptor heads with free-running index. + * __virtio16 used_flags; + * __virtio16 used_idx; + * struct vring_used_elem used[num]; + * __virtio16 avail_event_idx; + * }; + */ +/* We publish the used event index at the end of the available ring, and vice + * versa. They are at the end for backwards compatibility. */ +#define vring_used_event(vr) ((vr)->avail->ring[(vr)->num]) +#define vring_avail_event(vr) (*(__virtio16 *)&(vr)->used->ring[(vr)->num]) + +static __inline__ void vring_init(struct vring *vr, unsigned int num, void *p, + unsigned long align) +{ + vr->num = num; + vr->desc = p; + vr->avail = p + num*sizeof(struct vring_desc); + vr->used = (void *)(((uintptr_t)&vr->avail->ring[num] + sizeof(__virtio16) + + align-1) & ~(align - 1)); +} + +static __inline__ unsigned vring_size(unsigned int num, unsigned long align) +{ + return ((sizeof(struct vring_desc) * num + sizeof(__virtio16) * (3 + num) + + align - 1) & ~(align - 1)) + + sizeof(__virtio16) * 3 + sizeof(struct vring_used_elem) * num; +} + +/* The following is used with USED_EVENT_IDX and AVAIL_EVENT_IDX */ +/* Assuming a given event_idx value from the other side, if + * we have just incremented index from old to new_idx, + * should we trigger an event? */ +static __inline__ int vring_need_event(__u16 event_idx, __u16 new_idx, __u16 old) +{ + /* Note: Xen has similar logic for notification hold-off + * in include/xen/interface/io/ring.h with req_event and req_prod + * corresponding to event_idx + 1 and new_idx respectively. + * Note also that req_event and req_prod in Xen start at 1, + * event indexes in virtio start at 0. */ + return (__u16)(new_idx - event_idx - 1) < (__u16)(new_idx - old); +} + +#endif /* _LINUX_VIRTIO_RING_H */ diff --git a/include/hermit/virtio_types.h b/include/hermit/virtio_types.h new file mode 100644 index 000000000..4792dea96 --- /dev/null +++ b/include/hermit/virtio_types.h @@ -0,0 +1,57 @@ +#ifndef __VIRTIO_TYPES_H +#define __VIRTIO_TYPES_H +/* Type definitions for virtio implementations. + * + * This header is BSD licensed so anyone can use the definitions to implement + * compatible drivers/servers. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions + * are met: + * 1. Redistributions of source code must retain the above copyright + * notice, this list of conditions and the following disclaimer. + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * 3. Neither the name of IBM nor the names of its contributors + * may be used to endorse or promote products derived from this software + * without specific prior written permission. + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS ``AS IS'' AND + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL IBM OR CONTRIBUTORS BE LIABLE + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF + * SUCH DAMAGE. + * + * Copyright (C) 2014 Red Hat, Inc. + * Author: Michael S. Tsirkin + */ +#include + +/* + * __virtio{16,32,64} have the following meaning: + * - __u{16,32,64} for virtio devices in legacy mode, accessed in native endian + * - __le{16,32,64} for standard-compliant virtio devices + */ + +typedef uint8_t __u8; +typedef uint16_t __u16; +typedef uint32_t __u32; +typedef uint64_t __u64; +typedef size_t uintptr_t; + +#define __bitwise__ + +typedef __u16 __bitwise__ __virtio16; +typedef __u32 __bitwise__ __virtio32; +typedef __u64 __bitwise__ __virtio64; +typedef __u32 __bitwise__ __le32; +typedef __u16 __bitwise__ __le16; +typedef __u8 __bitwise__ __le8; + +#endif /* __VIRTIO_TYPES_H */ diff --git a/include/hermit/vma.h b/include/hermit/vma.h index fb17c5975..5e465112b 100644 --- a/include/hermit/vma.h +++ b/include/hermit/vma.h @@ -87,7 +87,7 @@ typedef struct vma { /** @brief Initalize the kernelspace VMA list * * Reserves several system-relevant virtual memory regions: - * - The kernel (kernel_start - kernel_end) + * - The kernel (image_size) * - Init Ramdisk * * @return @@ -96,7 +96,17 @@ typedef struct vma { */ int vma_init(void); -/** @brief Add a new virtual memory area to the list of VMAs +/** @brief Initalize the kernelspace VMA list + * + * Reserves several architecture-relevant virtual memory regions + * + * @return + * - 0 on success + * - <0 on failure + */ +int vma_arch_init(void); + +/** @brief Add a new virtual memory area to the list of VMAs * * @param start Start address of the new area * @param end End address of the new area diff --git a/install-sh b/install-sh deleted file mode 100755 index 0b0fdcbba..000000000 --- a/install-sh +++ /dev/null @@ -1,501 +0,0 @@ -#!/bin/sh -# install - install a program, script, or datafile - -scriptversion=2013-12-25.23; # UTC - -# This originates from X11R5 (mit/util/scripts/install.sh), which was -# later released in X11R6 (xc/config/util/install.sh) with the -# following copyright and license. -# -# Copyright (C) 1994 X Consortium -# -# Permission is hereby granted, free of charge, to any person obtaining a copy -# of this software and associated documentation files (the "Software"), to -# deal in the Software without restriction, including without limitation the -# rights to use, copy, modify, merge, publish, distribute, sublicense, and/or -# sell copies of the Software, and to permit persons to whom the Software is -# furnished to do so, subject to the following conditions: -# -# The above copyright notice and this permission notice shall be included in -# all copies or substantial portions of the Software. -# -# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR -# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, -# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE -# X CONSORTIUM BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN -# AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNEC- -# TION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. -# -# Except as contained in this notice, the name of the X Consortium shall not -# be used in advertising or otherwise to promote the sale, use or other deal- -# ings in this Software without prior written authorization from the X Consor- -# tium. -# -# -# FSF changes to this file are in the public domain. -# -# Calling this script install-sh is preferred over install.sh, to prevent -# 'make' implicit rules from creating a file called install from it -# when there is no Makefile. -# -# This script is compatible with the BSD install script, but was written -# from scratch. - -tab=' ' -nl=' -' -IFS=" $tab$nl" - -# Set DOITPROG to "echo" to test this script. - -doit=${DOITPROG-} -doit_exec=${doit:-exec} - -# Put in absolute file names if you don't have them in your path; -# or use environment vars. - -chgrpprog=${CHGRPPROG-chgrp} -chmodprog=${CHMODPROG-chmod} -chownprog=${CHOWNPROG-chown} -cmpprog=${CMPPROG-cmp} -cpprog=${CPPROG-cp} -mkdirprog=${MKDIRPROG-mkdir} -mvprog=${MVPROG-mv} -rmprog=${RMPROG-rm} -stripprog=${STRIPPROG-strip} - -posix_mkdir= - -# Desired mode of installed file. -mode=0755 - -chgrpcmd= -chmodcmd=$chmodprog -chowncmd= -mvcmd=$mvprog -rmcmd="$rmprog -f" -stripcmd= - -src= -dst= -dir_arg= -dst_arg= - -copy_on_change=false -is_target_a_directory=possibly - -usage="\ -Usage: $0 [OPTION]... [-T] SRCFILE DSTFILE - or: $0 [OPTION]... SRCFILES... DIRECTORY - or: $0 [OPTION]... -t DIRECTORY SRCFILES... - or: $0 [OPTION]... -d DIRECTORIES... - -In the 1st form, copy SRCFILE to DSTFILE. -In the 2nd and 3rd, copy all SRCFILES to DIRECTORY. -In the 4th, create DIRECTORIES. - -Options: - --help display this help and exit. - --version display version info and exit. - - -c (ignored) - -C install only if different (preserve the last data modification time) - -d create directories instead of installing files. - -g GROUP $chgrpprog installed files to GROUP. - -m MODE $chmodprog installed files to MODE. - -o USER $chownprog installed files to USER. - -s $stripprog installed files. - -t DIRECTORY install into DIRECTORY. - -T report an error if DSTFILE is a directory. - -Environment variables override the default commands: - CHGRPPROG CHMODPROG CHOWNPROG CMPPROG CPPROG MKDIRPROG MVPROG - RMPROG STRIPPROG -" - -while test $# -ne 0; do - case $1 in - -c) ;; - - -C) copy_on_change=true;; - - -d) dir_arg=true;; - - -g) chgrpcmd="$chgrpprog $2" - shift;; - - --help) echo "$usage"; exit $?;; - - -m) mode=$2 - case $mode in - *' '* | *"$tab"* | *"$nl"* | *'*'* | *'?'* | *'['*) - echo "$0: invalid mode: $mode" >&2 - exit 1;; - esac - shift;; - - -o) chowncmd="$chownprog $2" - shift;; - - -s) stripcmd=$stripprog;; - - -t) - is_target_a_directory=always - dst_arg=$2 - # Protect names problematic for 'test' and other utilities. - case $dst_arg in - -* | [=\(\)!]) dst_arg=./$dst_arg;; - esac - shift;; - - -T) is_target_a_directory=never;; - - --version) echo "$0 $scriptversion"; exit $?;; - - --) shift - break;; - - -*) echo "$0: invalid option: $1" >&2 - exit 1;; - - *) break;; - esac - shift -done - -# We allow the use of options -d and -T together, by making -d -# take the precedence; this is for compatibility with GNU install. - -if test -n "$dir_arg"; then - if test -n "$dst_arg"; then - echo "$0: target directory not allowed when installing a directory." >&2 - exit 1 - fi -fi - -if test $# -ne 0 && test -z "$dir_arg$dst_arg"; then - # When -d is used, all remaining arguments are directories to create. - # When -t is used, the destination is already specified. - # Otherwise, the last argument is the destination. Remove it from $@. - for arg - do - if test -n "$dst_arg"; then - # $@ is not empty: it contains at least $arg. - set fnord "$@" "$dst_arg" - shift # fnord - fi - shift # arg - dst_arg=$arg - # Protect names problematic for 'test' and other utilities. - case $dst_arg in - -* | [=\(\)!]) dst_arg=./$dst_arg;; - esac - done -fi - -if test $# -eq 0; then - if test -z "$dir_arg"; then - echo "$0: no input file specified." >&2 - exit 1 - fi - # It's OK to call 'install-sh -d' without argument. - # This can happen when creating conditional directories. - exit 0 -fi - -if test -z "$dir_arg"; then - if test $# -gt 1 || test "$is_target_a_directory" = always; then - if test ! -d "$dst_arg"; then - echo "$0: $dst_arg: Is not a directory." >&2 - exit 1 - fi - fi -fi - -if test -z "$dir_arg"; then - do_exit='(exit $ret); exit $ret' - trap "ret=129; $do_exit" 1 - trap "ret=130; $do_exit" 2 - trap "ret=141; $do_exit" 13 - trap "ret=143; $do_exit" 15 - - # Set umask so as not to create temps with too-generous modes. - # However, 'strip' requires both read and write access to temps. - case $mode in - # Optimize common cases. - *644) cp_umask=133;; - *755) cp_umask=22;; - - *[0-7]) - if test -z "$stripcmd"; then - u_plus_rw= - else - u_plus_rw='% 200' - fi - cp_umask=`expr '(' 777 - $mode % 1000 ')' $u_plus_rw`;; - *) - if test -z "$stripcmd"; then - u_plus_rw= - else - u_plus_rw=,u+rw - fi - cp_umask=$mode$u_plus_rw;; - esac -fi - -for src -do - # Protect names problematic for 'test' and other utilities. - case $src in - -* | [=\(\)!]) src=./$src;; - esac - - if test -n "$dir_arg"; then - dst=$src - dstdir=$dst - test -d "$dstdir" - dstdir_status=$? - else - - # Waiting for this to be detected by the "$cpprog $src $dsttmp" command - # might cause directories to be created, which would be especially bad - # if $src (and thus $dsttmp) contains '*'. - if test ! -f "$src" && test ! -d "$src"; then - echo "$0: $src does not exist." >&2 - exit 1 - fi - - if test -z "$dst_arg"; then - echo "$0: no destination specified." >&2 - exit 1 - fi - dst=$dst_arg - - # If destination is a directory, append the input filename; won't work - # if double slashes aren't ignored. - if test -d "$dst"; then - if test "$is_target_a_directory" = never; then - echo "$0: $dst_arg: Is a directory" >&2 - exit 1 - fi - dstdir=$dst - dst=$dstdir/`basename "$src"` - dstdir_status=0 - else - dstdir=`dirname "$dst"` - test -d "$dstdir" - dstdir_status=$? - fi - fi - - obsolete_mkdir_used=false - - if test $dstdir_status != 0; then - case $posix_mkdir in - '') - # Create intermediate dirs using mode 755 as modified by the umask. - # This is like FreeBSD 'install' as of 1997-10-28. - umask=`umask` - case $stripcmd.$umask in - # Optimize common cases. - *[2367][2367]) mkdir_umask=$umask;; - .*0[02][02] | .[02][02] | .[02]) mkdir_umask=22;; - - *[0-7]) - mkdir_umask=`expr $umask + 22 \ - - $umask % 100 % 40 + $umask % 20 \ - - $umask % 10 % 4 + $umask % 2 - `;; - *) mkdir_umask=$umask,go-w;; - esac - - # With -d, create the new directory with the user-specified mode. - # Otherwise, rely on $mkdir_umask. - if test -n "$dir_arg"; then - mkdir_mode=-m$mode - else - mkdir_mode= - fi - - posix_mkdir=false - case $umask in - *[123567][0-7][0-7]) - # POSIX mkdir -p sets u+wx bits regardless of umask, which - # is incompatible with FreeBSD 'install' when (umask & 300) != 0. - ;; - *) - tmpdir=${TMPDIR-/tmp}/ins$RANDOM-$$ - trap 'ret=$?; rmdir "$tmpdir/d" "$tmpdir" 2>/dev/null; exit $ret' 0 - - if (umask $mkdir_umask && - exec $mkdirprog $mkdir_mode -p -- "$tmpdir/d") >/dev/null 2>&1 - then - if test -z "$dir_arg" || { - # Check for POSIX incompatibilities with -m. - # HP-UX 11.23 and IRIX 6.5 mkdir -m -p sets group- or - # other-writable bit of parent directory when it shouldn't. - # FreeBSD 6.1 mkdir -m -p sets mode of existing directory. - ls_ld_tmpdir=`ls -ld "$tmpdir"` - case $ls_ld_tmpdir in - d????-?r-*) different_mode=700;; - d????-?--*) different_mode=755;; - *) false;; - esac && - $mkdirprog -m$different_mode -p -- "$tmpdir" && { - ls_ld_tmpdir_1=`ls -ld "$tmpdir"` - test "$ls_ld_tmpdir" = "$ls_ld_tmpdir_1" - } - } - then posix_mkdir=: - fi - rmdir "$tmpdir/d" "$tmpdir" - else - # Remove any dirs left behind by ancient mkdir implementations. - rmdir ./$mkdir_mode ./-p ./-- 2>/dev/null - fi - trap '' 0;; - esac;; - esac - - if - $posix_mkdir && ( - umask $mkdir_umask && - $doit_exec $mkdirprog $mkdir_mode -p -- "$dstdir" - ) - then : - else - - # The umask is ridiculous, or mkdir does not conform to POSIX, - # or it failed possibly due to a race condition. Create the - # directory the slow way, step by step, checking for races as we go. - - case $dstdir in - /*) prefix='/';; - [-=\(\)!]*) prefix='./';; - *) prefix='';; - esac - - oIFS=$IFS - IFS=/ - set -f - set fnord $dstdir - shift - set +f - IFS=$oIFS - - prefixes= - - for d - do - test X"$d" = X && continue - - prefix=$prefix$d - if test -d "$prefix"; then - prefixes= - else - if $posix_mkdir; then - (umask=$mkdir_umask && - $doit_exec $mkdirprog $mkdir_mode -p -- "$dstdir") && break - # Don't fail if two instances are running concurrently. - test -d "$prefix" || exit 1 - else - case $prefix in - *\'*) qprefix=`echo "$prefix" | sed "s/'/'\\\\\\\\''/g"`;; - *) qprefix=$prefix;; - esac - prefixes="$prefixes '$qprefix'" - fi - fi - prefix=$prefix/ - done - - if test -n "$prefixes"; then - # Don't fail if two instances are running concurrently. - (umask $mkdir_umask && - eval "\$doit_exec \$mkdirprog $prefixes") || - test -d "$dstdir" || exit 1 - obsolete_mkdir_used=true - fi - fi - fi - - if test -n "$dir_arg"; then - { test -z "$chowncmd" || $doit $chowncmd "$dst"; } && - { test -z "$chgrpcmd" || $doit $chgrpcmd "$dst"; } && - { test "$obsolete_mkdir_used$chowncmd$chgrpcmd" = false || - test -z "$chmodcmd" || $doit $chmodcmd $mode "$dst"; } || exit 1 - else - - # Make a couple of temp file names in the proper directory. - dsttmp=$dstdir/_inst.$$_ - rmtmp=$dstdir/_rm.$$_ - - # Trap to clean up those temp files at exit. - trap 'ret=$?; rm -f "$dsttmp" "$rmtmp" && exit $ret' 0 - - # Copy the file name to the temp name. - (umask $cp_umask && $doit_exec $cpprog "$src" "$dsttmp") && - - # and set any options; do chmod last to preserve setuid bits. - # - # If any of these fail, we abort the whole thing. If we want to - # ignore errors from any of these, just make sure not to ignore - # errors from the above "$doit $cpprog $src $dsttmp" command. - # - { test -z "$chowncmd" || $doit $chowncmd "$dsttmp"; } && - { test -z "$chgrpcmd" || $doit $chgrpcmd "$dsttmp"; } && - { test -z "$stripcmd" || $doit $stripcmd "$dsttmp"; } && - { test -z "$chmodcmd" || $doit $chmodcmd $mode "$dsttmp"; } && - - # If -C, don't bother to copy if it wouldn't change the file. - if $copy_on_change && - old=`LC_ALL=C ls -dlL "$dst" 2>/dev/null` && - new=`LC_ALL=C ls -dlL "$dsttmp" 2>/dev/null` && - set -f && - set X $old && old=:$2:$4:$5:$6 && - set X $new && new=:$2:$4:$5:$6 && - set +f && - test "$old" = "$new" && - $cmpprog "$dst" "$dsttmp" >/dev/null 2>&1 - then - rm -f "$dsttmp" - else - # Rename the file to the real destination. - $doit $mvcmd -f "$dsttmp" "$dst" 2>/dev/null || - - # The rename failed, perhaps because mv can't rename something else - # to itself, or perhaps because mv is so ancient that it does not - # support -f. - { - # Now remove or move aside any old file at destination location. - # We try this two ways since rm can't unlink itself on some - # systems and the destination file might be busy for other - # reasons. In this case, the final cleanup might fail but the new - # file should still install successfully. - { - test ! -f "$dst" || - $doit $rmcmd -f "$dst" 2>/dev/null || - { $doit $mvcmd -f "$dst" "$rmtmp" 2>/dev/null && - { $doit $rmcmd -f "$rmtmp" 2>/dev/null; :; } - } || - { echo "$0: cannot unlink or rename $dst" >&2 - (exit 1); exit 1 - } - } && - - # Now rename the file to the real destination. - $doit $mvcmd "$dsttmp" "$dst" - } - fi || exit 1 - - trap '' 0 - fi -done - -# Local variables: -# eval: (add-hook 'write-file-hooks 'time-stamp) -# time-stamp-start: "scriptversion=" -# time-stamp-format: "%:y-%02m-%02d.%02H" -# time-stamp-time-zone: "UTC" -# time-stamp-end: "; # UTC" -# End: diff --git a/kernel/Makefile b/kernel/Makefile deleted file mode 100644 index 524b2e44c..000000000 --- a/kernel/Makefile +++ /dev/null @@ -1,4 +0,0 @@ -C_source := main.c tasks.c syscall.c timer.c signal.c -MODULE := kernel - -include $(TOPDIR)/Makefile.inc diff --git a/kernel/main.c b/kernel/main.c index 2fcd9bce3..80cef7269 100644 --- a/kernel/main.c +++ b/kernel/main.c @@ -40,6 +40,7 @@ #include #include #include +#include #include #include @@ -58,6 +59,7 @@ #include #include #include +#include #define HERMIT_PORT 0x494E #define HERMIT_MAGIC 0x7E317 @@ -70,7 +72,6 @@ static const int sobufsize = 131072; * maintaining a value, rather their address is their value. */ extern const void kernel_start; -extern const void kernel_end; extern const void hbss_start; extern const void tls_start; extern const void tls_end; @@ -119,7 +120,7 @@ static int hermit_init(void) size_t sz = (size_t) &percore_end0 - (size_t) &percore_start; // initialize .kbss sections - memset((void*)&hbss_start, 0x00, ((size_t) &kernel_end - (size_t) &hbss_start)); + memset((void*)&hbss_start, 0x00, (size_t) &__bss_start - (size_t) &hbss_start); // initialize .percore section => copy first section to all other sections for(i=1; i Therefore, we are able to use ip_input instead of tcpip_input */ if ((err = netifapi_netif_add(&default_netif, ip_2_ip4(&ipaddr), ip_2_ip4(&netmask), ip_2_ip4(&gw), NULL, mmnif_init, ip_input)) != ERR_OK) -#endif { LOG_ERROR("Unable to add the intra network interface: err = %d\n", err); return -ENODEV; @@ -217,6 +216,8 @@ static int init_netifs(void) /* Note: Our drivers guarantee that the input function will be called in the context of the tcpip thread. * => Therefore, we are able to use ethernet_input instead of tcpip_input */ + if ((err = netifapi_netif_add(&default_netif, ip_2_ip4(&ipaddr), ip_2_ip4(&netmask), ip_2_ip4(&gw), NULL, vioif_init, ethernet_input)) == ERR_OK) + goto success; if ((err = netifapi_netif_add(&default_netif, ip_2_ip4(&ipaddr), ip_2_ip4(&netmask), ip_2_ip4(&gw), NULL, rtl8139if_init, ethernet_input)) == ERR_OK) goto success; if ((err = netifapi_netif_add(&default_netif, ip_2_ip4(&ipaddr), ip_2_ip4(&netmask), ip_2_ip4(&gw), NULL, e1000if_init, ethernet_input)) == ERR_OK) @@ -234,20 +235,17 @@ success: netifapi_dhcp_start(&default_netif); int mscnt = 0; + int ip_counter = 0; /* wait for ip address */ - while(!ip_2_ip4(&default_netif.ip_addr)->addr) { + while(!ip_2_ip4(&default_netif.ip_addr)->addr && (ip_counter < 20)) { uint64_t end_tsc, start_tsc = rdtsc(); -#if 1 do { if (ip_2_ip4(&default_netif.ip_addr)->addr) return 0; check_workqueues(); end_tsc = rdtsc(); } while(((end_tsc - start_tsc) / (get_cpu_frequency() * 1000)) < DHCP_FINE_TIMER_MSECS); -#else - sys_msleep(DHCP_FINE_TIMER_MSECS); -#endif dhcp_fine_tmr(); mscnt += DHCP_FINE_TIMER_MSECS; @@ -255,7 +253,12 @@ success: dhcp_coarse_tmr(); mscnt = 0; } + + ip_counter++; } + + if (!ip_2_ip4(&default_netif.ip_addr)->addr) + return -ENODEV; } return 0; @@ -271,10 +274,10 @@ int network_shutdown(void) lwip_close(s); } - mmnif_shutdown(); + mmnif_shutdown(); //stats_display(); - return 0; + return 0; } #if MAX_CORES > 1 @@ -379,6 +382,9 @@ static int initd(void* arg) LOG_INFO("Initd is running\n"); + // initialized bss section + memset((void*)&__bss_start, 0x00, (size_t) &kernel_start + image_size - (size_t) &__bss_start); + // setup heap if (!curr_task->heap) curr_task->heap = (vma_t*) kmalloc(sizeof(vma_t)); @@ -401,17 +407,18 @@ static int initd(void* arg) //create_kernel_task(NULL, foo, "foo2", NORMAL_PRIO); // initialize network - init_netifs(); + err = init_netifs(); -#if 0 - if (is_single_kernel()) { + if ((err != 0) || !is_proxy()) + { char* dummy[] = {"app_name", NULL}; - libc_start(1, dummy, NULL); + LOG_INFO("Boot time: %d ms\n", (get_clock_tick() * 1000) / TIMER_FREQ); + // call user code + libc_start(1, dummy, NULL); //argc, argv, environ); return 0; } -#endif // initialize iRCCE if (!is_single_kernel()) @@ -571,9 +578,9 @@ int hermit_main(void) LOG_INFO("This is Hermit %s, build date %u\n", PACKAGE_VERSION, &__DATE__); LOG_INFO("Isle %d of %d possible isles\n", isle, possible_isles); - LOG_INFO("Kernel starts at %p and ends at %p\n", &kernel_start, &kernel_end); + LOG_INFO("Kernel starts at %p and ends at %p\n", &kernel_start, (size_t)&kernel_start + image_size); LOG_INFO("TLS image starts at %p and ends at %p (size 0x%zx)\n", &tls_start, &tls_end, ((size_t) &tls_end) - ((size_t) &tls_start)); - LOG_INFO("BBS starts at %p and ends at %p\n", &hbss_start, &kernel_end); + LOG_INFO("BBS starts at %p and ends at %p\n", &hbss_start, (size_t)&kernel_start + image_size); LOG_INFO("Per core data starts at %p and ends at %p\n", &percore_start, &percore_end); LOG_INFO("Per core size 0x%zx\n", (size_t) &percore_end0 - (size_t) &percore_start); LOG_INFO("Processor frequency: %u MHz\n", get_cpu_frequency()); @@ -581,6 +588,9 @@ int hermit_main(void) LOG_INFO("Current allocated memory: %zd KiB\n", atomic_int64_read(&total_allocated_pages) * PAGE_SIZE / 1024ULL); LOG_INFO("Current available memory: %zd MiB\n", atomic_int64_read(&total_available_pages) * PAGE_SIZE / (1024ULL*1024ULL)); LOG_INFO("Core %d is the boot processor\n", boot_processor); + LOG_INFO("System is able to use %d processors\n", possible_cpus); + if (mb_info) + LOG_INFO("Kernel cmdline: %s\n", (char*) (size_t) mb_info->cmdline); if (hbmem_base) LOG_INFO("Found high bandwidth memory at 0x%zx (size 0x%zx)\n", hbmem_base, hbmem_size); diff --git a/kernel/syscall.c b/kernel/syscall.c index daf7c5ff9..ea106d2f7 100644 --- a/kernel/syscall.c +++ b/kernel/syscall.c @@ -37,6 +37,7 @@ #include #include #include +#include #include #include @@ -48,7 +49,6 @@ * maintaining a value, rather their address is their value. */ extern const void kernel_start; -extern const void kernel_end; //TODO: don't use one big kernel lock to comminicate with all proxies static spinlock_irqsave_t lwip_lock = SPINLOCK_IRQSAVE_INIT; @@ -89,24 +89,28 @@ typedef struct { /** @brief To be called by the systemcall to exit tasks */ void NORETURN sys_exit(int arg) { - sys_exit_t sysargs = {__NR_exit, arg}; - - spinlock_irqsave_lock(&lwip_lock); - if (libc_sd >= 0) - { - int s = libc_sd; - - lwip_write(s, &sysargs, sizeof(sysargs)); - libc_sd = -1; - - spinlock_irqsave_unlock(&lwip_lock); - - // switch to LwIP thread - reschedule(); - - lwip_close(s); + if (is_uhyve()) { + uhyve_send(UHYVE_PORT_EXIT, (unsigned) virt_to_phys((size_t) &arg)); } else { - spinlock_irqsave_unlock(&lwip_lock); + sys_exit_t sysargs = {__NR_exit, arg}; + + spinlock_irqsave_lock(&lwip_lock); + if (libc_sd >= 0) + { + int s = libc_sd; + + lwip_write(s, &sysargs, sizeof(sysargs)); + libc_sd = -1; + + spinlock_irqsave_unlock(&lwip_lock); + + // switch to LwIP thread + reschedule(); + + lwip_close(s); + } else { + spinlock_irqsave_unlock(&lwip_lock); + } } do_exit(arg); @@ -118,8 +122,23 @@ typedef struct { size_t len; } __attribute__((packed)) sys_read_t; +typedef struct { + int fd; + char* buf; + size_t len; + ssize_t ret; +} __attribute__((packed)) uhyve_read_t; + ssize_t sys_read(int fd, char* buf, size_t len) { + if (is_uhyve()) { + uhyve_read_t uhyve_args = {fd, (char*) virt_to_phys((size_t) buf), len, -1}; + + uhyve_send(UHYVE_PORT_READ, (unsigned)virt_to_phys((size_t)&uhyve_args)); + + return uhyve_args.ret; + } + sys_read_t sysargs = {__NR_read, fd, len}; ssize_t j, ret; int s; @@ -175,15 +194,29 @@ typedef struct { size_t len; } __attribute__((packed)) sys_write_t; +typedef struct { + int fd; + const char* buf; + size_t len; +} __attribute__((packed)) uhyve_write_t; + ssize_t sys_write(int fd, const char* buf, size_t len) { - ssize_t i, ret; - sys_write_t sysargs = {__NR_write, fd, len}; - int s; - if (BUILTIN_EXPECT(!buf, 0)) return -1; + if (is_uhyve()) { + uhyve_write_t uhyve_args = {fd, (const char*) virt_to_phys((size_t) buf), len}; + + uhyve_send(UHYVE_PORT_WRITE, (unsigned)virt_to_phys((size_t)&uhyve_args)); + + return uhyve_args.len; + } + + ssize_t i, ret; + int s; + sys_write_t sysargs = {__NR_write, fd, len}; + // do we have an LwIP file descriptor? if (fd & LWIP_FD_BIT) { ret = lwip_write(fd & ~LWIP_FD_BIT, buf, len); @@ -273,8 +306,23 @@ ssize_t sys_sbrk(ssize_t incr) return ret; } +typedef struct { + const char* name; + int flags; + int mode; + int ret; +} __attribute__((packed)) uhyve_open_t; + int sys_open(const char* name, int flags, int mode) { + if (is_uhyve()) { + uhyve_open_t uhyve_open = {(const char*)virt_to_phys((size_t)name), flags, mode, -1}; + + uhyve_send(UHYVE_PORT_OPEN, (unsigned)virt_to_phys((size_t) &uhyve_open)); + + return uhyve_open.ret; + } + int s, i, ret, sysnr = __NR_open; size_t len; @@ -331,8 +379,21 @@ typedef struct { int fd; } __attribute__((packed)) sys_close_t; +typedef struct { + int fd; + int ret; +} __attribute__((packed)) uhyve_close_t; + int sys_close(int fd) { + if (is_uhyve()) { + uhyve_close_t uhyve_close = {fd, -1}; + + uhyve_send(UHYVE_PORT_CLOSE, (unsigned)virt_to_phys((size_t) &uhyve_close)); + + return uhyve_close.ret; + } + int ret, s; sys_close_t sysargs = {__NR_close, fd}; @@ -363,6 +424,56 @@ out: return ret; } +int sys_spinlock_init(spinlock_t** lock) +{ + int ret; + + if (BUILTIN_EXPECT(!lock, 0)) + return -EINVAL; + + *lock = (spinlock_t*) kmalloc(sizeof(spinlock_t)); + if (BUILTIN_EXPECT(!(*lock), 0)) + return -ENOMEM; + + ret = spinlock_init(*lock); + if (ret) { + kfree(*lock); + *lock = NULL; + } + + return ret; +} + +int sys_spinlock_destroy(spinlock_t* lock) +{ + int ret; + + if (BUILTIN_EXPECT(!lock, 0)) + return -EINVAL; + + ret = spinlock_destroy(lock); + if (!ret) + kfree(lock); + + return ret; +} + +int sys_spinlock_lock(spinlock_t* lock) +{ + if (BUILTIN_EXPECT(!lock, 0)) + return -EINVAL; + + return spinlock_lock(lock); +} + +int sys_spinlock_unlock(spinlock_t* lock) +{ + if (BUILTIN_EXPECT(!lock, 0)) + return -EINVAL; + + return spinlock_unlock(lock); +} + void sys_msleep(unsigned int ms) { if (ms * TIMER_FREQ / 1000 > 0) @@ -449,8 +560,22 @@ typedef struct { int whence; } __attribute__((packed)) sys_lseek_t; +typedef struct { + int fd; + off_t offset; + int whence; +} __attribute__((packed)) uhyve_lseek_t; + off_t sys_lseek(int fd, off_t offset, int whence) { + if (is_uhyve()) { + uhyve_lseek_t uhyve_lseek = { fd, offset, whence }; + + outportl(UHYVE_PORT_LSEEK, (unsigned)virt_to_phys((size_t) &uhyve_lseek)); + + return uhyve_lseek.offset; + } + off_t off; sys_lseek_t sysargs = {__NR_lseek, fd, offset, whence}; int s; diff --git a/kernel/tasks.c b/kernel/tasks.c index 4cc5a7e88..bc9bbccd6 100644 --- a/kernel/tasks.c +++ b/kernel/tasks.c @@ -37,17 +37,16 @@ #include #include #include -#include #include /* * Note that linker symbols are not variables, they have no memory allocated for * maintaining a value, rather their address is their value. */ -extern const void tls_start; -extern const void tls_end; extern atomic_int32_t cpu_online; +volatile uint32_t go_down = 0; + #define TLS_OFFSET 8 /** @brief Array of task structures (aka PCB) @@ -177,6 +176,10 @@ static void readyqueues_push_back(uint32_t core_id, task_t* task) // increase the number of ready tasks readyqueues[core_id].nr_tasks++; + + // should we wakeup the core? + if (readyqueues[core_id].nr_tasks == 1) + wakeup_core(core_id); } @@ -196,6 +199,34 @@ static void readyqueues_remove(uint32_t core_id, task_t* task) } +void fpu_handler(void) +{ + task_t* task = per_core(current_task); + uint32_t core_id = CORE_ID; + + task->flags |= TASK_FPU_USED; + + if (!(task->flags & TASK_FPU_INIT)) { + // use the FPU at the first time => Initialize FPU + fpu_init(&task->fpu); + task->flags |= TASK_FPU_INIT; + } + + if (readyqueues[core_id].fpu_owner == task->id) + return; + + spinlock_irqsave_lock(&readyqueues[core_id].lock); + // did another already use the the FPU? => save FPU state + if (readyqueues[core_id].fpu_owner) { + save_fpu_state(&(task_table[readyqueues[core_id].fpu_owner].fpu)); + task_table[readyqueues[core_id].fpu_owner].flags &= ~TASK_FPU_USED; + } + readyqueues[core_id].fpu_owner = task->id; + spinlock_irqsave_unlock(&readyqueues[core_id].lock); + + restore_fpu_state(&task->fpu); +} + void check_scheduling(void) { if (!is_irq_enabled()) @@ -207,7 +238,7 @@ void check_scheduling(void) if (prio > curr_task->prio) { reschedule(); #ifdef DYNAMIC_TICKS - } else if (prio == curr_task->prio) { + } else if ((prio > 0) && (prio == curr_task->prio)) { // if a task is ready, check if the current task runs already one tick (one time slice) // => reschedule to realize round robin @@ -253,7 +284,7 @@ int multitasking_init(void) task_table[0].ist_addr = (char*)&boot_ist; set_per_core(kernel_stack, task_table[0].stack + KERNEL_STACK_SIZE - 0x10); set_per_core(current_task, task_table+0); - set_tss((size_t) task_table[0].stack + KERNEL_STACK_SIZE - 0x10, (size_t) task_table[0].ist_addr + KERNEL_STACK_SIZE - 0x10); + arch_init_task(task_table+0); readyqueues[core_id].idle = task_table+0; @@ -261,39 +292,6 @@ int multitasking_init(void) } -/* interrupt handler to save / restore the FPU context */ -void fpu_handler(struct state *s) -{ - (void) s; - - task_t* task = per_core(current_task); - uint32_t core_id = CORE_ID; - - clts(); // clear the TS flag of cr0 - task->flags |= TASK_FPU_USED; - - if (!(task->flags & TASK_FPU_INIT)) { - // use the FPU at the first time => Initialize FPU - fpu_init(&task->fpu); - task->flags |= TASK_FPU_INIT; - } - - if (readyqueues[core_id].fpu_owner == task->id) - return; - - spinlock_irqsave_lock(&readyqueues[core_id].lock); - // did another already use the the FPU? => save FPU state - if (readyqueues[core_id].fpu_owner) { - save_fpu_state(&(task_table[readyqueues[core_id].fpu_owner].fpu)); - task_table[readyqueues[core_id].fpu_owner].flags &= ~TASK_FPU_USED; - } - readyqueues[core_id].fpu_owner = task->id; - spinlock_irqsave_unlock(&readyqueues[core_id].lock); - - restore_fpu_state(&task->fpu); -} - - int set_idle_task(void) { uint32_t i, core_id = CORE_ID; @@ -314,7 +312,7 @@ int set_idle_task(void) task_table[i].heap = NULL; readyqueues[core_id].idle = task_table+i; set_per_core(current_task, readyqueues[core_id].idle); - set_tss((size_t) task_table[i].stack + KERNEL_STACK_SIZE - 0x10, (size_t) task_table[i].ist_addr + KERNEL_STACK_SIZE - 0x10); + arch_init_task(task_table+i); ret = 0; break; @@ -326,36 +324,6 @@ int set_idle_task(void) return ret; } - -int init_tls(void) -{ - task_t* curr_task = per_core(current_task); - - // do we have a thread local storage? - if (((size_t) &tls_end - (size_t) &tls_start) > 0) { - char* tls_addr = NULL; - - curr_task->tls_addr = (size_t) &tls_start; - curr_task->tls_size = (size_t) &tls_end - (size_t) &tls_start; - - tls_addr = kmalloc(curr_task->tls_size + TLS_OFFSET); - if (BUILTIN_EXPECT(!tls_addr, 0)) { - LOG_ERROR("load_task: heap is missing!\n"); - return -ENOMEM; - } - - memset(tls_addr, 0x00, TLS_OFFSET); - memcpy((void*) (tls_addr+TLS_OFFSET), (void*) curr_task->tls_addr, curr_task->tls_size); - - // set fs register to the TLS segment - set_tls((size_t) tls_addr + curr_task->tls_size + TLS_OFFSET); - LOG_INFO("TLS of task %d on core %d starts at 0x%zx (TLS)\n", curr_task->id, CORE_ID, tls_addr + TLS_OFFSET); - } else set_tls(0); // no TLS => clear fs register - - return 0; -} - - void finish_task_switch(void) { task_t* old; @@ -519,7 +487,7 @@ int clone_task(tid_t* id, entry_point_t ep, void* arg, uint8_t prio) task_table[i].stack = stack; task_table[i].prio = prio; task_table[i].heap = curr_task->heap; - task_table[i].start_tick = get_clock_tick(); + task_table[i].start_tick = get_clock_tick(); task_table[i].last_tsc = 0; task_table[i].parent = curr_task->id; task_table[i].tls_addr = curr_task->tls_addr; @@ -549,6 +517,9 @@ int clone_task(tid_t* id, entry_point_t ep, void* arg, uint8_t prio) readyqueues[core_id].queue[prio-1].last->next = task_table+i; readyqueues[core_id].queue[prio-1].last = task_table+i; } + // should we wakeup the core? + if (readyqueues[core_id].nr_tasks == 1) + wakeup_core(core_id); spinlock_irqsave_unlock(&readyqueues[core_id].lock); break; } @@ -556,8 +527,9 @@ int clone_task(tid_t* id, entry_point_t ep, void* arg, uint8_t prio) spinlock_irqsave_unlock(&table_lock); - if (!ret) - LOG_INFO("start new thread %d on core %d with stack address %p\n", i, core_id, stack); + if (!ret) { + LOG_DEBUG("start new thread %d on core %d with stack address %p\n", i, core_id, stack); + } out: if (ret) { @@ -709,6 +681,8 @@ int wakeup_task(tid_t id) core_id = task->last_core; if (task->status == TASK_BLOCKED) { + LOG_DEBUG("wakeup task %d\n", id); + task->status = TASK_READY; ret = 0; @@ -746,6 +720,8 @@ int block_task(tid_t id) core_id = task->last_core; if (task->status == TASK_RUNNING) { + LOG_DEBUG("block task %d\n", id); + task->status = TASK_BLOCKED; spinlock_irqsave_lock(&readyqueues[core_id].lock); diff --git a/libkern/Makefile b/libkern/Makefile deleted file mode 100644 index 3e29d4408..000000000 --- a/libkern/Makefile +++ /dev/null @@ -1,4 +0,0 @@ -C_source := string.c stdio.c printf.c sprintf.c strtol.c strtoul.c strstr.c -MODULE := libkern - -include $(TOPDIR)/Makefile.inc diff --git a/libkern/stdio.c b/libkern/stdio.c index 8c4eee2a4..0b1976589 100644 --- a/libkern/stdio.c +++ b/libkern/stdio.c @@ -32,7 +32,6 @@ #include #include #include -#include #include static atomic_int32_t kmsg_counter = ATOMIC_INIT(-1); @@ -46,13 +45,7 @@ spinlock_irqsave_t stdio_lock = SPINLOCK_IRQSAVE_INIT; int koutput_init(void) { if (is_single_kernel()) - { -#ifdef CONFIG_VGA - vga_init(); -#else - uart_early_init(NULL); -#endif - } + uart_init(); return 0; } @@ -68,13 +61,8 @@ int kputchar(int c) pos = atomic_int32_inc(&kmsg_counter); kmessages[pos % KMSG_SIZE] = (unsigned char) c; - if (is_single_kernel()) { -#ifdef CONFIG_VGA - vga_putchar(c); -#else + if (is_single_kernel()) uart_putchar(c); -#endif - } return 1; } @@ -90,13 +78,8 @@ int kputs(const char *str) kmessages[pos % KMSG_SIZE] = str[i]; } - if (is_single_kernel()) { -#ifdef CONFIG_VGA - vga_puts(str); -#else + if (is_single_kernel()) uart_puts(str); -#endif - } spinlock_irqsave_unlock(&stdio_lock); diff --git a/libkern/string.c b/libkern/string.c index 68cc92b5c..31ba69b8b 100644 --- a/libkern/string.c +++ b/libkern/string.c @@ -10,8 +10,8 @@ #include -#ifndef HAVE_ARCH_MEMCPY -void *memcpy(void *dest, const void *src, size_t count) +#if !HAVE_ARCH_MEMCPY +void *_memcpy(void *dest, const void *src, size_t count) { size_t i; @@ -20,13 +20,13 @@ void *memcpy(void *dest, const void *src, size_t count) for (i = 0; i < count; i++) ((char*)dest)[i] = ((char*)src)[i]; - + return dest; } #endif -#ifndef HAVE_ARCH_MEMSET -void *memset(void *dest, int val, size_t count) +#if !HAVE_ARCH_MEMSET +void *_memset(void *dest, int val, size_t count) { size_t i; @@ -40,8 +40,8 @@ void *memset(void *dest, int val, size_t count) } #endif -#ifndef HAVE_ARCH_MEMCMP -int memcmp(const void *s1, const void *s2, size_t n) +#if !HAVE_ARCH_MEMCMP +int _memcmp(const void *s1, const void *s2, size_t n) { if (n != 0) { const unsigned char *p1 = s1, *p2 = s2; @@ -56,8 +56,8 @@ int memcmp(const void *s1, const void *s2, size_t n) } #endif -#ifndef HAVE_ARCH_STRLEN -size_t strlen(const char *str) +#if !HAVE_ARCH_STRLEN +size_t _strlen(const char *str) { size_t len = 0; @@ -71,8 +71,8 @@ size_t strlen(const char *str) } #endif -#ifndef HAVE_ARCH_STRNCPY -char* strncpy(char *dest, const char *src, size_t n) +#if !HAVE_ARCH_STRNCPY +char* _strncpy(char *dest, const char *src, size_t n) { size_t i; @@ -90,8 +90,8 @@ char* strncpy(char *dest, const char *src, size_t n) } #endif -#ifndef HAVE_ARCH_STRCPY -char* strcpy(char *dest, const char *src) +#if !HAVE_ARCH_STRCPY +char* _strcpy(char *dest, const char *src) { size_t i; @@ -106,8 +106,8 @@ char* strcpy(char *dest, const char *src) } #endif -#ifndef HAVE_ARCH_STRCMP -int strcmp(const char *s1, const char *s2) +#if !HAVE_ARCH_STRCMP +int _strcmp(const char *s1, const char *s2) { while (*s1 != '\0' && *s1 == *s2) { s1++; @@ -118,8 +118,8 @@ int strcmp(const char *s1, const char *s2) } #endif -#ifndef HAVE_ARCH_STRNCMP -int strncmp(const char *s1, const char *s2, size_t n) +#if !HAVE_ARCH_STRNCMP +int _strncmp(const char *s1, const char *s2, size_t n) { if (BUILTIN_EXPECT(n == 0, 0)) return 0; diff --git a/libkern/strstr.c b/libkern/strstr.c index fb313d529..ae0898ebc 100644 --- a/libkern/strstr.c +++ b/libkern/strstr.c @@ -48,7 +48,7 @@ * Find the first occurrence of find in s. */ char * -strstr(s, find) +_strstr(s, find) const char *s, *find; { char c, sc; diff --git a/libkern/strtol.c b/libkern/strtol.c index bf31f3162..7c1998831 100644 --- a/libkern/strtol.c +++ b/libkern/strtol.c @@ -32,9 +32,9 @@ * From: @(#)strtol.c 8.1 (Berkeley) 6/4/93 */ -/* +/* * The code has been taken from FreeBSD (sys/libkern/strtol.c) and is consequently - * BSD-licensed. Unnecessary functions have been removed and all typedefs required + * BSD-licensed. Unnecessary functions have been removed and all typedefs required * have been added. */ @@ -50,7 +50,7 @@ * alphabets and digits are each contiguous. */ long -strtol(nptr, endptr, base) +_strtol(nptr, endptr, base) const char *nptr; char **endptr; int base; @@ -130,4 +130,3 @@ strtol(nptr, endptr, base) *((const char **)endptr) = any ? s - 1 : nptr; return (acc); } - diff --git a/libkern/strtoul.c b/libkern/strtoul.c index e0752f803..a934927e5 100644 --- a/libkern/strtoul.c +++ b/libkern/strtoul.c @@ -32,9 +32,9 @@ * From: @(#)strtoul.c 8.1 (Berkeley) 6/4/93 */ -/* +/* * The code has been taken from FreeBSD (sys/libkern/strtoul.c) and is consequently - * BSD-licensed. Unnecessary functions have been removed and all typedefs required + * BSD-licensed. Unnecessary functions have been removed and all typedefs required * have been added. */ @@ -50,7 +50,7 @@ * alphabets and digits are each contiguous. */ unsigned long -strtoul(nptr, endptr, base) +_strtoul(nptr, endptr, base) const char *nptr; char **endptr; int base; @@ -109,4 +109,3 @@ strtoul(nptr, endptr, base) *((const char **)endptr) = any ? s - 1 : nptr; return (acc); } - diff --git a/link.ld b/link.ld deleted file mode 100644 index a7813252b..000000000 --- a/link.ld +++ /dev/null @@ -1,39 +0,0 @@ -OUTPUT_FORMAT("elf64-x86-64") -OUTPUT_ARCH("i386:x86-64") -ENTRY(start) -phys = (2 << 20); -cores = 40; - -SECTIONS -{ - kernel_start = phys; - .mboot phys : AT(ADDR(.mboot)) { - *(.mboot) - . = ALIGN((1 << 12)); - *(.kmsg) - } - .text ALIGN(4096) : AT(ADDR(.text)) { - *(.text) - *(.text.startup) - } - .rodata ALIGN(4096) : AT(ADDR(.rodata)) { - *(.rodata) - *(.rodata.*) - } - .data ALIGN(4096) : AT(ADDR(.data)) { - *(.data) - } - .bss ALIGN(4096) : AT(ADDR(.bss)) { - bss_start = .; - *(.bss) - } - bss_end = .; - .percore ALIGN(4096) : AT(ADDR(.percore)) { - percore_start = .; - *(.percore) - . = ALIGN(64); - percore_end0 = .; - } - percore_end = percore_start + cores * SIZEOF(.percore); - kernel_end = percore_end; -} diff --git a/lwip b/lwip index 278d4691a..54ebf03e3 160000 --- a/lwip +++ b/lwip @@ -1 +1 @@ -Subproject commit 278d4691a11f52329058487444e688d391e78040 +Subproject commit 54ebf03e37f113f035b8ac50aa32ef35168790ed diff --git a/mm/Makefile b/mm/Makefile deleted file mode 100644 index dbcf4aabe..000000000 --- a/mm/Makefile +++ /dev/null @@ -1,4 +0,0 @@ -C_source := memory.c malloc.c vma.c shm.c hbmemory.c -MODULE := mm - -include $(TOPDIR)/Makefile.inc diff --git a/mm/malloc.c b/mm/malloc.c index 9db7eee01..7bdafc67d 100644 --- a/mm/malloc.c +++ b/mm/malloc.c @@ -137,7 +137,7 @@ void* palloc(size_t sz, uint32_t flags) uint32_t npages = PAGE_FLOOR(sz) >> PAGE_BITS; int err; - LOG_DEBUG("palloc(%lu) (%lu pages)\n", sz, npages); + LOG_DEBUG("palloc(%zd) (%u pages)\n", sz, npages); // get free virtual address space viraddr = vma_alloc(PAGE_FLOOR(sz), flags); @@ -152,10 +152,7 @@ void* palloc(size_t sz, uint32_t flags) } //TODO: interpretation of from (vma) flags is missing - bits = PG_RW|PG_GLOBAL; - // protect heap by the NX flag - if (has_nx()) - bits |= PG_XD; + bits = PG_RW|PG_GLOBAL|PG_NX; // map physical pages to VMA err = page_map(viraddr, phyaddr, npages, bits); @@ -174,7 +171,7 @@ void* create_stack(size_t sz) uint32_t npages = PAGE_FLOOR(sz) >> PAGE_BITS; int err; - LOG_DEBUG("create_stack(0x%zx) (%lu pages)\n", DEFAULT_STACK_SIZE, npages); + LOG_DEBUG("create_stack(0x%zx) (%u pages)\n", DEFAULT_STACK_SIZE, npages); if (BUILTIN_EXPECT(!sz, 0)) return NULL; @@ -191,10 +188,7 @@ void* create_stack(size_t sz) return NULL; } - bits = PG_RW|PG_GLOBAL; - // protect heap by the NX flag - if (has_nx()) - bits |= PG_XD; + bits = PG_RW|PG_GLOBAL|PG_NX; // map physical pages to VMA err = page_map(viraddr+PAGE_SIZE, phyaddr, npages, bits); @@ -251,7 +245,7 @@ void* kmalloc(size_t sz) buddy->prefix.magic = BUDDY_MAGIC; buddy->prefix.exponent = exp; - LOG_DEBUG("kmalloc(%lu) = %p\n", sz, buddy+1); + LOG_DEBUG("kmalloc(%zd) = %p\n", sz, buddy+1); // pointer arithmetic: we hide the prefix return buddy+1; @@ -262,7 +256,7 @@ void kfree(void *addr) if (BUILTIN_EXPECT(!addr, 0)) return; - LOG_DEBUG("kfree(%lu)\n", addr); + LOG_DEBUG("kfree(%p)\n", addr); buddy_t* buddy = (buddy_t*) addr - 1; // get prefix diff --git a/mm/vma.c b/mm/vma.c index 435ba0977..88f30bdd1 100644 --- a/mm/vma.c +++ b/mm/vma.c @@ -32,18 +32,16 @@ #include #include #include -#include -/* +/* * Note that linker symbols are not variables, they have no memory allocated for * maintaining a value, rather their address is their value. */ extern const void kernel_start; -extern const void kernel_end; /* * Kernel space VMA list and lock - * + * * For bootstrapping we initialize the VMA list with one empty VMA * (start == end) and expand this VMA by calls to vma_alloc() */ @@ -51,19 +49,17 @@ static vma_t vma_boot = { VMA_MIN, VMA_MIN, VMA_HEAP }; static vma_t* vma_list = &vma_boot; static spinlock_irqsave_t vma_lock = SPINLOCK_IRQSAVE_INIT; -// TODO: we might move the architecture specific VMA regions to a -// seperate function arch_vma_init() int vma_init(void) { int ret; LOG_INFO("vma_init: reserve vma region 0x%llx - 0x%llx\n", PAGE_2M_CEIL((size_t) &kernel_start), - PAGE_2M_FLOOR((size_t) &kernel_end)); + PAGE_2M_FLOOR((size_t) &kernel_start + image_size)); // add Kernel ret = vma_add(PAGE_2M_CEIL((size_t) &kernel_start), - PAGE_2M_FLOOR((size_t) &kernel_end), + PAGE_2M_FLOOR((size_t) &kernel_start + image_size), VMA_READ|VMA_WRITE|VMA_EXECUTE|VMA_CACHEABLE); if (BUILTIN_EXPECT(ret, 0)) goto out; @@ -73,24 +69,9 @@ int vma_init(void) if (BUILTIN_EXPECT(ret, 0)) goto out; -#ifdef CONFIG_VGA - // add VGA video memory - ret = vma_add(VIDEO_MEM_ADDR, VIDEO_MEM_ADDR + PAGE_SIZE, VMA_READ|VMA_WRITE); - if (BUILTIN_EXPECT(ret, 0)) - goto out; -#endif - - if (mb_info) { - ret = vma_add((size_t)mb_info & PAGE_MASK, ((size_t)mb_info & PAGE_MASK) + PAGE_SIZE, VMA_READ|VMA_WRITE); - if (BUILTIN_EXPECT(ret, 0)) - goto out; - - if ((mb_info->cmdline & PAGE_MASK) != ((size_t) mb_info & PAGE_MASK)) { - ret = vma_add((size_t)mb_info->cmdline & PAGE_MASK, ((size_t)mb_info->cmdline & PAGE_MASK) + PAGE_SIZE, VMA_READ|VMA_WRITE); - if (BUILTIN_EXPECT(ret, 0)) - goto out; - } - } + // we might move the architecture specific VMA regions to a + // seperate function vma_arch_init() + ret = vma_arch_init(); out: return ret; diff --git a/test.sh b/test.sh deleted file mode 100644 index c29469b81..000000000 --- a/test.sh +++ /dev/null @@ -1,18 +0,0 @@ -#!/bin/bash -# -# do not use this script -# it is written only for internal tests via Travis CI - -FILES="usr/tests/hello usr/tests/hellof usr/tests/hello++ usr/tests/thr_hello usr/tests/pi usr/benchmarks/stream usr/benchmarks/basic" -PROXY=/opt/hermit/bin/proxy - -for f in $FILES; do echo "check $f..."; $PROXY $f || exit 1; done - -# test echo server at port 8000 -#HERMIT_APP_PORT=8000 $PROXY usr/tests/server & -#sleep 10 -#curl http://127.0.0.1:8000/help -#sleep 1 - -# kill server -#kill $! diff --git a/tests.sh b/tests.sh new file mode 100755 index 000000000..3cabbadbe --- /dev/null +++ b/tests.sh @@ -0,0 +1,21 @@ +#!/bin/bash +# +# do not use this script +# it is written only for internal tests via Travis CI + +TDIR=build/local_prefix/opt/hermit/x86_64-hermit/extra +FILES="$TDIR/tests/hello $TDIR/tests/hellof $TDIR/tests/hello++ $TDIR/tests/thr_hello $TDIR/tests/pi $TDIR/benchmarks/stream $TDIR/benchmarks/basic $TDIR/tests/signals $TDIR/tests/test-malloc $TDIR/tests/test-malloc-mt" +PROXY=build/local_prefix/opt/hermit/bin/proxy + +for f in $FILES; do echo "check $f..."; HERMIT_ISLE=qemu HERMIT_CPUS=1 HERMIT_KVM=0 HERMIT_VERBOSE=1 timeout --kill-after=5m 5m $PROXY $f || exit 1; done + +# test echo server at port 8000 +HERMIT_ISLE=qemu HERMIT_CPUS=1 HERMIT_KVM=0 HERMIT_VERBOSE=1 HERMIT_APP_PORT=8000 $PROXY $TDIR/tests/server & +sleep 10 +curl http://127.0.0.1:8000/help +sleep 1 +curl http://127.0.0.1:8000/hello +sleep 1 + +# kill server +kill $! diff --git a/tools/CMakeLists.txt b/tools/CMakeLists.txt new file mode 100644 index 000000000..2b2ef5532 --- /dev/null +++ b/tools/CMakeLists.txt @@ -0,0 +1,20 @@ +cmake_minimum_required(VERSION 3.7) +project(hermit_tools) + +include(../cmake/HermitCore-Paths.cmake) + +add_compile_options(-std=c99) + +add_executable(proxy proxy.c uhyve.c) +target_compile_options(proxy PUBLIC -pthread) +target_link_libraries(proxy -pthread) + +install(TARGETS proxy + DESTINATION bin) + +install(FILES init.sh + DESTINATION tools) + +# Show include files in IDE +file(GLOB_RECURSE TOOLS_INCLUDES "*.h") +add_custom_target(tools_includes_ide SOURCES ${TOOLS_INCLUDES}) diff --git a/tools/Makefile.in b/tools/Makefile.in deleted file mode 100644 index 34535c35c..000000000 --- a/tools/Makefile.in +++ /dev/null @@ -1,46 +0,0 @@ -MAKE = make -CC = gcc -CFLAGS = -O2 -Wall -std=gnu99 $(ARCH_OPT) -PROXYFILES = proxy init.sh $(shell find ../usr/tests ../usr/benchmarks ../usr/openmpbench -type f -executable) - -prefix = @prefix@ -INSTALL = @INSTALL@ -INSTALL_PROGRAM = @INSTALL_PROGRAM@ -INSTALL_SCRIPT = @INSTALL_SCRIPT@ -INSTALL_DATA = @INSTALL_DATA@ - -# Prettify output -V = 0 -ifeq ($V,0) - Q = @ - P = > /dev/null -endif - -# other implicit rules -%.o : %.c - @echo [CC] $@ - $Q$(CC) -c $(CFLAGS) -o $@ $< - -all: proxy - -proxy: proxy.o - @echo [LD] $@ - $Q$(CC) $(CFLAGS) -o $@ $< - -clean: - @echo Cleaning tools - $Q$(RM) -rf *.o *~ *.bin *.obj - -install: proxy - @echo Install tools - $Q$(INSTALL_PROGRAM) -d $(prefix)/bin - $Q$(INSTALL_PROGRAM) proxy $(prefix)/bin - $Q$(INSTALL_DATA) ../arch/x86/loader/ldhermit.elf $(prefix)/bin - -veryclean: clean - -depend: - $(CC) -MM $(CFLAGS) *.c > Makefile.dep - --include Makefile.dep -# DO NOT DELETE diff --git a/tools/hermit_ircce.json b/tools/hermit_ircce.json deleted file mode 100644 index 9dd6b85ca..000000000 --- a/tools/hermit_ircce.json +++ /dev/null @@ -1,5846 +0,0 @@ -{ - "version": 1, - "width": 80, - "height": 25, - "duration": 88.835376, - "command": "./demo.sh", - "title": "HermitCore iRCCE Demo", - "env": { - "TERM": "xterm-256color", - "SHELL": "/bin/bash" - }, - "stdout": [ - [ - 0.029569, - "\u001b[3;J\u001b[H\u001b[2J" - ], - [ - 0.000305, - "~ \u003e" - ], - [ - 0.009620, - " " - ], - [ - 0.078121, - "\u001b" - ], - [ - 0.096134, - "[" - ], - [ - 0.096132, - "9" - ], - [ - 0.108147, - "2" - ], - [ - 0.018085, - "m" - ], - [ - 0.006096, - "#" - ], - [ - 0.102055, - " " - ], - [ - 0.054078, - "H" - ], - [ - 0.048094, - "e" - ], - [ - 0.048071, - "r" - ], - [ - 0.060101, - "m" - ], - [ - 0.060102, - "i" - ], - [ - 0.036090, - "t" - ], - [ - 0.096136, - "C" - ], - [ - 0.036087, - "o" - ], - [ - 0.018088, - "r" - ], - [ - 0.066114, - "e" - ], - [ - 0.060051, - " " - ], - [ - 0.096148, - "e" - ], - [ - 0.030085, - "x" - ], - [ - 0.072113, - "t" - ], - [ - 0.024098, - "e" - ], - [ - 0.084113, - "n" - ], - [ - 0.006091, - "d" - ], - [ - 0.096134, - "s" - ], - [ - 0.024088, - " " - ], - [ - 0.018093, - "t" - ], - [ - 0.012031, - "h" - ], - [ - 0.054082, - "e" - ], - [ - 0.042039, - " " - ], - [ - 0.066079, - "b" - ], - [ - 0.066139, - "\u0008 \u0008" - ], - [ - 0.054093, - "m" - ], - [ - 0.006086, - "u" - ], - [ - 0.090126, - "l" - ], - [ - 0.006087, - "t" - ], - [ - 0.108148, - "i" - ], - [ - 0.018091, - "-" - ], - [ - 0.048031, - "k" - ], - [ - 0.054089, - "e" - ], - [ - 0.108121, - "r" - ], - [ - 0.102145, - "n" - ], - [ - 0.054089, - "e" - ], - [ - 0.024095, - "l" - ], - [ - 0.024092, - " " - ], - [ - 0.078116, - "a" - ], - [ - 0.060101, - "p" - ], - [ - 0.072121, - "p" - ], - [ - 0.024027, - "r" - ], - [ - 0.066081, - "o" - ], - [ - 0.012053, - "a" - ], - [ - 0.006082, - "c" - ], - [ - 0.102143, - "h" - ], - [ - 0.048086, - " " - ], - [ - 0.054094, - "a" - ], - [ - 0.054091, - "n" - ], - [ - 0.024086, - "d" - ], - [ - 0.078122, - " " - ], - [ - 0.006102, - "c" - ], - [ - 0.090067, - "o" - ], - [ - 0.072098, - "m" - ], - [ - 0.078079, - "b" - ], - [ - 0.030107, - "i" - ], - [ - 0.030094, - "n" - ], - [ - 0.006093, - "e" - ], - [ - 0.060107, - "s" - ], - [ - 0.108153, - " " - ], - [ - 0.084120, - "i" - ], - [ - 0.018095, - "t" - ], - [ - 0.018048, - " " - ], - [ - 0.078091, - "w" - ], - [ - 0.054073, - "i" - ], - [ - 0.054067, - "t" - ], - [ - 0.096160, - "h" - ], - [ - 0.018106, - " " - ], - [ - 0.102143, - "u" - ], - [ - 0.006090, - "n" - ], - [ - 0.060095, - "i" - ], - [ - 0.078124, - "-" - ], - [ - 0.030054, - "\u001b" - ], - [ - 0.102107, - "[" - ], - [ - 0.078096, - "3" - ], - [ - 0.048079, - "9" - ], - [ - 0.006105, - "m" - ], - [ - 0.024093, - "\r\n" - ], - [ - 0.018435, - "~ \u003e" - ], - [ - 0.000942, - " " - ], - [ - 0.096119, - "\u001b" - ], - [ - 0.096033, - "[" - ], - [ - 0.072096, - "9" - ], - [ - 0.102140, - "2" - ], - [ - 0.084109, - "m" - ], - [ - 0.036091, - "#" - ], - [ - 0.084123, - " " - ], - [ - 0.054092, - "k" - ], - [ - 0.090127, - "e" - ], - [ - 0.078116, - "r" - ], - [ - 0.078102, - "n" - ], - [ - 0.096118, - "e" - ], - [ - 0.078090, - "l" - ], - [ - 0.060087, - " " - ], - [ - 0.090133, - "f" - ], - [ - 0.078120, - "e" - ], - [ - 0.066105, - "a" - ], - [ - 0.024089, - "t" - ], - [ - 0.078116, - "u" - ], - [ - 0.054094, - "r" - ], - [ - 0.018041, - "e" - ], - [ - 0.096111, - "s" - ], - [ - 0.084096, - " " - ], - [ - 0.078133, - "w" - ], - [ - 0.210244, - "\u0008 \u0008" - ], - [ - 0.024086, - "w" - ], - [ - 0.042093, - "h" - ], - [ - 0.108145, - "i" - ], - [ - 0.042085, - "l" - ], - [ - 0.012070, - "e" - ], - [ - 0.006095, - " " - ], - [ - 0.042083, - "p" - ], - [ - 0.042099, - "r" - ], - [ - 0.060125, - "o" - ], - [ - 0.078093, - "v" - ], - [ - 0.042096, - "i" - ], - [ - 0.108151, - "d" - ], - [ - 0.042089, - "a" - ], - [ - 0.078106, - "\u0008 \u0008" - ], - [ - 0.012072, - "i" - ], - [ - 0.078074, - "n" - ], - [ - 0.084132, - "g" - ], - [ - 0.090134, - " " - ], - [ - 0.102145, - "b" - ], - [ - 0.036091, - "e" - ], - [ - 0.090130, - "t" - ], - [ - 0.060097, - "t" - ], - [ - 0.102129, - "e" - ], - [ - 0.102123, - "r" - ], - [ - 0.030069, - " " - ], - [ - 0.024085, - "p" - ], - [ - 0.066108, - "r" - ], - [ - 0.102143, - "o" - ], - [ - 0.060099, - "g" - ], - [ - 0.054092, - "r" - ], - [ - 0.084118, - "a" - ], - [ - 0.066111, - "m" - ], - [ - 0.018050, - "m" - ], - [ - 0.006070, - "a" - ], - [ - 0.102159, - "b" - ], - [ - 0.024086, - "i" - ], - [ - 0.084150, - "l" - ], - [ - 0.006085, - "i" - ], - [ - 0.012088, - "t" - ], - [ - 0.108149, - "y" - ], - [ - 0.108139, - " " - ], - [ - 0.102077, - "a" - ], - [ - 0.054067, - "n" - ], - [ - 0.072087, - "d" - ], - [ - 0.072102, - " " - ], - [ - 0.036077, - "s" - ], - [ - 0.090138, - "c" - ], - [ - 0.054091, - "a" - ], - [ - 0.078117, - "l" - ], - [ - 0.102144, - "a" - ], - [ - 0.066110, - "b" - ], - [ - 0.084058, - "i" - ], - [ - 0.072086, - "l" - ], - [ - 0.018071, - "i" - ], - [ - 0.084116, - "t" - ], - [ - 0.048113, - "y" - ], - [ - 0.006092, - "\u001b" - ], - [ - 0.012091, - "[" - ], - [ - 0.066105, - "3" - ], - [ - 0.090128, - "9" - ], - [ - 0.060097, - "m" - ], - [ - 0.030081, - "\r\n" - ], - [ - 0.048402, - "~ \u003e" - ], - [ - 0.000652, - " " - ], - [ - 0.096148, - "\u001b" - ], - [ - 0.030064, - "[" - ], - [ - 0.036090, - "9" - ], - [ - 0.072115, - "2" - ], - [ - 0.084126, - "m" - ], - [ - 0.090127, - "#" - ], - [ - 0.018086, - " " - ], - [ - 0.096136, - "f" - ], - [ - 0.102086, - "o" - ], - [ - 0.066061, - "r" - ], - [ - 0.096123, - " " - ], - [ - 0.066097, - "h" - ], - [ - 0.066113, - "i" - ], - [ - 0.066109, - "e" - ], - [ - 0.042091, - "r" - ], - [ - 0.042091, - "a" - ], - [ - 0.066106, - "r" - ], - [ - 0.102150, - "c" - ], - [ - 0.006049, - "h" - ], - [ - 0.108121, - "i" - ], - [ - 0.012064, - "c" - ], - [ - 0.054084, - "a" - ], - [ - 0.018082, - "l" - ], - [ - 0.012094, - " " - ], - [ - 0.030105, - "s" - ], - [ - 0.102151, - "y" - ], - [ - 0.042086, - "s" - ], - [ - 0.102152, - "t" - ], - [ - 0.054063, - "e" - ], - [ - 0.054068, - "m" - ], - [ - 0.030063, - "s" - ], - [ - 0.036070, - "." - ], - [ - 0.078141, - "\u001b" - ], - [ - 0.060100, - "[" - ], - [ - 0.108164, - "3" - ], - [ - 0.054078, - "9" - ], - [ - 0.042092, - "m" - ], - [ - 0.012094, - "\r\n" - ], - [ - 0.042485, - "~ \u003e\r\n~ \u003e" - ], - [ - 0.000638, - " " - ], - [ - 0.090112, - "\u001b" - ], - [ - 0.096113, - "[" - ], - [ - 0.108167, - "9" - ], - [ - 0.048085, - "2" - ], - [ - 0.060093, - "m" - ], - [ - 0.012096, - "#" - ], - [ - 0.072104, - " " - ], - [ - 0.102143, - "B" - ], - [ - 0.078091, - "y" - ], - [ - 0.078104, - " " - ], - [ - 0.036052, - "s" - ], - [ - 0.018052, - "t" - ], - [ - 0.048082, - "a" - ], - [ - 0.096136, - "m" - ], - [ - 0.156202, - "\u0008 \u0008" - ], - [ - 0.162202, - "r" - ], - [ - 0.066101, - "t" - ], - [ - 0.006063, - "i" - ], - [ - 0.066075, - "n" - ], - [ - 0.054063, - "g" - ], - [ - 0.024077, - " " - ], - [ - 0.096143, - "a" - ], - [ - 0.024087, - " " - ], - [ - 0.006080, - "H" - ], - [ - 0.102146, - "e" - ], - [ - 0.048085, - "r" - ], - [ - 0.018086, - "o" - ], - [ - 0.006087, - "\u0008 \u0008" - ], - [ - 0.216075, - "m" - ], - [ - 0.048054, - "i" - ], - [ - 0.060069, - "t" - ], - [ - 0.078095, - "C" - ], - [ - 0.030065, - "o" - ], - [ - 0.012084, - "r" - ], - [ - 0.030091, - "e" - ], - [ - 0.066104, - " " - ], - [ - 0.102145, - "a" - ], - [ - 0.042091, - "p" - ], - [ - 0.054087, - "p" - ], - [ - 0.036102, - "l" - ], - [ - 0.084024, - "i" - ], - [ - 0.030070, - "c" - ], - [ - 0.108112, - "a" - ], - [ - 0.024080, - "t" - ], - [ - 0.030079, - "i" - ], - [ - 0.060125, - "o" - ], - [ - 0.012065, - "n" - ], - [ - 0.042089, - "," - ], - [ - 0.072109, - " " - ], - [ - 0.102139, - "c" - ], - [ - 0.018094, - "o" - ], - [ - 0.048023, - "r" - ], - [ - 0.048070, - "e" - ], - [ - 0.066106, - "s" - ], - [ - 0.102111, - " " - ], - [ - 0.012113, - "a" - ], - [ - 0.054102, - "r" - ], - [ - 0.012083, - "e" - ], - [ - 0.012091, - " " - ], - [ - 0.054090, - "b" - ], - [ - 0.096130, - "e" - ], - [ - 0.018098, - " " - ], - [ - 0.006015, - "s" - ], - [ - 0.054069, - "p" - ], - [ - 0.078080, - "e" - ], - [ - 0.024092, - "r" - ], - [ - 0.072137, - "a" - ], - [ - 0.024110, - "t" - ], - [ - 0.012080, - "e" - ], - [ - 0.054095, - "d" - ], - [ - 0.102139, - " " - ], - [ - 0.054090, - "f" - ], - [ - 0.042093, - "r" - ], - [ - 0.042013, - "o" - ], - [ - 0.096109, - "m" - ], - [ - 0.060064, - " " - ], - [ - 0.006082, - "L" - ], - [ - 0.060096, - "i" - ], - [ - 0.108145, - "n" - ], - [ - 0.078113, - "u" - ], - [ - 0.006086, - "x" - ], - [ - 0.030087, - " " - ], - [ - 0.054098, - "a" - ], - [ - 0.108120, - "n" - ], - [ - 0.048062, - "d" - ], - [ - 0.108126, - "\u001b" - ], - [ - 0.024092, - "[" - ], - [ - 0.030088, - "3" - ], - [ - 0.012084, - "9" - ], - [ - 0.036086, - "m" - ], - [ - 0.006100, - "\r\n" - ], - [ - 0.060476, - "~ \u003e" - ], - [ - 0.000805, - " " - ], - [ - 0.048099, - "\u001b" - ], - [ - 0.042056, - "[" - ], - [ - 0.036067, - "9" - ], - [ - 0.096128, - "2" - ], - [ - 0.018088, - "m" - ], - [ - 0.096143, - "#" - ], - [ - 0.108158, - " " - ], - [ - 0.102144, - "a" - ], - [ - 0.072107, - " " - ], - [ - 0.018090, - "u" - ], - [ - 0.102007, - "n" - ], - [ - 0.018080, - "i" - ], - [ - 0.018039, - "k" - ], - [ - 0.030070, - "e" - ], - [ - 0.096146, - "r" - ], - [ - 0.036090, - "n" - ], - [ - 0.018088, - "e" - ], - [ - 0.048088, - "l" - ], - [ - 0.036090, - " " - ], - [ - 0.096135, - "i" - ], - [ - 0.108155, - "s" - ], - [ - 0.102016, - " " - ], - [ - 0.030053, - "b" - ], - [ - 0.012104, - "e" - ], - [ - 0.042052, - " " - ], - [ - 0.054074, - "b" - ], - [ - 0.090133, - "o" - ], - [ - 0.090133, - "o" - ], - [ - 0.006079, - "t" - ], - [ - 0.036093, - "e" - ], - [ - 0.060095, - "d" - ], - [ - 0.054091, - " " - ], - [ - 0.042079, - "o" - ], - [ - 0.036021, - "n" - ], - [ - 0.018071, - " " - ], - [ - 0.072092, - "t" - ], - [ - 0.090114, - "h" - ], - [ - 0.024108, - "e" - ], - [ - 0.054105, - "s" - ], - [ - 0.006097, - "e" - ], - [ - 0.084132, - " " - ], - [ - 0.096135, - "c" - ], - [ - 0.084115, - "o" - ], - [ - 0.054034, - "r" - ], - [ - 0.024072, - "e" - ], - [ - 0.090103, - "s" - ], - [ - 0.054095, - " " - ], - [ - 0.006092, - "w" - ], - [ - 0.096134, - "i" - ], - [ - 0.108149, - "t" - ], - [ - 0.108146, - "h" - ], - [ - 0.096141, - " " - ], - [ - 0.108068, - "t" - ], - [ - 0.102131, - "h" - ], - [ - 0.054059, - "e" - ], - [ - 0.054080, - " " - ], - [ - 0.084122, - "a" - ], - [ - 0.090132, - "p" - ], - [ - 0.108147, - "p" - ], - [ - 0.084124, - "l" - ], - [ - 0.060106, - "i" - ], - [ - 0.018067, - "c" - ], - [ - 0.048029, - "a" - ], - [ - 0.048068, - "t" - ], - [ - 0.042053, - "i" - ], - [ - 0.090151, - "o" - ], - [ - 0.036107, - "n" - ], - [ - 0.108148, - "." - ], - [ - 0.096130, - "\u001b" - ], - [ - 0.024099, - "[" - ], - [ - 0.024090, - "3" - ], - [ - 0.090133, - "9" - ], - [ - 0.072015, - "m" - ], - [ - 0.036065, - "\r\n" - ], - [ - 0.072531, - "~ \u003e" - ], - [ - 0.000801, - " " - ], - [ - 0.084124, - "\u001b" - ], - [ - 0.102143, - "[" - ], - [ - 0.036090, - "9" - ], - [ - 0.108147, - "2" - ], - [ - 0.090097, - "m" - ], - [ - 0.090103, - "#" - ], - [ - 0.108173, - " " - ], - [ - 0.036058, - "C" - ], - [ - 0.018086, - "o" - ], - [ - 0.036111, - "n" - ], - [ - 0.102131, - "s" - ], - [ - 0.060098, - "e" - ], - [ - 0.024092, - "q" - ], - [ - 0.036092, - "u" - ], - [ - 0.006072, - "e" - ], - [ - 0.042043, - "n" - ], - [ - 0.108182, - "t" - ], - [ - 0.102150, - "l" - ], - [ - 0.048116, - "y" - ], - [ - 0.018081, - "," - ], - [ - 0.090125, - " " - ], - [ - 0.042088, - "H" - ], - [ - 0.036094, - "e" - ], - [ - 0.102113, - "r" - ], - [ - 0.012074, - "m" - ], - [ - 0.102130, - "i" - ], - [ - 0.054112, - "t" - ], - [ - 0.108145, - "C" - ], - [ - 0.006090, - "o" - ], - [ - 0.048100, - "r" - ], - [ - 0.108144, - "e" - ], - [ - 0.084126, - " " - ], - [ - 0.018074, - "i" - ], - [ - 0.054075, - "s" - ], - [ - 0.042098, - " " - ], - [ - 0.072091, - "a" - ], - [ - 0.048081, - " " - ], - [ - 0.006112, - "s" - ], - [ - 0.090113, - "i" - ], - [ - 0.108151, - "n" - ], - [ - 0.012092, - "j" - ], - [ - 0.060106, - "\u0008 \u0008" - ], - [ - 0.006080, - "g" - ], - [ - 0.066080, - "l" - ], - [ - 0.006061, - "e" - ], - [ - 0.048070, - "-" - ], - [ - 0.042074, - "a" - ], - [ - 0.084130, - "d" - ], - [ - 0.072099, - "d" - ], - [ - 0.060101, - "r" - ], - [ - 0.096136, - "e" - ], - [ - 0.084124, - "s" - ], - [ - 0.042091, - "s" - ], - [ - 0.090033, - " " - ], - [ - 0.042086, - "s" - ], - [ - 0.036031, - "p" - ], - [ - 0.006076, - "a" - ], - [ - 0.042087, - "c" - ], - [ - 0.012083, - "e" - ], - [ - 0.078141, - " " - ], - [ - 0.012079, - "o" - ], - [ - 0.036088, - "p" - ], - [ - 0.066110, - "e" - ], - [ - 0.012096, - "r" - ], - [ - 0.024089, - "a" - ], - [ - 0.066040, - "t" - ], - [ - 0.102107, - "i" - ], - [ - 0.102115, - "n" - ], - [ - 0.030095, - "g" - ], - [ - 0.042084, - " " - ], - [ - 0.078122, - "s" - ], - [ - 0.084121, - "y" - ], - [ - 0.006085, - "s" - ], - [ - 0.072118, - "t" - ], - [ - 0.084130, - "e" - ], - [ - 0.108024, - "m" - ], - [ - 0.060070, - " " - ], - [ - 0.036061, - "w" - ], - [ - 0.078141, - "h" - ], - [ - 0.018075, - "i" - ], - [ - 0.006093, - "c" - ], - [ - 0.078133, - "h" - ], - [ - 0.054082, - "\u001b" - ], - [ - 0.090128, - "[" - ], - [ - 0.042087, - "3" - ], - [ - 0.054094, - "9" - ], - [ - 0.066030, - "m" - ], - [ - 0.018055, - "\r\n" - ], - [ - 0.006430, - "~ \u003e" - ], - [ - 0.000824, - " " - ], - [ - 0.096137, - "\u001b" - ], - [ - 0.048088, - "[" - ], - [ - 0.018096, - "9" - ], - [ - 0.096140, - "2" - ], - [ - 0.096134, - "m" - ], - [ - 0.024082, - "#" - ], - [ - 0.012066, - " " - ], - [ - 0.036051, - "p" - ], - [ - 0.006102, - "r" - ], - [ - 0.006067, - "u" - ], - [ - 0.210263, - "\u0008 \u0008" - ], - [ - 0.018088, - "o" - ], - [ - 0.048086, - "m" - ], - [ - 0.096136, - "i" - ], - [ - 0.042118, - "s" - ], - [ - 0.108054, - "e" - ], - [ - 0.006050, - " " - ], - [ - 0.096155, - "a" - ], - [ - 0.024064, - " " - ], - [ - 0.084123, - "l" - ], - [ - 0.042107, - "o" - ], - [ - 0.090137, - "w" - ], - [ - 0.096135, - "e" - ], - [ - 0.066106, - "r" - ], - [ - 0.108105, - " " - ], - [ - 0.012062, - "O" - ], - [ - 0.018074, - "S" - ], - [ - 0.084107, - " " - ], - [ - 0.006105, - "n" - ], - [ - 0.090151, - "o" - ], - [ - 0.030082, - "i" - ], - [ - 0.036096, - "s" - ], - [ - 0.030084, - "e" - ], - [ - 0.096138, - " " - ], - [ - 0.030090, - "a" - ], - [ - 0.048020, - "n" - ], - [ - 0.102112, - "d" - ], - [ - 0.090148, - " " - ], - [ - 0.060094, - "b" - ], - [ - 0.012092, - "e" - ], - [ - 0.012087, - "t" - ], - [ - 0.012087, - "t" - ], - [ - 0.084122, - "e" - ], - [ - 0.024086, - "r" - ], - [ - 0.054094, - " " - ], - [ - 0.024077, - "s" - ], - [ - 0.036046, - "c" - ], - [ - 0.048095, - "a" - ], - [ - 0.102133, - "l" - ], - [ - 0.030100, - "a" - ], - [ - 0.102137, - "b" - ], - [ - 0.042094, - "i" - ], - [ - 0.108144, - "l" - ], - [ - 0.078117, - "i" - ], - [ - 0.096138, - "t" - ], - [ - 0.096131, - "y" - ], - [ - 0.108137, - "." - ], - [ - 0.060091, - "\u001b" - ], - [ - 0.036093, - "[" - ], - [ - 0.006087, - "3" - ], - [ - 0.036096, - "9" - ], - [ - 0.012091, - "m" - ], - [ - 0.084124, - "\r\n" - ], - [ - 0.066584, - "~ \u003e\r\n~ \u003e" - ], - [ - 0.000889, - " " - ], - [ - 0.078107, - "\u001b" - ], - [ - 0.108141, - "[" - ], - [ - 0.072114, - "9" - ], - [ - 0.108152, - "2" - ], - [ - 0.066110, - "q" - ], - [ - 0.126057, - "\u0008 \u0008" - ], - [ - 0.186244, - "\u001b[92m" - ], - [ - 0.084129, - " #" - ], - [ - 0.066113, - " " - ], - [ - 0.090117, - "O" - ], - [ - 0.054099, - "u" - ], - [ - 0.042089, - "r" - ], - [ - 0.090135, - " " - ], - [ - 0.066055, - "t" - ], - [ - 0.054088, - "e" - ], - [ - 0.102099, - "g" - ], - [ - 0.198249, - "\u0008 \u0008" - ], - [ - 0.072111, - "s" - ], - [ - 0.060103, - "t" - ], - [ - 0.018090, - " " - ], - [ - 0.090125, - "s" - ], - [ - 0.018090, - "y" - ], - [ - 0.006050, - "s" - ], - [ - 0.060076, - "t" - ], - [ - 0.030055, - "o" - ], - [ - 0.036053, - "\u0008 \u0008" - ], - [ - 0.078109, - "e" - ], - [ - 0.036079, - "m" - ], - [ - 0.078119, - " " - ], - [ - 0.018094, - "i" - ], - [ - 0.030090, - "s" - ], - [ - 0.006095, - " " - ], - [ - 0.072103, - "a" - ], - [ - 0.030093, - " " - ], - [ - 0.048038, - "N" - ], - [ - 0.066087, - "U" - ], - [ - 0.060072, - "M" - ], - [ - 0.078107, - "A" - ], - [ - 0.096129, - " " - ], - [ - 0.024085, - "s" - ], - [ - 0.060097, - "y" - ], - [ - 0.018084, - "s" - ], - [ - 0.012090, - "t" - ], - [ - 0.066102, - "e" - ], - [ - 0.084132, - "m" - ], - [ - 0.006011, - " " - ], - [ - 0.054280, - "b" - ], - [ - 0.071871, - "a" - ], - [ - 0.036062, - "s" - ], - [ - 0.042075, - "e" - ], - [ - 0.108144, - "d" - ], - [ - 0.078113, - " " - ], - [ - 0.060100, - "o" - ], - [ - 0.024090, - "n" - ], - [ - 0.042091, - " " - ], - [ - 0.084120, - "I" - ], - [ - 0.066061, - "n" - ], - [ - 0.072092, - "t" - ], - [ - 0.054086, - "e" - ], - [ - 0.048067, - "l" - ], - [ - 0.006087, - "'" - ], - [ - 0.072133, - "s" - ], - [ - 0.096118, - " " - ], - [ - 0.072111, - "C" - ], - [ - 0.096129, - "P" - ], - [ - 0.090139, - "U" - ], - [ - 0.102043, - " " - ], - [ - 0.018070, - "E" - ], - [ - 0.096110, - "5" - ], - [ - 0.102149, - "-" - ], - [ - 0.054090, - "2" - ], - [ - 0.048091, - "6" - ], - [ - 0.066106, - "5" - ], - [ - 0.072110, - "0" - ], - [ - 0.078124, - " " - ], - [ - 0.108132, - "v" - ], - [ - 0.096117, - "3" - ], - [ - 0.060072, - "\u001b" - ], - [ - 0.084109, - "[" - ], - [ - 0.060102, - "3" - ], - [ - 0.090141, - "9" - ], - [ - 0.024084, - "m" - ], - [ - 0.030082, - "\r\n" - ], - [ - 0.012502, - "~ \u003e" - ], - [ - 0.000884, - " " - ], - [ - 0.060081, - "n" - ], - [ - 0.084133, - "u" - ], - [ - 0.066096, - "m" - ], - [ - 0.060102, - "a" - ], - [ - 0.060102, - "c" - ], - [ - 0.090128, - "t" - ], - [ - 0.048090, - "l" - ], - [ - 0.048090, - " " - ], - [ - 0.090104, - "-" - ], - [ - 0.102163, - "-" - ], - [ - 0.024071, - "h" - ], - [ - 0.012093, - "a" - ], - [ - 0.030094, - "r" - ], - [ - 0.096132, - "d" - ], - [ - 0.066105, - "w" - ], - [ - 0.060103, - "a" - ], - [ - 0.030080, - "r" - ], - [ - 0.048101, - "e" - ], - [ - 0.012052, - "\r\n" - ], - [ - 0.091847, - "available: 2 nodes (0-1)\r\nnode 0 cpus: 0 1 2 3 4 5 6 7 8 9\r\nnode 0 size: 32051 MB\r\nnode 0 free: 31540 MB\r\nnode 1 cpus: 10 11 12 13 14 15 16 17 18 19\r\nnode 1 size: 32254 MB\r\nnode 1 free: 31991 MB\r\nnode distances:\r\nnode 0 1 \r\n 0: 10 21 \r\n 1: 21 10 \r\n" - ], - [ - 0.000197, - "~ \u003e" - ], - [ - 1.012298, - " " - ], - [ - 0.036100, - "l" - ], - [ - 0.096126, - "s" - ], - [ - 0.012091, - "c" - ], - [ - 0.018088, - "p" - ], - [ - 0.024091, - "u" - ], - [ - 0.048101, - "\r\n" - ], - [ - 0.057376, - "Architektur: x86_64\r\nCPU Operationsmodus: 32-bit, 64-bit\r\nByte-Reihenfolge: Little Endian\r\nCPU(s): 20\r\nListe der Online-CPU(s):0-19\r\nThread(s) pro Kern: 1\r\nKern(e) pro Socket: 10\r\nSockel: 2\r\nNUMA-Knoten: 2\r\nAnbieterkennung: GenuineIntel\r\nProzessorfamilie: 6\r\nModell: 63\r\nModellname: Intel(R) Xeon(R) CPU E5-2650 v3 @ 2.30GHz\r\nStepping: 2\r\nCPU MHz: 1253.500\r\nMaximale Taktfrequenz der CPU:3000,0000\r\nMinimale Taktfrequenz der CPU:1200,0000\r\nBogoMIPS: 4604.86\r\nVirtualisierung: VT-x\r\nL1d Cache: 32K\r\nL1i Cache: 32K\r\nL2 Cache: 256K\r\nL3 Cache: 25600K\r\nNUMA-Knoten0 CPU(s): 0-9\r\nNUMA-Knoten1 CPU(s): 10-19\r\nMarkierungen: fpu vme de pse tsc msr pae mce cx8 apic sep mtrr pge mca cmov pat pse36 clflush dts acpi mmx fxsr sse sse2 ss ht tm pbe syscall nx pdpe1gb rdtscp lm constant_tsc arch_perfmon pebs bts rep_good nopl xtopology nonstop_tsc aperfmperf eagerfpu pni pclmulqdq dtes64 monitor ds_cpl vmx smx est tm2 ssse3 fma cx16 xtpr pdcm pcid dca sse4_1 sse4_2 x2apic movbe popcnt tsc_deadline_timer aes xsave avx f16c rdrand lahf_lm abm arat epb pln pts dtherm tpr_shadow vnmi flexpriority ept vpid fsgsbase tsc_adjust bmi1 avx2 smep bmi2 erms invpcid cqm xsaveopt cqm_llc cqm_occup_llc\r\n" - ], - [ - 0.000264, - "~ \u003e" - ], - [ - 0.000705, - " " - ], - [ - 0.030089, - "\u001b" - ], - [ - 0.054114, - "[" - ], - [ - 0.090123, - "9" - ], - [ - 0.048092, - "2" - ], - [ - 0.048096, - "m" - ], - [ - 0.018092, - "#" - ], - [ - 0.012080, - " " - ], - [ - 0.060018, - "H" - ], - [ - 0.084104, - "e" - ], - [ - 0.042063, - "r" - ], - [ - 0.054067, - "m" - ], - [ - 0.048099, - "i" - ], - [ - 0.096137, - "t" - ], - [ - 0.078114, - "C" - ], - [ - 0.042097, - "o" - ], - [ - 0.018095, - "r" - ], - [ - 0.048091, - "e" - ], - [ - 0.108144, - " " - ], - [ - 0.108113, - "i" - ], - [ - 0.024107, - "s" - ], - [ - 0.066079, - " " - ], - [ - 0.072100, - "a" - ], - [ - 0.048105, - "b" - ], - [ - 0.108153, - "l" - ], - [ - 0.006086, - "e" - ], - [ - 0.054095, - " " - ], - [ - 0.042100, - "t" - ], - [ - 0.108063, - "o" - ], - [ - 0.060086, - " " - ], - [ - 0.030063, - "b" - ], - [ - 0.054056, - "o" - ], - [ - 0.054078, - "o" - ], - [ - 0.060098, - "t" - ], - [ - 0.102142, - " " - ], - [ - 0.102139, - "a" - ], - [ - 0.096132, - "n" - ], - [ - 0.030092, - " " - ], - [ - 0.012082, - "a" - ], - [ - 0.096041, - "p" - ], - [ - 0.030071, - "p" - ], - [ - 0.060063, - "l" - ], - [ - 0.030069, - "i" - ], - [ - 0.006066, - "c" - ], - [ - 0.102142, - "a" - ], - [ - 0.078114, - "t" - ], - [ - 0.066095, - "i" - ], - [ - 0.096137, - "o" - ], - [ - 0.102140, - "n" - ], - [ - 0.102103, - " " - ], - [ - 0.048082, - "o" - ], - [ - 0.096096, - "n" - ], - [ - 0.054087, - " " - ], - [ - 0.078124, - "e" - ], - [ - 0.084128, - "a" - ], - [ - 0.060109, - "c" - ], - [ - 0.060102, - "h" - ], - [ - 0.102142, - " " - ], - [ - 0.012091, - "N" - ], - [ - 0.018032, - "U" - ], - [ - 0.006063, - "M" - ], - [ - 0.060074, - "A" - ], - [ - 0.066094, - " " - ], - [ - 0.060104, - "n" - ], - [ - 0.060088, - "o" - ], - [ - 0.096138, - "d" - ], - [ - 0.084120, - "e" - ], - [ - 0.096135, - " " - ], - [ - 0.084138, - "w" - ], - [ - 0.024035, - "h" - ], - [ - 0.036071, - "i" - ], - [ - 0.108126, - "c" - ], - [ - 0.108161, - "h" - ], - [ - 0.072108, - " " - ], - [ - 0.084120, - "w" - ], - [ - 0.078124, - "e" - ], - [ - 0.072097, - " " - ], - [ - 0.036090, - "c" - ], - [ - 0.054085, - "a" - ], - [ - 0.006021, - "l" - ], - [ - 0.042055, - "l" - ], - [ - 0.066075, - "\u001b" - ], - [ - 0.084117, - "[" - ], - [ - 0.072128, - "3" - ], - [ - 0.006078, - "9" - ], - [ - 0.060097, - "m" - ], - [ - 0.102144, - "\r\n" - ], - [ - 0.030533, - "~ \u003e" - ], - [ - 0.000746, - " " - ], - [ - 0.030038, - "\u001b" - ], - [ - 0.096157, - "[" - ], - [ - 0.048073, - "9" - ], - [ - 0.018097, - "2" - ], - [ - 0.108148, - "m" - ], - [ - 0.078115, - "#" - ], - [ - 0.018092, - " " - ], - [ - 0.078115, - "i" - ], - [ - 0.036092, - "s" - ], - [ - 0.078100, - "l" - ], - [ - 0.102116, - "e" - ], - [ - 0.078100, - "s" - ], - [ - 0.024092, - "." - ], - [ - 0.012075, - " " - ], - [ - 0.024101, - "v" - ], - [ - 0.078125, - "\u0008 \u0008" - ], - [ - 0.150186, - "T" - ], - [ - 0.012092, - "h" - ], - [ - 0.012086, - "e" - ], - [ - 0.006043, - " " - ], - [ - 0.060071, - "m" - ], - [ - 0.006082, - "e" - ], - [ - 0.024051, - "s" - ], - [ - 0.006067, - "s" - ], - [ - 0.054109, - "a" - ], - [ - 0.072116, - "g" - ], - [ - 0.072105, - "e" - ], - [ - 0.096139, - " " - ], - [ - 0.030093, - "p" - ], - [ - 0.108153, - "x" - ], - [ - 0.048077, - "\u0008 \u0008" - ], - [ - 0.132133, - "a" - ], - [ - 0.024069, - "s" - ], - [ - 0.102152, - "s" - ], - [ - 0.024093, - "i" - ], - [ - 0.108147, - "n" - ], - [ - 0.018084, - "g" - ], - [ - 0.012087, - " " - ], - [ - 0.024102, - "i" - ], - [ - 0.030056, - "n" - ], - [ - 0.096099, - "t" - ], - [ - 0.090115, - "e" - ], - [ - 0.102144, - "r" - ], - [ - 0.024095, - "f" - ], - [ - 0.096134, - "a" - ], - [ - 0.018088, - "c" - ], - [ - 0.108139, - "e" - ], - [ - 0.006100, - " " - ], - [ - 0.060089, - "i" - ], - [ - 0.018074, - "R" - ], - [ - 0.018052, - "C" - ], - [ - 0.066115, - "C" - ], - [ - 0.102157, - "E" - ], - [ - 0.066103, - " " - ], - [ - 0.108151, - "i" - ], - [ - 0.048088, - "s" - ], - [ - 0.030090, - " " - ], - [ - 0.036087, - "s" - ], - [ - 0.012073, - "u" - ], - [ - 0.048075, - "p" - ], - [ - 0.018092, - "p" - ], - [ - 0.108142, - "o" - ], - [ - 0.006089, - "r" - ], - [ - 0.066109, - "t" - ], - [ - 0.084131, - "e" - ], - [ - 0.048088, - "d" - ], - [ - 0.072109, - " " - ], - [ - 0.066117, - "f" - ], - [ - 0.030056, - "o" - ], - [ - 0.024080, - "r" - ], - [ - 0.030043, - " " - ], - [ - 0.024109, - "t" - ], - [ - 0.078119, - "h" - ], - [ - 0.024086, - "e" - ], - [ - 0.102147, - " " - ], - [ - 0.036089, - "i" - ], - [ - 0.042083, - "n" - ], - [ - 0.012093, - "t" - ], - [ - 0.036102, - "e" - ], - [ - 0.036041, - "r" - ], - [ - 0.036069, - "-" - ], - [ - 0.048099, - "n" - ], - [ - 0.048100, - "o" - ], - [ - 0.084129, - "d" - ], - [ - 0.048084, - "e" - ], - [ - 0.036081, - "\u001b" - ], - [ - 0.012090, - "[" - ], - [ - 0.030090, - "3" - ], - [ - 0.036088, - "9" - ], - [ - 0.042093, - "m" - ], - [ - 0.030083, - "\r\n" - ], - [ - 0.006546, - "~ \u003e" - ], - [ - 0.000866, - " " - ], - [ - 0.102141, - "\u001b" - ], - [ - 0.042095, - "[" - ], - [ - 0.030113, - "9" - ], - [ - 0.066096, - "2" - ], - [ - 0.066114, - "m" - ], - [ - 0.096029, - "#" - ], - [ - 0.048069, - " " - ], - [ - 0.060100, - "c" - ], - [ - 0.048100, - "o" - ], - [ - 0.066099, - "m" - ], - [ - 0.042079, - "m" - ], - [ - 0.084123, - "u" - ], - [ - 0.042094, - "n" - ], - [ - 0.018093, - "i" - ], - [ - 0.054109, - "c" - ], - [ - 0.072118, - "a" - ], - [ - 0.072016, - "t" - ], - [ - 0.072101, - "i" - ], - [ - 0.090128, - "o" - ], - [ - 0.048089, - "n" - ], - [ - 0.018095, - "." - ], - [ - 0.006088, - " " - ], - [ - 0.030089, - "M" - ], - [ - 0.048092, - "P" - ], - [ - 0.090117, - "I" - ], - [ - 0.096143, - " " - ], - [ - 0.048064, - "s" - ], - [ - 0.030064, - "u" - ], - [ - 0.012055, - "p" - ], - [ - 0.048118, - "p" - ], - [ - 0.072120, - "o" - ], - [ - 0.072117, - "r" - ], - [ - 0.066107, - "t" - ], - [ - 0.018085, - " " - ], - [ - 0.108148, - "w" - ], - [ - 0.024092, - "i" - ], - [ - 0.024093, - "l" - ], - [ - 0.090135, - "l" - ], - [ - 0.072106, - " " - ], - [ - 0.006099, - "b" - ], - [ - 0.006079, - "e" - ], - [ - 0.024084, - " " - ], - [ - 0.096139, - "p" - ], - [ - 0.066096, - "u" - ], - [ - 0.102149, - "b" - ], - [ - 0.030094, - "l" - ], - [ - 0.006021, - "i" - ], - [ - 0.006060, - "s" - ], - [ - 0.012116, - "h" - ], - [ - 0.060101, - "e" - ], - [ - 0.072115, - "d" - ], - [ - 0.072110, - " " - ], - [ - 0.090131, - "s" - ], - [ - 0.090129, - "o" - ], - [ - 0.006100, - "o" - ], - [ - 0.006073, - "n" - ], - [ - 0.060056, - "." - ], - [ - 0.012075, - " " - ], - [ - 0.096090, - "A" - ], - [ - 0.102177, - " " - ], - [ - 0.060098, - "p" - ], - [ - 0.012075, - "r" - ], - [ - 0.096127, - "o" - ], - [ - 0.090134, - "t" - ], - [ - 0.084124, - "o" - ], - [ - 0.090103, - "t" - ], - [ - 0.042067, - "y" - ], - [ - 0.090153, - "p" - ], - [ - 0.090136, - " " - ], - [ - 0.054092, - "e" - ], - [ - 0.006087, - "x" - ], - [ - 0.036088, - "i" - ], - [ - 0.048086, - "s" - ], - [ - 0.018087, - "t" - ], - [ - 0.048087, - "s" - ], - [ - 0.066098, - "\u001b" - ], - [ - 0.036092, - "[" - ], - [ - 0.060037, - "3" - ], - [ - 0.096164, - "9" - ], - [ - 0.042095, - "m" - ], - [ - 0.078121, - "\r\n" - ], - [ - 0.078660, - "~ \u003e" - ], - [ - 0.000852, - " " - ], - [ - 0.024074, - "\u001b" - ], - [ - 0.048098, - "[" - ], - [ - 0.030081, - "9" - ], - [ - 0.024112, - "2" - ], - [ - 0.084122, - "m" - ], - [ - 0.018088, - "#" - ], - [ - 0.096129, - " " - ], - [ - 0.060095, - "a" - ], - [ - 0.102154, - "l" - ], - [ - 0.012046, - "r" - ], - [ - 0.096099, - "e" - ], - [ - 0.078129, - "a" - ], - [ - 0.036101, - "d" - ], - [ - 0.108154, - "y" - ], - [ - 0.108150, - "." - ], - [ - 0.024092, - " " - ], - [ - 0.090120, - "T" - ], - [ - 0.018104, - "h" - ], - [ - 0.012053, - "e" - ], - [ - 0.042084, - " " - ], - [ - 0.036052, - "e" - ], - [ - 0.072094, - "n" - ], - [ - 0.090158, - "v" - ], - [ - 0.072104, - "i" - ], - [ - 0.102141, - "r" - ], - [ - 0.072116, - "o" - ], - [ - 0.054090, - "n" - ], - [ - 0.078123, - "m" - ], - [ - 0.012028, - "e" - ], - [ - 0.078100, - "n" - ], - [ - 0.084094, - "t" - ], - [ - 0.102166, - " " - ], - [ - 0.108142, - "v" - ], - [ - 0.018088, - "a" - ], - [ - 0.096138, - "r" - ], - [ - 0.084125, - "i" - ], - [ - 0.060103, - "a" - ], - [ - 0.096053, - "b" - ], - [ - 0.066071, - "l" - ], - [ - 0.078128, - "e" - ], - [ - 0.024087, - " " - ], - [ - 0.012087, - "H" - ], - [ - 0.012112, - "E" - ], - [ - 0.030080, - "R" - ], - [ - 0.102137, - "M" - ], - [ - 0.066107, - "I" - ], - [ - 0.030086, - "T" - ], - [ - 0.102097, - "_" - ], - [ - 0.018078, - "I" - ], - [ - 0.108110, - "S" - ], - [ - 0.048091, - "L" - ], - [ - 0.060120, - "E" - ], - [ - 0.018086, - " " - ], - [ - 0.012092, - "s" - ], - [ - 0.108157, - "p" - ], - [ - 0.060092, - "e" - ], - [ - 0.090143, - "c" - ], - [ - 0.054031, - "i" - ], - [ - 0.072077, - "f" - ], - [ - 0.048104, - "i" - ], - [ - 0.048064, - "e" - ], - [ - 0.024095, - "s" - ], - [ - 0.006102, - " " - ], - [ - 0.048086, - "o" - ], - [ - 0.108148, - "n" - ], - [ - 0.066103, - " " - ], - [ - 0.102140, - "w" - ], - [ - 0.108083, - "h" - ], - [ - 0.048066, - "i" - ], - [ - 0.096134, - "c" - ], - [ - 0.012103, - "h" - ], - [ - 0.060092, - " " - ], - [ - 0.066104, - "i" - ], - [ - 0.042097, - "s" - ], - [ - 0.072120, - "l" - ], - [ - 0.006084, - "e" - ], - [ - 0.078119, - " " - ], - [ - 0.102079, - "t" - ], - [ - 0.012082, - "h" - ], - [ - 0.072071, - "e" - ], - [ - 0.060074, - "\u001b" - ], - [ - 0.102177, - "[" - ], - [ - 0.006089, - "3" - ], - [ - 0.018091, - "9" - ], - [ - 0.060099, - "m" - ], - [ - 0.006089, - "\r\n" - ], - [ - 0.054486, - "~ \u003e" - ], - [ - 0.000810, - " " - ], - [ - 0.042082, - "\u001b" - ], - [ - 0.048045, - "[" - ], - [ - 0.066099, - "9" - ], - [ - 0.012080, - "2" - ], - [ - 0.096150, - "m" - ], - [ - 0.036094, - "#" - ], - [ - 0.072116, - " " - ], - [ - 0.096135, - "g" - ], - [ - 0.216142, - "\u0008 \u0008" - ], - [ - 0.126125, - "a" - ], - [ - 0.090143, - "p" - ], - [ - 0.084128, - "p" - ], - [ - 0.108145, - "i" - ], - [ - 0.084133, - "\u0008 \u0008" - ], - [ - 0.156198, - "l" - ], - [ - 0.048092, - "i" - ], - [ - 0.066048, - "c" - ], - [ - 0.060055, - "a" - ], - [ - 0.054074, - "t" - ], - [ - 0.060073, - "i" - ], - [ - 0.072115, - "o" - ], - [ - 0.084135, - "y" - ], - [ - 0.090134, - "\u0008 \u0008" - ], - [ - 0.132174, - "n" - ], - [ - 0.024088, - " " - ], - [ - 0.048093, - "w" - ], - [ - 0.024036, - "i" - ], - [ - 0.090095, - "l" - ], - [ - 0.084095, - "l" - ], - [ - 0.042083, - " " - ], - [ - 0.012085, - "b" - ], - [ - 0.078117, - "e" - ], - [ - 0.036092, - " " - ], - [ - 0.096129, - "s" - ], - [ - 0.024088, - "t" - ], - [ - 0.060090, - "a" - ], - [ - 0.054102, - "r" - ], - [ - 0.066031, - "t" - ], - [ - 0.072090, - "e" - ], - [ - 0.096112, - "d" - ], - [ - 0.084132, - "." - ], - [ - 0.048102, - "\u001b" - ], - [ - 0.090119, - "[" - ], - [ - 0.018087, - "3" - ], - [ - 0.054099, - "9" - ], - [ - 0.108157, - "m" - ], - [ - 0.030095, - "\r\n" - ], - [ - 0.036429, - "~ \u003e" - ], - [ - 0.001104, - " " - ], - [ - 0.072116, - "\u001b" - ], - [ - 0.108147, - "[" - ], - [ - 0.012091, - "9" - ], - [ - 0.024092, - "2" - ], - [ - 0.006019, - "m" - ], - [ - 0.018066, - "#" - ], - [ - 0.018070, - " " - ], - [ - 0.102137, - "T" - ], - [ - 0.060099, - "h" - ], - [ - 0.054094, - "e" - ], - [ - 0.030091, - " " - ], - [ - 0.054097, - "k" - ], - [ - 0.102146, - "\u0008 \u0008" - ], - [ - 0.144193, - "f" - ], - [ - 0.036012, - "u" - ], - [ - 0.084102, - "n" - ], - [ - 0.036063, - "c" - ], - [ - 0.108155, - "t" - ], - [ - 0.018084, - "i" - ], - [ - 0.018121, - "o" - ], - [ - 0.006084, - "n" - ], - [ - 0.108156, - "a" - ], - [ - 0.054098, - "l" - ], - [ - 0.024101, - "i" - ], - [ - 0.030036, - "t" - ], - [ - 0.066084, - "y" - ], - [ - 0.012064, - " " - ], - [ - 0.090120, - "w" - ], - [ - 0.030079, - "i" - ], - [ - 0.078145, - "l" - ], - [ - 0.066099, - "l" - ], - [ - 0.072114, - " " - ], - [ - 0.042092, - "b" - ], - [ - 0.012086, - "e" - ], - [ - 0.102119, - " " - ], - [ - 0.024084, - "d" - ], - [ - 0.012045, - "e" - ], - [ - 0.054074, - "m" - ], - [ - 0.108155, - "o" - ], - [ - 0.084132, - "n" - ], - [ - 0.078115, - "s" - ], - [ - 0.042094, - "t" - ], - [ - 0.072110, - "r" - ], - [ - 0.060103, - "a" - ], - [ - 0.042085, - "t" - ], - [ - 0.084098, - "e" - ], - [ - 0.072095, - "d" - ], - [ - 0.078129, - " " - ], - [ - 0.036086, - "w" - ], - [ - 0.066114, - "i" - ], - [ - 0.006090, - "t" - ], - [ - 0.066108, - "h" - ], - [ - 0.066105, - " " - ], - [ - 0.066116, - "a" - ], - [ - 0.096064, - " " - ], - [ - 0.066071, - "P" - ], - [ - 0.072118, - "i" - ], - [ - 0.012113, - "n" - ], - [ - 0.006107, - "g" - ], - [ - 0.042095, - "P" - ], - [ - 0.006090, - "o" - ], - [ - 0.054094, - "n" - ], - [ - 0.066106, - "g" - ], - [ - 0.054093, - " " - ], - [ - 0.102096, - "b" - ], - [ - 0.084104, - "e" - ], - [ - 0.090117, - "n" - ], - [ - 0.066082, - "c" - ], - [ - 0.084119, - "h" - ], - [ - 0.096142, - "m" - ], - [ - 0.096142, - "a" - ], - [ - 0.102144, - "r" - ], - [ - 0.042097, - "k" - ], - [ - 0.036061, - "." - ], - [ - 0.012068, - "\u001b" - ], - [ - 0.066079, - "[" - ], - [ - 0.096127, - "3" - ], - [ - 0.054092, - "9" - ], - [ - 0.078116, - "m" - ], - [ - 0.042095, - "\r\n" - ], - [ - 0.024482, - "~ \u003e" - ], - [ - 0.000756, - " " - ], - [ - 0.060107, - "H" - ], - [ - 0.084074, - "E" - ], - [ - 0.108125, - "R" - ], - [ - 0.030061, - "M" - ], - [ - 0.108157, - "I" - ], - [ - 0.108147, - "T" - ], - [ - 0.060101, - "_" - ], - [ - 0.054092, - "C" - ], - [ - 0.042087, - "P" - ], - [ - 0.042089, - "U" - ], - [ - 0.066124, - "S" - ], - [ - 0.006021, - "=" - ], - [ - 0.078097, - "1" - ], - [ - 0.084090, - " " - ], - [ - 0.078110, - "H" - ], - [ - 0.018088, - "E" - ], - [ - 0.072118, - "R" - ], - [ - 0.066114, - "M" - ], - [ - 0.054092, - "I" - ], - [ - 0.108148, - "T" - ], - [ - 0.096121, - "_" - ], - [ - 0.096041, - "I" - ], - [ - 0.042061, - "S" - ], - [ - 0.084101, - "L" - ], - [ - 0.018067, - "E" - ], - [ - 0.090138, - "=" - ], - [ - 0.072113, - "0" - ], - [ - 0.012090, - " " - ], - [ - 0.096132, - "h" - ], - [ - 0.012089, - "e" - ], - [ - 0.012094, - "r" - ], - [ - 0.042075, - "m" - ], - [ - 0.096033, - "i" - ], - [ - 0.012060, - "t" - ], - [ - 0.072090, - "/" - ], - [ - 0.096151, - "u" - ], - [ - 0.012089, - "s" - ], - [ - 0.018097, - "r" - ], - [ - 0.036096, - "/" - ], - [ - 0.048084, - "b" - ], - [ - 0.054091, - "e" - ], - [ - 0.102137, - "n" - ], - [ - 0.048090, - "c" - ], - [ - 0.024054, - "h" - ], - [ - 0.078089, - "m" - ], - [ - 0.012054, - "a" - ], - [ - 0.042079, - "r" - ], - [ - 0.036087, - "k" - ], - [ - 0.072117, - "s" - ], - [ - 0.096127, - "/" - ], - [ - 0.030086, - "R" - ], - [ - 0.060098, - "C" - ], - [ - 0.078116, - "C" - ], - [ - 0.066101, - "E" - ], - [ - 0.036061, - "_" - ], - [ - 0.096105, - "p" - ], - [ - 0.042105, - "i" - ], - [ - 0.102145, - "n" - ], - [ - 0.102142, - "g" - ], - [ - 0.030090, - "p" - ], - [ - 0.108144, - "o" - ], - [ - 0.108154, - "n" - ], - [ - 0.072050, - "g" - ], - [ - 0.096107, - " " - ], - [ - 0.012063, - "2" - ], - [ - 0.030074, - " " - ], - [ - 0.078138, - "5" - ], - [ - 0.018088, - "3" - ], - [ - 0.048088, - "3" - ], - [ - 0.006092, - " " - ], - [ - 0.060102, - "0" - ], - [ - 0.102149, - " " - ], - [ - 0.108107, - "1" - ], - [ - 0.102135, - " " - ], - [ - 0.018110, - "\u0026" - ], - [ - 0.072105, - "\r\n" - ], - [ - 0.194643, - "My rank is 0, physical core ID is 0\r\n" - ], - [ - 0.413070, - "~ \u003e" - ], - [ - 0.000700, - " " - ], - [ - 0.078106, - "H" - ], - [ - 0.048087, - "E" - ], - [ - 0.090016, - "R" - ], - [ - 0.090141, - "M" - ], - [ - 0.096114, - "I" - ], - [ - 0.054091, - "T" - ], - [ - 0.072096, - "_" - ], - [ - 0.042086, - "C" - ], - [ - 0.006082, - "P" - ], - [ - 0.048082, - "U" - ], - [ - 0.012081, - "S" - ], - [ - 0.036086, - "=" - ], - [ - 0.072097, - "1" - ], - [ - 0.054042, - "1" - ], - [ - 0.066100, - " " - ], - [ - 0.054084, - "H" - ], - [ - 0.066094, - "E" - ], - [ - 0.054079, - "R" - ], - [ - 0.096134, - "M" - ], - [ - 0.030069, - "I" - ], - [ - 0.054101, - "T" - ], - [ - 0.012077, - "_" - ], - [ - 0.060080, - "I" - ], - [ - 0.096125, - "S" - ], - [ - 0.036070, - "L" - ], - [ - 0.048073, - "E" - ], - [ - 0.060055, - "=" - ], - [ - 0.054053, - "1" - ], - [ - 0.006080, - " " - ], - [ - 0.108140, - "h" - ], - [ - 0.096132, - "e" - ], - [ - 0.024075, - "r" - ], - [ - 0.096123, - "m" - ], - [ - 0.066104, - "i" - ], - [ - 0.096127, - "t" - ], - [ - 0.036030, - "/" - ], - [ - 0.078101, - "u" - ], - [ - 0.060090, - "s" - ], - [ - 0.018078, - "r" - ], - [ - 0.006076, - "/" - ], - [ - 0.078118, - "b" - ], - [ - 0.102129, - "e" - ], - [ - 0.036074, - "n" - ], - [ - 0.018078, - "c" - ], - [ - 0.006075, - "h" - ], - [ - 0.108141, - "m" - ], - [ - 0.018048, - "a" - ], - [ - 0.036078, - "r" - ], - [ - 0.030033, - "k" - ], - [ - 0.006068, - "s" - ], - [ - 0.066090, - "/" - ], - [ - 0.096127, - "R" - ], - [ - 0.096124, - "C" - ], - [ - 0.066088, - "C" - ], - [ - 0.060098, - "E" - ], - [ - 0.084103, - "_" - ], - [ - 0.066100, - "p" - ], - [ - 0.084082, - "i" - ], - [ - 0.024078, - "n" - ], - [ - 0.006084, - "g" - ], - [ - 0.108126, - "p" - ], - [ - 0.096133, - "o" - ], - [ - 0.012082, - "n" - ], - [ - 0.096118, - "g" - ], - [ - 0.048086, - " " - ], - [ - 0.012072, - "2" - ], - [ - 0.060098, - " " - ], - [ - 0.048084, - "5" - ], - [ - 0.102044, - "3" - ], - [ - 0.012073, - "3" - ], - [ - 0.036072, - " " - ], - [ - 0.090121, - "0" - ], - [ - 0.108132, - " " - ], - [ - 0.096136, - "1" - ], - [ - 0.042087, - "\r\n" - ], - [ - 0.184360, - "My rank is 1, physical core ID is 1\r\n" - ], - [ - 0.235012, - "#bytes\t\tusec\t\tMB/sec\r\n" - ], - [ - 0.012993, - "1\t\t0.65\t\t1.46\r\n" - ], - [ - 0.013000, - "2\t\t0.65\t\t2.92\r\n" - ], - [ - 0.013001, - "4\t\t0.65\t\t5.86\r\n" - ], - [ - 0.013999, - "8\t\t0.66\t\t11.56\r\n" - ], - [ - 0.012999, - "16\t\t0.66\t\t23.05\r\n" - ], - [ - 0.013001, - "32\t\t0.66\t\t46.15\r\n" - ], - [ - 0.013000, - "64\t\t0.67\t\t91.62\r\n" - ], - [ - 0.013999, - "128\t\t0.67\t\t182.48\r\n" - ], - [ - 0.015999, - "256\t\t0.81\t\t300.68\r\n" - ], - [ - 0.016001, - "512\t\t0.82\t\t593.22\r\n" - ], - [ - 0.020000, - "1024\t\t0.97\t\t1010.89\r\n" - ], - [ - 0.023002, - "2048\t\t1.17\t\t1668.23\r\n" - ], - [ - 0.033998, - "4096\t\t1.67\t\t2334.55\r\n" - ], - [ - 0.050002, - "8192\t\t2.50\t\t3126.52\r\n" - ], - [ - 0.082999, - "16384\t\t4.16\t\t3753.40\r\n" - ], - [ - 0.163001, - "32768\t\t8.16\t\t3828.60\r\n" - ], - [ - 0.332001, - "65536\t\t16.60\t\t3764.13\r\n" - ], - [ - 0.663000, - "131072\t\t33.16\t\t3769.55\r\n" - ], - [ - 1.295002, - "262144\t\t64.73\t\t3861.90\r\n" - ], - [ - 0.828887, - "~ \u003e" - ], - [ - 0.301359, - " " - ], - [ - 0.060076, - "\u001b" - ], - [ - 0.012074, - "[" - ], - [ - 0.018073, - "9" - ], - [ - 0.054080, - "2" - ], - [ - 0.006075, - "m" - ], - [ - 0.078102, - "H" - ], - [ - 0.024074, - "e" - ], - [ - 0.024074, - "r" - ], - [ - 0.036084, - "m" - ], - [ - 0.024040, - "i" - ], - [ - 0.060066, - "t" - ], - [ - 0.012060, - "C" - ], - [ - 0.024056, - "o" - ], - [ - 0.006080, - "r" - ], - [ - 0.102119, - "e" - ], - [ - 0.030072, - " " - ], - [ - 0.036072, - "(" - ], - [ - 0.048074, - "\u001b" - ], - [ - 0.048075, - "[" - ], - [ - 0.066089, - "3" - ], - [ - 0.108131, - "1" - ], - [ - 0.054081, - "m" - ], - [ - 0.048023, - "h" - ], - [ - 0.102109, - "t" - ], - [ - 0.078088, - "t" - ], - [ - 0.006074, - "p" - ], - [ - 0.042072, - ":" - ], - [ - 0.036074, - "/" - ], - [ - 0.084107, - "/" - ], - [ - 0.060085, - "w" - ], - [ - 0.030075, - "w" - ], - [ - 0.018075, - "w" - ], - [ - 0.072096, - "." - ], - [ - 0.078106, - "h" - ], - [ - 0.078035, - "e" - ], - [ - 0.006057, - "r" - ], - [ - 0.102112, - "m" - ], - [ - 0.042058, - "i" - ], - [ - 0.042089, - "t" - ], - [ - 0.024074, - "c" - ], - [ - 0.036075, - "o" - ], - [ - 0.096118, - "r" - ], - [ - 0.030075, - "e" - ], - [ - 0.102124, - "." - ], - [ - 0.066089, - "o" - ], - [ - 0.072098, - "r" - ], - [ - 0.024032, - "g" - ], - [ - 0.060069, - "\u001b" - ], - [ - 0.036057, - "[" - ], - [ - 0.096113, - "9" - ], - [ - 0.024081, - "2" - ], - [ - 0.006072, - "m" - ], - [ - 0.102125, - ")" - ], - [ - 0.072097, - " " - ], - [ - 0.090114, - "i" - ], - [ - 0.066089, - "s" - ], - [ - 0.024074, - " " - ], - [ - 0.012076, - "a" - ], - [ - 0.108035, - "n" - ], - [ - 0.048058, - " " - ], - [ - 0.036059, - "e" - ], - [ - 0.030058, - "x" - ], - [ - 0.078102, - "p" - ], - [ - 0.030073, - "e" - ], - [ - 0.036073, - "r" - ], - [ - 0.048074, - "i" - ], - [ - 0.096121, - "m" - ], - [ - 0.090115, - "e" - ], - [ - 0.018073, - "n" - ], - [ - 0.060084, - "t" - ], - [ - 0.054080, - "a" - ], - [ - 0.102028, - "l" - ], - [ - 0.060068, - " " - ], - [ - 0.012057, - "p" - ], - [ - 0.018057, - "l" - ], - [ - 0.054083, - "a" - ], - [ - 0.042070, - "t" - ], - [ - 0.096117, - "f" - ], - [ - 0.066089, - "o" - ], - [ - 0.108132, - "r" - ], - [ - 0.036074, - "m" - ], - [ - 0.036074, - "." - ], - [ - 0.096118, - "\u001b" - ], - [ - 0.084063, - "[" - ], - [ - 0.030056, - "3" - ], - [ - 0.072081, - "9" - ], - [ - 0.054061, - "m" - ], - [ - 0.054077, - "\r\n" - ], - [ - 0.108452, - "~ \u003e" - ], - [ - 0.000533, - " " - ], - [ - 0.060083, - "\u001b" - ], - [ - 0.108131, - "[" - ], - [ - 0.084107, - "9" - ], - [ - 0.024070, - "2" - ], - [ - 0.066090, - "m" - ], - [ - 0.024074, - "B" - ], - [ - 0.090113, - "u" - ], - [ - 0.084070, - "t" - ], - [ - 0.012055, - " " - ], - [ - 0.078087, - "t" - ], - [ - 0.108129, - "r" - ], - [ - 0.084108, - "y" - ], - [ - 0.090112, - " " - ], - [ - 0.078099, - "i" - ], - [ - 0.102124, - "t" - ], - [ - 0.006071, - " " - ], - [ - 0.102125, - "o" - ], - [ - 0.072086, - "u" - ], - [ - 0.012051, - "t" - ], - [ - 0.066073, - " " - ], - [ - 0.006056, - "a" - ], - [ - 0.090112, - "n" - ], - [ - 0.102126, - "d" - ], - [ - 0.096118, - " " - ], - [ - 0.078100, - "s" - ], - [ - 0.072095, - "e" - ], - [ - 0.012073, - "n" - ], - [ - 0.078100, - "d" - ], - [ - 0.072093, - " " - ], - [ - 0.048008, - "u" - ], - [ - 0.048057, - "s" - ], - [ - 0.078084, - " " - ], - [ - 0.042056, - "a" - ], - [ - 0.078115, - " " - ], - [ - 0.030074, - "f" - ], - [ - 0.042071, - "e" - ], - [ - 0.066089, - "e" - ], - [ - 0.102124, - "d" - ], - [ - 0.090115, - "b" - ], - [ - 0.030068, - "a" - ], - [ - 0.078100, - "c" - ], - [ - 0.048043, - "k" - ], - [ - 0.084091, - "!" - ], - [ - 0.108116, - "\u001b" - ], - [ - 0.084119, - "[" - ], - [ - 0.012074, - "3" - ], - [ - 0.072096, - "9" - ], - [ - 0.084105, - "m" - ], - [ - 0.012073, - "\r\n" - ] - ] -} diff --git a/tools/hermit_kvm.json b/tools/hermit_kvm.json deleted file mode 100644 index e2add4188..000000000 --- a/tools/hermit_kvm.json +++ /dev/null @@ -1,3942 +0,0 @@ -{ - "version": 1, - "width": 80, - "height": 24, - "duration": 62.102665, - "command": "./demo_kvm.sh", - "title": "HermitCore within a VM", - "env": { - "TERM": "xterm-256color", - "SHELL": "/bin/sh" - }, - "stdout": [ - [ - 0.004642, - "\u001b[3;J\u001b[H\u001b[2J" - ], - [ - 0.000135, - "~ \u003e" - ], - [ - 0.003563, - " " - ], - [ - 0.102140, - "\u001b" - ], - [ - 0.078113, - "[" - ], - [ - 0.066111, - "9" - ], - [ - 0.078115, - "2" - ], - [ - 0.054098, - "m" - ], - [ - 0.072043, - "#" - ], - [ - 0.048060, - " " - ], - [ - 0.006069, - "H" - ], - [ - 0.036067, - "e" - ], - [ - 0.006092, - "r" - ], - [ - 0.024080, - "m" - ], - [ - 0.084127, - "i" - ], - [ - 0.030083, - "t" - ], - [ - 0.108148, - "C" - ], - [ - 0.084126, - "o" - ], - [ - 0.042096, - "r" - ], - [ - 0.084069, - "e" - ], - [ - 0.018094, - " " - ], - [ - 0.060103, - "i" - ], - [ - 0.090099, - "s" - ], - [ - 0.096132, - " " - ], - [ - 0.054095, - "a" - ], - [ - 0.084123, - "l" - ], - [ - 0.096131, - "s" - ], - [ - 0.030086, - "o" - ], - [ - 0.084115, - " " - ], - [ - 0.108165, - "u" - ], - [ - 0.066045, - "s" - ], - [ - 0.066132, - "a" - ], - [ - 0.030100, - "b" - ], - [ - 0.108136, - "l" - ], - [ - 0.048089, - "e" - ], - [ - 0.096136, - " " - ], - [ - 0.018096, - "a" - ], - [ - 0.042082, - "s" - ], - [ - 0.108032, - " " - ], - [ - 0.102168, - "a" - ], - [ - 0.102133, - " " - ], - [ - 0.054101, - "c" - ], - [ - 0.078117, - "l" - ], - [ - 0.006087, - "a" - ], - [ - 0.096131, - "s" - ], - [ - 0.024084, - "s" - ], - [ - 0.042087, - "i" - ], - [ - 0.042071, - "c" - ], - [ - 0.054024, - "a" - ], - [ - 0.042100, - "l" - ], - [ - 0.030083, - " " - ], - [ - 0.060090, - "u" - ], - [ - 0.006086, - "n" - ], - [ - 0.078116, - "i" - ], - [ - 0.084116, - "k" - ], - [ - 0.072109, - "e" - ], - [ - 0.090127, - "r" - ], - [ - 0.024084, - "n" - ], - [ - 0.060087, - "e" - ], - [ - 0.006053, - "l" - ], - [ - 0.042125, - "." - ], - [ - 0.108119, - " " - ], - [ - 0.042098, - "B" - ], - [ - 0.078120, - "y" - ], - [ - 0.006084, - " " - ], - [ - 0.072107, - "s" - ], - [ - 0.042088, - "e" - ], - [ - 0.084119, - "t" - ], - [ - 0.090106, - "t" - ], - [ - 0.012070, - "i" - ], - [ - 0.006111, - "n" - ], - [ - 0.102146, - "g" - ], - [ - 0.006090, - " " - ], - [ - 0.060090, - "t" - ], - [ - 0.018090, - "h" - ], - [ - 0.102140, - "e" - ], - [ - 0.066110, - "\u001b" - ], - [ - 0.036084, - "[" - ], - [ - 0.024042, - "3" - ], - [ - 0.108180, - "9" - ], - [ - 0.036028, - "m" - ], - [ - 0.102176, - "\r\n" - ], - [ - 0.048337, - "~ \u003e" - ], - [ - 0.002177, - " " - ], - [ - 0.060089, - "\u001b" - ], - [ - 0.024019, - "[" - ], - [ - 0.102121, - "9" - ], - [ - 0.018052, - "2" - ], - [ - 0.012106, - "m" - ], - [ - 0.048087, - "#" - ], - [ - 0.030096, - " " - ], - [ - 0.066102, - "e" - ], - [ - 0.030088, - "n" - ], - [ - 0.090131, - "p" - ], - [ - 0.162207, - "\u0008 \u0008" - ], - [ - 0.006007, - "v" - ], - [ - 0.006056, - "i" - ], - [ - 0.072135, - "r" - ], - [ - 0.024086, - "o" - ], - [ - 0.054085, - "n" - ], - [ - 0.042086, - "m" - ], - [ - 0.012085, - "e" - ], - [ - 0.036088, - "n" - ], - [ - 0.030094, - "t" - ], - [ - 0.066102, - " " - ], - [ - 0.096155, - "v" - ], - [ - 0.078029, - "a" - ], - [ - 0.084101, - "r" - ], - [ - 0.048054, - "i" - ], - [ - 0.066137, - "a" - ], - [ - 0.006103, - "b" - ], - [ - 0.048090, - "l" - ], - [ - 0.054092, - "e" - ], - [ - 0.090130, - " " - ], - [ - 0.072110, - "H" - ], - [ - 0.078125, - "E" - ], - [ - 0.066064, - "R" - ], - [ - 0.030064, - "M" - ], - [ - 0.006116, - "I" - ], - [ - 0.054057, - "T" - ], - [ - 0.006088, - "_" - ], - [ - 0.048102, - "I" - ], - [ - 0.078135, - "S" - ], - [ - 0.030089, - "L" - ], - [ - 0.012089, - "E" - ], - [ - 0.078116, - " " - ], - [ - 0.030091, - "t" - ], - [ - 0.078052, - "p" - ], - [ - 0.210224, - "\u0008 \u0008" - ], - [ - 0.054114, - "o" - ], - [ - 0.042089, - " " - ], - [ - 0.036115, - "q" - ], - [ - 0.012078, - "e" - ], - [ - 0.024100, - "m" - ], - [ - 0.084122, - "u" - ], - [ - 0.030082, - "," - ], - [ - 0.036073, - " " - ], - [ - 0.090103, - "t" - ], - [ - 0.102117, - "h" - ], - [ - 0.066127, - "e" - ], - [ - 0.108151, - " " - ], - [ - 0.066114, - "a" - ], - [ - 0.048102, - "p" - ], - [ - 0.090131, - "p" - ], - [ - 0.108130, - "l" - ], - [ - 0.048022, - "i" - ], - [ - 0.036067, - "c" - ], - [ - 0.096117, - "a" - ], - [ - 0.078123, - "t" - ], - [ - 0.066101, - "i" - ], - [ - 0.024091, - "o" - ], - [ - 0.018101, - "n" - ], - [ - 0.012087, - " " - ], - [ - 0.072110, - "w" - ], - [ - 0.048086, - "i" - ], - [ - 0.048091, - "l" - ], - [ - 0.090028, - "l" - ], - [ - 0.012063, - " " - ], - [ - 0.102125, - "b" - ], - [ - 0.096159, - "e" - ], - [ - 0.006102, - " " - ], - [ - 0.072116, - "s" - ], - [ - 0.006091, - "t" - ], - [ - 0.030078, - "a" - ], - [ - 0.102142, - "r" - ], - [ - 0.108132, - "t" - ], - [ - 0.066081, - "e" - ], - [ - 0.108132, - "d" - ], - [ - 0.030111, - "\u001b" - ], - [ - 0.006090, - "[" - ], - [ - 0.012103, - "3" - ], - [ - 0.024100, - "9" - ], - [ - 0.048086, - "m" - ], - [ - 0.090134, - "\r\n" - ], - [ - 0.078293, - "~ \u003e" - ], - [ - 0.001563, - " " - ], - [ - 0.078120, - "\u001b" - ], - [ - 0.072124, - "[" - ], - [ - 0.024071, - "9" - ], - [ - 0.060085, - "2" - ], - [ - 0.072069, - "m" - ], - [ - 0.060115, - "#" - ], - [ - 0.072116, - " " - ], - [ - 0.078103, - "w" - ], - [ - 0.012086, - "i" - ], - [ - 0.066099, - "t" - ], - [ - 0.078120, - "h" - ], - [ - 0.102146, - "i" - ], - [ - 0.072054, - "n" - ], - [ - 0.090094, - " " - ], - [ - 0.084138, - "a" - ], - [ - 0.066121, - " " - ], - [ - 0.024090, - "v" - ], - [ - 0.042086, - "i" - ], - [ - 0.054087, - "r" - ], - [ - 0.078116, - "t" - ], - [ - 0.108144, - "u" - ], - [ - 0.042087, - "a" - ], - [ - 0.012023, - "l" - ], - [ - 0.096115, - " " - ], - [ - 0.060116, - "m" - ], - [ - 0.018084, - "a" - ], - [ - 0.006092, - "c" - ], - [ - 0.090129, - "h" - ], - [ - 0.072115, - "i" - ], - [ - 0.072115, - "n" - ], - [ - 0.072109, - "e" - ], - [ - 0.042086, - "." - ], - [ - 0.036054, - " " - ], - [ - 0.096105, - "T" - ], - [ - 0.102167, - "h" - ], - [ - 0.108153, - "e" - ], - [ - 0.048089, - " " - ], - [ - 0.060100, - "b" - ], - [ - 0.072112, - "o" - ], - [ - 0.054088, - "o" - ], - [ - 0.012083, - "t" - ], - [ - 0.036097, - " " - ], - [ - 0.042063, - "t" - ], - [ - 0.084099, - "i" - ], - [ - 0.018093, - "m" - ], - [ - 0.018097, - "e" - ], - [ - 0.036079, - " " - ], - [ - 0.042089, - "i" - ], - [ - 0.054086, - "s" - ], - [ - 0.090127, - " " - ], - [ - 0.006085, - "a" - ], - [ - 0.054102, - "b" - ], - [ - 0.018070, - "o" - ], - [ - 0.018080, - "u" - ], - [ - 0.036079, - "t" - ], - [ - 0.078081, - " " - ], - [ - 0.030102, - "1" - ], - [ - 0.036093, - "s" - ], - [ - 0.060104, - "." - ], - [ - 0.102143, - "\u001b" - ], - [ - 0.108139, - "[" - ], - [ - 0.018095, - "3" - ], - [ - 0.030091, - "9" - ], - [ - 0.030068, - "m" - ], - [ - 0.006064, - "\r\n" - ], - [ - 0.018242, - "~ \u003e" - ], - [ - 0.001447, - " " - ], - [ - 0.054099, - "H" - ], - [ - 0.078081, - "E" - ], - [ - 0.084088, - "R" - ], - [ - 0.072092, - "M" - ], - [ - 0.042104, - "I" - ], - [ - 0.072090, - "T" - ], - [ - 0.054089, - "_" - ], - [ - 0.018091, - "I" - ], - [ - 0.012090, - "S" - ], - [ - 0.108148, - "L" - ], - [ - 0.084116, - "E" - ], - [ - 0.024080, - "=" - ], - [ - 0.072091, - "q" - ], - [ - 0.012066, - "e" - ], - [ - 0.030107, - "m" - ], - [ - 0.096148, - "u" - ], - [ - 0.018089, - " " - ], - [ - 0.024096, - "t" - ], - [ - 0.054108, - "i" - ], - [ - 0.006083, - "m" - ], - [ - 0.090122, - "e" - ], - [ - 0.048078, - " " - ], - [ - 0.012032, - "h" - ], - [ - 0.024059, - "e" - ], - [ - 0.078099, - "r" - ], - [ - 0.006124, - "m" - ], - [ - 0.012107, - "i" - ], - [ - 0.090128, - "t" - ], - [ - 0.018089, - "/" - ], - [ - 0.084124, - "u" - ], - [ - 0.030092, - "s" - ], - [ - 0.072118, - "r" - ], - [ - 0.054055, - "/" - ], - [ - 0.108115, - "t" - ], - [ - 0.030069, - "e" - ], - [ - 0.090165, - "s" - ], - [ - 0.072109, - "t" - ], - [ - 0.078119, - "s" - ], - [ - 0.102150, - "/" - ], - [ - 0.078105, - "h" - ], - [ - 0.078137, - "e" - ], - [ - 0.078035, - "l" - ], - [ - 0.102107, - "l" - ], - [ - 0.042115, - "o" - ], - [ - 0.084133, - "\r\n" - ], - [ - 1.157188, - "Hello World!!!\r\n\r\n" - ], - [ - 0.000286, - "qemu: terminating on signal 2 from pid 26119" - ], - [ - 0.000005, - "\r\n" - ], - [ - 0.004099, - "\r\n" - ], - [ - 0.000130, - "1.01user " - ], - [ - 0.000010, - "0.14system 0:01.14elapsed " - ], - [ - 0.000016, - "101%CPU (0avg" - ], - [ - 0.000021, - "text+0avg" - ], - [ - 0.000005, - "data 59464maxres" - ], - [ - 0.000003, - "ident)" - ], - [ - 0.000003, - "k" - ], - [ - 0.000005, - "\r\n0i" - ], - [ - 0.000004, - "n" - ], - [ - 0.000003, - "puts+0" - ], - [ - 0.000003, - "o" - ], - [ - 0.000003, - "utp" - ], - [ - 0.000004, - "ut" - ], - [ - 0.000003, - "s (0" - ], - [ - 0.000003, - "m" - ], - [ - 0.000003, - "a" - ], - [ - 0.000002, - "j" - ], - [ - 0.000003, - "o" - ], - [ - 0.000003, - "r+" - ], - [ - 0.000010, - "11544mino" - ], - [ - 0.000004, - "r" - ], - [ - 0.000003, - ")p" - ], - [ - 0.000003, - "ag" - ], - [ - 0.000003, - "ef" - ], - [ - 0.000004, - "a" - ], - [ - 0.000004, - "u" - ], - [ - 0.000004, - "lt" - ], - [ - 0.000008, - "s 0swaps" - ], - [ - 0.000003, - "\r\n" - ], - [ - 0.000142, - "~ \u003e" - ], - [ - 0.001468, - " " - ], - [ - 0.096115, - "\u001b" - ], - [ - 0.048025, - "[" - ], - [ - 0.084075, - "9" - ], - [ - 0.102107, - "2" - ], - [ - 0.042054, - "m" - ], - [ - 0.012082, - "#" - ], - [ - 0.078081, - " " - ], - [ - 0.030055, - "T" - ], - [ - 0.018072, - "h" - ], - [ - 0.030072, - "e" - ], - [ - 0.042072, - " " - ], - [ - 0.102124, - "v" - ], - [ - 0.018075, - "a" - ], - [ - 0.078105, - "r" - ], - [ - 0.108034, - "i" - ], - [ - 0.096104, - "a" - ], - [ - 0.090098, - "b" - ], - [ - 0.018084, - "l" - ], - [ - 0.048077, - "e" - ], - [ - 0.066088, - " " - ], - [ - 0.054077, - "H" - ], - [ - 0.090113, - "E" - ], - [ - 0.084108, - "R" - ], - [ - 0.096120, - "M" - ], - [ - 0.066089, - "U" - ], - [ - 0.108043, - "\u0008 \u0008" - ], - [ - 0.090096, - "I" - ], - [ - 0.048056, - "T" - ], - [ - 0.024059, - "_" - ], - [ - 0.054086, - "C" - ], - [ - 0.024071, - "P" - ], - [ - 0.090113, - "U" - ], - [ - 0.036072, - "S" - ], - [ - 0.012071, - " " - ], - [ - 0.048074, - "d" - ], - [ - 0.006070, - "e" - ], - [ - 0.096117, - "f" - ], - [ - 0.048071, - "i" - ], - [ - 0.102043, - "n" - ], - [ - 0.078086, - "e" - ], - [ - 0.018055, - "s" - ], - [ - 0.042057, - " " - ], - [ - 0.018088, - "t" - ], - [ - 0.084103, - "h" - ], - [ - 0.048074, - "e" - ], - [ - 0.090112, - " " - ], - [ - 0.054076, - "n" - ], - [ - 0.108135, - "u" - ], - [ - 0.018074, - "m" - ], - [ - 0.090115, - "b" - ], - [ - 0.096023, - "e" - ], - [ - 0.006056, - "r" - ], - [ - 0.006056, - " " - ], - [ - 0.060067, - "o" - ], - [ - 0.018063, - "f" - ], - [ - 0.012093, - " " - ], - [ - 0.102125, - "v" - ], - [ - 0.054085, - "i" - ], - [ - 0.102124, - "r" - ], - [ - 0.108133, - "t" - ], - [ - 0.036079, - "u" - ], - [ - 0.048068, - "a" - ], - [ - 0.084052, - "l" - ], - [ - 0.060068, - " " - ], - [ - 0.036057, - "c" - ], - [ - 0.060066, - "o" - ], - [ - 0.108157, - "r" - ], - [ - 0.096118, - "e" - ], - [ - 0.042073, - "s" - ], - [ - 0.030073, - "," - ], - [ - 0.108131, - " " - ], - [ - 0.090117, - "w" - ], - [ - 0.072095, - "h" - ], - [ - 0.030043, - "i" - ], - [ - 0.084092, - "l" - ], - [ - 0.030055, - "e" - ], - [ - 0.090138, - "\u001b" - ], - [ - 0.030056, - "[" - ], - [ - 0.066091, - "3" - ], - [ - 0.054074, - "9" - ], - [ - 0.048072, - "m" - ], - [ - 0.078102, - "\r\n" - ], - [ - 0.042195, - "~ \u003e" - ], - [ - 0.001168, - " " - ], - [ - 0.060066, - "\u001b" - ], - [ - 0.096101, - "[" - ], - [ - 0.012083, - "9" - ], - [ - 0.096121, - "2" - ], - [ - 0.054076, - "m" - ], - [ - 0.006073, - "#" - ], - [ - 0.096118, - " " - ], - [ - 0.060084, - "H" - ], - [ - 0.048073, - "E" - ], - [ - 0.012071, - "R" - ], - [ - 0.006076, - "M" - ], - [ - 0.048022, - "I" - ], - [ - 0.006056, - "T" - ], - [ - 0.096103, - "_" - ], - [ - 0.090124, - "M" - ], - [ - 0.054077, - "E" - ], - [ - 0.012070, - "M" - ], - [ - 0.048077, - " " - ], - [ - 0.066087, - "s" - ], - [ - 0.024071, - "p" - ], - [ - 0.078101, - "e" - ], - [ - 0.108130, - "c" - ], - [ - 0.066090, - "i" - ], - [ - 0.108008, - "f" - ], - [ - 0.084090, - "i" - ], - [ - 0.078085, - "e" - ], - [ - 0.066108, - "s" - ], - [ - 0.096112, - " " - ], - [ - 0.006070, - "t" - ], - [ - 0.096117, - "h" - ], - [ - 0.036074, - "e" - ], - [ - 0.036073, - " " - ], - [ - 0.090111, - "m" - ], - [ - 0.042073, - "e" - ], - [ - 0.012072, - "m" - ], - [ - 0.012015, - "o" - ], - [ - 0.006056, - "r" - ], - [ - 0.066074, - "y" - ], - [ - 0.102137, - " " - ], - [ - 0.018069, - "s" - ], - [ - 0.102125, - "i" - ], - [ - 0.078101, - "z" - ], - [ - 0.096119, - "e" - ], - [ - 0.108130, - " " - ], - [ - 0.066089, - "o" - ], - [ - 0.108100, - "f" - ], - [ - 0.036058, - " " - ], - [ - 0.048057, - "t" - ], - [ - 0.108116, - "h" - ], - [ - 0.018097, - "e" - ], - [ - 0.012072, - " " - ], - [ - 0.048074, - "v" - ], - [ - 0.006072, - "i" - ], - [ - 0.006070, - "r" - ], - [ - 0.036071, - "t" - ], - [ - 0.006073, - "u" - ], - [ - 0.078102, - "a" - ], - [ - 0.024072, - "l" - ], - [ - 0.078067, - " " - ], - [ - 0.066073, - "m" - ], - [ - 0.030056, - "a" - ], - [ - 0.042057, - "c" - ], - [ - 0.060099, - "h" - ], - [ - 0.102119, - "i" - ], - [ - 0.084105, - "n" - ], - [ - 0.078105, - "e" - ], - [ - 0.060085, - "." - ], - [ - 0.084103, - "\u001b" - ], - [ - 0.042074, - "[" - ], - [ - 0.030074, - "3" - ], - [ - 0.090052, - "9" - ], - [ - 0.096103, - "m" - ], - [ - 0.096104, - "\r\n" - ], - [ - 0.024214, - "~ \u003e" - ], - [ - 0.001179, - " " - ], - [ - 0.024096, - "H" - ], - [ - 0.102122, - "E" - ], - [ - 0.006077, - "R" - ], - [ - 0.078102, - "M" - ], - [ - 0.042029, - "I" - ], - [ - 0.054079, - "T" - ], - [ - 0.054076, - "_" - ], - [ - 0.054084, - "I" - ], - [ - 0.084119, - "S" - ], - [ - 0.090118, - "L" - ], - [ - 0.042082, - "E" - ], - [ - 0.072105, - "=" - ], - [ - 0.060095, - "q" - ], - [ - 0.042085, - "e" - ], - [ - 0.084107, - "m" - ], - [ - 0.018057, - "u" - ], - [ - 0.042084, - " " - ], - [ - 0.036063, - "H" - ], - [ - 0.030078, - "E" - ], - [ - 0.018076, - "R" - ], - [ - 0.084111, - "M" - ], - [ - 0.030080, - "I" - ], - [ - 0.078108, - "T" - ], - [ - 0.060082, - "_" - ], - [ - 0.024075, - "C" - ], - [ - 0.036084, - "P" - ], - [ - 0.072099, - "U" - ], - [ - 0.012045, - "S" - ], - [ - 0.066096, - "=" - ], - [ - 0.072109, - "4" - ], - [ - 0.072102, - " " - ], - [ - 0.108141, - "H" - ], - [ - 0.042072, - "E" - ], - [ - 0.024079, - "R" - ], - [ - 0.048080, - "M" - ], - [ - 0.066098, - "I" - ], - [ - 0.066101, - "T" - ], - [ - 0.066106, - "_" - ], - [ - 0.036016, - "M" - ], - [ - 0.090107, - "E" - ], - [ - 0.078080, - "M" - ], - [ - 0.096154, - "=" - ], - [ - 0.096125, - "1" - ], - [ - 0.048074, - "G" - ], - [ - 0.066100, - " " - ], - [ - 0.006079, - "h" - ], - [ - 0.072095, - "e" - ], - [ - 0.084120, - "r" - ], - [ - 0.066066, - "m" - ], - [ - 0.048105, - "i" - ], - [ - 0.084100, - "t" - ], - [ - 0.054079, - "/" - ], - [ - 0.018075, - "u" - ], - [ - 0.012085, - "s" - ], - [ - 0.078110, - "r" - ], - [ - 0.054082, - "/" - ], - [ - 0.006075, - "b" - ], - [ - 0.030073, - "e" - ], - [ - 0.048084, - "n" - ], - [ - 0.030089, - "c" - ], - [ - 0.036048, - "h" - ], - [ - 0.096095, - "m" - ], - [ - 0.066074, - "a" - ], - [ - 0.036102, - "r" - ], - [ - 0.090122, - "k" - ], - [ - 0.108140, - "s" - ], - [ - 0.090117, - "/" - ], - [ - 0.084112, - "s" - ], - [ - 0.036071, - "t" - ], - [ - 0.108137, - "r" - ], - [ - 0.084029, - "e" - ], - [ - 0.018059, - "a" - ], - [ - 0.078078, - "m" - ], - [ - 0.054061, - "\r\n" - ], - [ - 1.094708, - "-------------------------------------------------------------\r\nSTREAM version $Revision: 5.10 $\r\n-------------------------------------------------------------\r\nThis system uses 8 bytes per array element.\r\n-------------------------------------------------------------\r\nArray size = 14000000 (elements), Offset = 0 (elements)\r\nMemory per array = 106.8 MiB (= 0.1 GiB).\r\nTotal memory required = 320.4 MiB (= 0.3 GiB).\r\nEach kernel will be executed 100 times.\r\n The *best* time for each kernel (excluding the first iteration)\r\n will be used to compute the reported bandwidth.\r\n-------------------------------------------------------------\r\nNumber of Threads requested = 4\r\nNumber of Threads counted = 4\r\n" - ], - [ - 0.000277, - "-------------------------------------------------------------\r\nYour clock granularity/precision appears to be 1 microseconds.\r\nEach test below will take on the order of 7122 microseconds.\r\n (= 7122 clock ticks)\r\nIncrease the size of the arrays if this shows that\r\nyou are not getting at least 20 clock ticks per test.\r\n-------------------------------------------------------------\r\nWARNING -- The above is only a rough guideline.\r\nFor best results, please be sure you know the\r\n" - ], - [ - 0.000038, - "precision of your system timer.\r\n" - ], - [ - 0.000123, - "-------------------------------------------------------------\r\n" - ], - [ - 5.250874, - "Function Best Rate MB/s Avg time Min time Max time\r\n" - ], - [ - 0.000265, - "Copy: 23538.3 0.009590 0.009516 0.009647\r\n" - ], - [ - 0.000170, - "Scale: 20853.9 0.010799 0.010741 0.010861\r\n" - ], - [ - 0.000118, - "Add: 20874.9 0.016152 0.016096 0.016249\r\n" - ], - [ - 0.000139, - "Triad: 21194.5 0.015923 0.015853 0.016030\r\n" - ], - [ - 0.000143, - "-------------------------------------------------------------\r\n" - ], - [ - 0.078512, - "Solution Validates: avg error less than 1.000000e-13 on all three arrays\r\n" - ], - [ - 0.000097, - "-------------------------------------------------------------\r\n" - ], - [ - 0.002830, - "Did HermitCore receive an exception?\r\n" - ], - [ - 0.000004, - "qemu: terminating on signal 2 from pid 26144\r\n" - ], - [ - 0.005386, - "\r\n" - ], - [ - 0.000166, - "~ \u003e" - ], - [ - 0.001717, - " " - ], - [ - 0.024097, - "\u001b" - ], - [ - 0.060091, - "[" - ], - [ - 0.084023, - "9" - ], - [ - 0.006057, - "2" - ], - [ - 0.078086, - "m" - ], - [ - 0.090119, - "#" - ], - [ - 0.090119, - " " - ], - [ - 0.084106, - "H" - ], - [ - 0.024072, - "e" - ], - [ - 0.048072, - "r" - ], - [ - 0.036074, - "m" - ], - [ - 0.042071, - "i" - ], - [ - 0.084108, - "t" - ], - [ - 0.090112, - "C" - ], - [ - 0.036005, - "o" - ], - [ - 0.078085, - "r" - ], - [ - 0.018057, - "e" - ], - [ - 0.012055, - "'" - ], - [ - 0.036086, - "s" - ], - [ - 0.030073, - " " - ], - [ - 0.096119, - "k" - ], - [ - 0.030075, - "e" - ], - [ - 0.090110, - "r" - ], - [ - 0.036075, - "n" - ], - [ - 0.066086, - "e" - ], - [ - 0.066089, - "l" - ], - [ - 0.012072, - " " - ], - [ - 0.102018, - "m" - ], - [ - 0.048055, - "e" - ], - [ - 0.024057, - "s" - ], - [ - 0.012057, - "s" - ], - [ - 0.060098, - "a" - ], - [ - 0.042069, - "g" - ], - [ - 0.078102, - "e" - ], - [ - 0.018072, - "s" - ], - [ - 0.102124, - " " - ], - [ - 0.042071, - "a" - ], - [ - 0.108130, - "r" - ], - [ - 0.042073, - "e" - ], - [ - 0.078085, - " " - ], - [ - 0.078003, - "p" - ], - [ - 0.036058, - "u" - ], - [ - 0.102108, - "b" - ], - [ - 0.036059, - "l" - ], - [ - 0.078128, - "i" - ], - [ - 0.012071, - "s" - ], - [ - 0.102125, - "h" - ], - [ - 0.066087, - "e" - ], - [ - 0.078101, - "d" - ], - [ - 0.054075, - " " - ], - [ - 0.048074, - "b" - ], - [ - 0.066089, - "y" - ], - [ - 0.048025, - " " - ], - [ - 0.108115, - "s" - ], - [ - 0.042057, - "e" - ], - [ - 0.078114, - "t" - ], - [ - 0.036070, - "t" - ], - [ - 0.060081, - "i" - ], - [ - 0.066089, - "n" - ], - [ - 0.096118, - "g" - ], - [ - 0.030070, - " " - ], - [ - 0.066089, - "t" - ], - [ - 0.042073, - "h" - ], - [ - 0.054077, - "e" - ], - [ - 0.006050, - " " - ], - [ - 0.096103, - "e" - ], - [ - 0.108116, - "n" - ], - [ - 0.072121, - "v" - ], - [ - 0.102124, - "i" - ], - [ - 0.102125, - "r" - ], - [ - 0.048072, - "o" - ], - [ - 0.054077, - "n" - ], - [ - 0.048071, - "m" - ], - [ - 0.054078, - "e" - ], - [ - 0.042073, - "n" - ], - [ - 0.048039, - "t" - ], - [ - 0.102109, - "\u001b" - ], - [ - 0.078085, - "[" - ], - [ - 0.090140, - "3" - ], - [ - 0.054075, - "9" - ], - [ - 0.006070, - "m" - ], - [ - 0.102124, - "\r\n" - ], - [ - 0.060203, - "~ \u003e" - ], - [ - 0.001293, - " " - ], - [ - 0.096107, - "\u001b" - ], - [ - 0.006084, - "[" - ], - [ - 0.066087, - "9" - ], - [ - 0.048074, - "2" - ], - [ - 0.030077, - "m" - ], - [ - 0.054071, - "#" - ], - [ - 0.012071, - " " - ], - [ - 0.012073, - "H" - ], - [ - 0.030072, - "E" - ], - [ - 0.036072, - "R" - ], - [ - 0.030074, - "M" - ], - [ - 0.048041, - "I" - ], - [ - 0.048058, - "T" - ], - [ - 0.030056, - "_" - ], - [ - 0.096103, - "V" - ], - [ - 0.030085, - "E" - ], - [ - 0.048072, - "R" - ], - [ - 0.042071, - "B" - ], - [ - 0.078099, - "O" - ], - [ - 0.108132, - "S" - ], - [ - 0.066088, - "E" - ], - [ - 0.108129, - " " - ], - [ - 0.024077, - "t" - ], - [ - 0.012031, - "o" - ], - [ - 0.048058, - " " - ], - [ - 0.036055, - "1" - ], - [ - 0.024057, - "." - ], - [ - 0.084120, - "\u001b" - ], - [ - 0.024072, - "[" - ], - [ - 0.054076, - "3" - ], - [ - 0.048073, - "9" - ], - [ - 0.072095, - "m" - ], - [ - 0.096118, - "\r\n" - ], - [ - 0.096214, - "~ \u003e" - ], - [ - 0.001054, - " " - ], - [ - 0.102034, - "H" - ], - [ - 0.054061, - "E" - ], - [ - 0.066134, - "R" - ], - [ - 0.006079, - "M" - ], - [ - 0.006079, - "I" - ], - [ - 0.084118, - "T" - ], - [ - 0.060093, - "_" - ], - [ - 0.006074, - "I" - ], - [ - 0.066107, - "S" - ], - [ - 0.030085, - "L" - ], - [ - 0.030082, - "E" - ], - [ - 0.030062, - "=" - ], - [ - 0.018031, - "q" - ], - [ - 0.030084, - "e" - ], - [ - 0.060034, - "m" - ], - [ - 0.048082, - "u" - ], - [ - 0.096158, - " " - ], - [ - 0.036093, - "H" - ], - [ - 0.036092, - "E" - ], - [ - 0.102140, - "R" - ], - [ - 0.084120, - "M" - ], - [ - 0.066114, - "I" - ], - [ - 0.024061, - "T" - ], - [ - 0.012021, - "_" - ], - [ - 0.024061, - "C" - ], - [ - 0.072074, - "P" - ], - [ - 0.108161, - "U" - ], - [ - 0.102138, - "S" - ], - [ - 0.096139, - "=" - ], - [ - 0.006085, - "4" - ], - [ - 0.090126, - " " - ], - [ - 0.012087, - "H" - ], - [ - 0.036107, - "E" - ], - [ - 0.036028, - "R" - ], - [ - 0.048076, - "M" - ], - [ - 0.084157, - "I" - ], - [ - 0.036091, - "T" - ], - [ - 0.036119, - "_" - ], - [ - 0.006106, - "V" - ], - [ - 0.096135, - "E" - ], - [ - 0.036085, - "R" - ], - [ - 0.072104, - "B" - ], - [ - 0.018108, - "O" - ], - [ - 0.024019, - "S" - ], - [ - 0.096100, - "E" - ], - [ - 0.012068, - "=" - ], - [ - 0.078118, - "1" - ], - [ - 0.018086, - " " - ], - [ - 0.096141, - "h" - ], - [ - 0.006087, - "e" - ], - [ - 0.042087, - "r" - ], - [ - 0.060120, - "m" - ], - [ - 0.102137, - "i" - ], - [ - 0.060052, - "t" - ], - [ - 0.006062, - "/" - ], - [ - 0.090103, - "u" - ], - [ - 0.018104, - "s" - ], - [ - 0.096163, - "r" - ], - [ - 0.012092, - "/" - ], - [ - 0.054088, - "b" - ], - [ - 0.030088, - "e" - ], - [ - 0.018086, - "n" - ], - [ - 0.066108, - "c" - ], - [ - 0.048085, - "h" - ], - [ - 0.042019, - "m" - ], - [ - 0.012064, - "a" - ], - [ - 0.048054, - "r" - ], - [ - 0.078096, - "k" - ], - [ - 0.030096, - "s" - ], - [ - 0.036129, - "/" - ], - [ - 0.084126, - "s" - ], - [ - 0.036079, - "t" - ], - [ - 0.018091, - "r" - ], - [ - 0.036087, - "e" - ], - [ - 0.102142, - "a" - ], - [ - 0.054036, - "m" - ], - [ - 0.072094, - "\r\n" - ], - [ - 0.024934, - "qemu startup command: qemu-system-x86_64 -nographic -smp 4 -m 2G -net nic,model=rtl8139 -net user,hostfwd=tcp:127.0.0.1:18766-:18766 -chardev file,id=gnc0,path=/tmp/hermit-GccQJB -device pci-serial,chardev=gnc0 -monitor telnet:127.0.0.1:18767,server,nowait -kernel /work/lankes/HermitCore/hermit/tools/../arch/x86/loader/ldhermit.elf -initrd hermit/usr/benchmarks/stream -s -machine accel=kvm -cpu host -net dump\r\n" - ], - [ - 1.119367, - "-------------------------------------------------------------\r\nSTREAM version $Revision: 5.10 $\r\n-------------------------------------------------------------\r\nThis system uses 8 bytes per array element.\r\n-------------------------------------------------------------\r\nArray size = 14000000 (elements), Offset = 0 (elements)\r\nMemory per array = 106.8 MiB (= 0.1 GiB).\r\nTotal memory required = 320.4 MiB (= 0.3 GiB).\r\nEach kernel will be executed 100 times.\r\n The *best* time for each kernel (excluding the first iteration)\r\n will be used to compute the reported bandwidth.\r\n-------------------------------------------------------------\r\nNumber of Threads requested = 4\r\nNumber of Threads counted = 4\r\n-------------------------------------------------------------\r\n" - ], - [ - 0.000015, - "Your clock granularity/precision appears to be 1 microseconds.\r\nEach test below will take on the order of 8969 microseconds.\r\n (= 8969 clock ticks)\r\nIncrease the size of the arrays if this shows that\r\nyou are not getting at least 20 clock ticks per test.\r\n-------------------------------------------------------------\r\nWARNING -- The above is only a rough guideline.\r\n" - ], - [ - 0.000160, - "For best results, please be sure you know the\r\n" - ], - [ - 0.000157, - "precision of your system timer.\r\n" - ], - [ - 0.000154, - "-------------------------------------------------------------\r\n" - ], - [ - 5.174281, - "Function Best Rate MB/s Avg time Min time Max time\r\n" - ], - [ - 0.000171, - "Copy: 32764.7 0.009369 0.006837 0.012350\r\n" - ], - [ - 0.000142, - "Scale: 26661.5 0.010836 0.008402 0.013904\r\n" - ], - [ - 0.000160, - "Add: 27466.1 0.015824 0.012233 0.020037\r\n" - ], - [ - 0.000157, - "Triad: 27652.2 0.015589 0.012151 0.019822\r\n" - ], - [ - 0.000161, - "-------------------------------------------------------------\r\n" - ], - [ - 0.078723, - "Solution Validates: avg error less than 1.000000e-13 on all three arrays\r\n" - ], - [ - 0.000111, - "-------------------------------------------------------------\r\n" - ], - [ - 0.000718, - "qemu: terminating on signal 2 from pid 26173\r\n" - ], - [ - 0.005181, - "\r\nDump kernel log:\r\n================\r\n\r\n" - ], - [ - 0.000017, - "HermitCore loader...\r\nLoader starts at 0x100000 and ends at 0x10b009\r\n" - ], - [ - 0.000015, - "Found mb_info at 0x9500\r\nMap module info at 0x10c000 (ret 0)\r\nMap first page of module 0 at 0x10d000 (ret 0)\r\nModule 0 consists 586\r\nPage pool starts at 0x557000\r\nFree region 0x0 - 0x9fc00\r\nFree region 0x100000 - 0x7ffe0000\r\n" - ], - [ - 0.000012, - "ELF file is located at 0x10d000\r\nMap 791 pages from physical start address 0x10e000 linear to 0x800000\r\nRemap 549 pages from physical start address 0x200000 linear to 0x800000\r\nEntry point: 0x800000\r\ncpuid level 13\r\nPaging features: PSE (2/4Mb) PAE PGE PAT PSE36 NX PSE (1Gb) LM\r\nPhysical adress-width: 40 bits\r\n" - ], - [ - 0.000007, - "Linear adress-width: 48 bits\r\nSysenter instruction: available\r\nSyscall instruction: available\r\nSet XCR0 to 0x7" - ], - [ - 0.000007, - "\r\nCore 0 set per_core offset to 0x0\r\nCore id is set to 0\r\nFound and initialized FPU!\r\n" - ], - [ - 0.000013, - "CPU features: SSE SSE2 SSE3 SSE4.1 SSE4.2 AVX AVX2 FMA MOVBE X2APIC FPU FXSR XSAVE OSXSAVE RDTSCP FSGSBASE BMI1 BMI2 \r\nExt_Save_Area_2: offset 576, size 256\r\nExt_Save_Area_3: offset 0, size 0\r\nExt_Save_Area_4: offset 0, size 0\r\n" - ], - [ - 0.000012, - "HermitCore is running on a hypervisor!\r\nHypervisor Vendor Id: KVMKVMKVM\r\nMaximum input value for hypervisor: 0x40000001\r\nCR0 0x80040033, CR4 0x506a0" - ], - [ - 0.000005, - "\r\nsize of xsave_t: 832\r\nIA32_MISC_ENABLE 0x1" - ], - [ - 0.000007, - "\r\nIA32_PLATFORM_ID 0x0\r\nIA32_CR_PAT 0x7040600070406\r\nPAT use per default writeback." - ], - [ - 0.000006, - "\r\nMTRR is enabled.\r\nFixed-range MTRR is enabled.\r\nMTRR used per default writeback.\r\n" - ], - [ - 0.000005, - "mb_info: 0x9500\r\nmemory_init: base 0x200000, image_size 0x14675b08, limit 0x7ffe0000\r\nFree region 0x0 - 0x9f000" - ], - [ - 0.000003, - "\r\n" - ], - [ - 0.000006, - "Free region 0x100000 - 0x7ffe0000\r\nAdd region 0x14a00000 - 0x7ffe0000\r\nfree list starts at 0x14a00000, limit 0x7ffe0000\r\n" - ], - [ - 0.000009, - "vma_init: reserve vma region 0x800000 - 0x15000000\r\nAdd region 0x100000 - 0x200000\r\nFound MP config table at 0xf64a0\r\nSystem uses Multiprocessing Specification 1.4\r\n" - ], - [ - 0.000009, - "MP features 1: 0\r\nVirtual-Wire mode implemented\r\nFound IOAPIC at 0xfec00000\r\nMap IOAPIC to 0x7fe000\r\nIOAPIC version: 0x11" - ], - [ - 0.000008, - "\r\nMax Redirection Entry: 23\r\nFound 4 cores\r\nFound APIC at 0xfee00000" - ], - [ - 0.000005, - "\r\nEnable X2APIC support!\r\nMaximum LVT Entry: 0x5\r\n" - ], - [ - 0.000005, - "APIC Version: 0x14\r\n" - ], - [ - 0.000005, - "EOI-broadcast: available\r\nBoot processor 0 (ID 0)\r\nProcessor: Intel(R) Xeon(R) CPU E5-2650 v3 @ 2.30GHz\r\n" - ], - [ - 0.000004, - "APIC calibration determined an ICR of 0x9899c4\r\n" - ], - [ - 0.000004, - "CR0 of core 0: 0x8004003b\r\nWakeup application processor 1 via IPI\r\nMap reset vector to 0xd0467\r\n" - ], - [ - 0.000004, - "Enable X2APIC support!\r\n" - ], - [ - 0.000009, - "Processor 1 (local id 1) is entering its idle task\r\nSet XCR0 to 0x7\r\nCore 1 set per_core offset to 0x40\r\nCore id is set to 1\r\nCPU 1 of isle 0 is now online (CR0 0x8004003b, CR4 0x506a0)\r\n" - ], - [ - 0.000010, - "Wakeup application processor 2 via IPI\r\nEnable X2APIC support!\r\nProcessor 2 (local id 2) is entering its idle task\r\nSet XCR0 to 0x7\r\nCore 2 set per_core offset to 0x80\r\nCore id is set to 2" - ], - [ - 0.000003, - "\r\n" - ], - [ - 0.000005, - "CPU 2 of isle 0 is now online (CR0 0x8004003b, CR4 0x506a0)\r\nWakeup application processor 3 via IPI\r\nEnable X2APIC support!\r\nProcessor 3 (local id 3) is entering its idle task\r\n" - ], - [ - 0.000003, - "Set XCR0 to 0x7\r\n" - ], - [ - 0.000007, - "Core 3 set per_core offset to 0xc0\r\nCore id is set to 3\r\nCPU 3 of isle 0 is now online (CR0 0x8004003b, CR4 0x506a0)\r\n" - ], - [ - 0.000009, - "4 cores online\r\nThis is Hermit 1b5e7d-dirty, build date 10517952\r\nIsle 0 of 1 possible isles\r\nKernel starts at 0x800000 and ends at 0x14e75b08\r\nTLS image starts at 0xa24140 and ends at 0xa24160" - ], - [ - 0.000007, - "\r\nKernel BBS starts at 0xa24148 and ends at 0x14e75b08\r\nPer core data starts at 0xa22140 and ends at 0xa24140\r\nPer core size 0x40" - ], - [ - 0.000006, - "\r\nProcessor frequency: 2300 MHz\r\nTotal memory: 2047 MiB\r\nCurrent allocated memory: 335964 KiB\r\n" - ], - [ - 0.000004, - "Current available memory: 1719 MiB\r\nCore 0 is the boot processor\r\n" - ], - [ - 0.000006, - "CPU 0 of isle 0 is now online (CR0 0x8004003b, CR4 0x506a0)\r\nTask 4 use use the memory region [0xde000 - 0xdffff] as stack\r\nTask 4 use use the memory region [0xf0000 - 0xf1fff] as IST1" - ], - [ - 0.000006, - "\r\nstart new task 4 on core 0 with stack address 0xde000\r\nTLS of task 4 on core 0 starts at 0xc0250 (TLS)" - ], - [ - 0.000006, - "\r\nInitd is running\r\n" - ], - [ - 0.000004, - "netif_set_ipaddr: netif address being changed\r\n" - ], - [ - 0.000003, - "netif: IP address of interface ?? set to 127.0.0.1" - ], - [ - 0.000010, - "\r\nnetif: netmask of interface ?? set to 255.0.0.0\r\nnetif: GW address of interface ?? set to 127.0.0.1" - ], - [ - 0.000005, - "\r\nnetif: added interface lo IP addr 127.0.0.1 netmask 255.0.0.0 gw 127.0.0.1\r\nTask 5 use use the memory region [0xf8000 - 0xf9fff] as stack\r\nTask 5 use use the memory region [0x10a000 - 0x10bfff] as IST1" - ], - [ - 0.000004, - "\r\n" - ], - [ - 0.000005, - "start new task 5 on core 0 with stack address 0xf8000\r\nsys_thread_new: create_kernel_task 0, id = 5, prio = 16\r\n" - ], - [ - 0.000003, - "TLS of task 5 on core 0 starts at 0xc0390 (TLS)\r\nLwIP's tcpip thread has task id 5\r\n" - ], - [ - 0.000011, - "TCP/IP initialized.\r\nnetif: IP address of interface ?? set to 0.0.0.0\r\nnetif: netmask of interface ?? set to 0.0.0.0\r\nnetif: GW address of interface ?? set to 0.0.0.0\r\nrtl8139if_init: Found RealTek RTL8139 at iobase 0xc000 (irq 11)\r\nrtl8139if_init: MAC address 52 54 00 12 34 56 " - ], - [ - 0.000007, - "\r\nRTL8139: CR = 0xd, ISR = 0x0, speed = 10 mbps\r\nnetif: added interface en IP addr 0.0.0.0 netmask 0.0.0.0 gw 0.0.0.0\r\nnetif: setting default interface en\r\nStarting DHCPD..." - ], - [ - 0.000007, - "\r\nnetif_set_ipaddr: netif address being changed\r\nnetif: IP address of interface en set to 10.0.2.15\r\n" - ], - [ - 0.000005, - "netif: netmask of interface en set to 255.255.255.0\r\nnetif: GW address of interface en set to 10.0.2.2\r\nBoot time: 70 ms\r\n" - ], - [ - 0.000004, - "TCP server is listening.\r\nEstablish IP connection" - ], - [ - 0.000004, - "\r\n" - ], - [ - 0.000004, - "Task 6 use use the memory region [0x115000 - 0x116fff] as stack\r\n" - ], - [ - 0.000008, - "Task 6 use use the memory region [0x127000 - 0x128fff] as IST1\r\nstart new thread 6 on core 1 with stack address 0x115000\r\nTLS of task 6 on core 1 starts at 0xc1d10 (TLS)" - ], - [ - 0.000007, - "\r\nTask 7 use use the memory region [0x12b000 - 0x12cfff] as stack\r\nTask 7 use use the memory region [0x13d000 - 0x13efff] as IST1" - ], - [ - 0.000007, - "\r\nstart new thread 7 on core 2 with stack address 0x12b000\r\nTLS of task 7 on core 2 starts at 0xc1d50 (TLS)" - ], - [ - 0.000009, - "\r\nTask 8 use use the memory region [0x141000 - 0x142fff] as stack\r\nTask 8 use use the memory region [0x153000 - 0x154fff] as IST1" - ], - [ - 0.000007, - "\r\nstart new thread 8 on core 3 with stack address 0x141000\r\nTLS of task 8 on core 3 starts at 0xc1d90 (TLS)\r\nTerminate task: 7, return value 0" - ], - [ - 0.000003, - "\r\n" - ], - [ - 0.000011, - "Terminate task: 8, return va\r\n" - ], - [ - 0.000137, - "~ \u003e" - ], - [ - 0.001464, - " " - ], - [ - 0.084139, - "\u001b" - ], - [ - 0.072095, - "[" - ], - [ - 0.030072, - "9" - ], - [ - 0.054003, - "2" - ], - [ - 0.036059, - "m" - ], - [ - 0.102109, - "H" - ], - [ - 0.036057, - "e" - ], - [ - 0.108157, - "r" - ], - [ - 0.072094, - "m" - ], - [ - 0.066093, - "i" - ], - [ - 0.048077, - "t" - ], - [ - 0.072091, - "C" - ], - [ - 0.042072, - "o" - ], - [ - 0.060084, - "r" - ], - [ - 0.018075, - "e" - ], - [ - 0.060034, - " " - ], - [ - 0.078084, - "(" - ], - [ - 0.024055, - "\u001b" - ], - [ - 0.066073, - "[" - ], - [ - 0.066114, - "3" - ], - [ - 0.102126, - "1" - ], - [ - 0.024077, - "m" - ], - [ - 0.042072, - "h" - ], - [ - 0.084107, - "t" - ], - [ - 0.018073, - "t" - ], - [ - 0.024072, - "p" - ], - [ - 0.066088, - ":" - ], - [ - 0.096056, - "/" - ], - [ - 0.066075, - "/" - ], - [ - 0.024056, - "w" - ], - [ - 0.006056, - "w" - ], - [ - 0.096145, - "w" - ], - [ - 0.090112, - "." - ], - [ - 0.096120, - "h" - ], - [ - 0.030072, - "e" - ], - [ - 0.096120, - "r" - ], - [ - 0.084105, - "m" - ], - [ - 0.042071, - "i" - ], - [ - 0.108069, - "t" - ], - [ - 0.018056, - "c" - ], - [ - 0.018056, - "o" - ], - [ - 0.072080, - "r" - ], - [ - 0.108159, - "e" - ], - [ - 0.042072, - "." - ], - [ - 0.066090, - "o" - ], - [ - 0.108129, - "r" - ], - [ - 0.096120, - "g" - ], - [ - 0.036073, - "\u001b" - ], - [ - 0.078101, - "[" - ], - [ - 0.042060, - "9" - ], - [ - 0.012003, - "2" - ], - [ - 0.066074, - "m" - ], - [ - 0.042057, - ")" - ], - [ - 0.066072, - " " - ], - [ - 0.018085, - "i" - ], - [ - 0.036072, - "s" - ], - [ - 0.060081, - " " - ], - [ - 0.072095, - "a" - ], - [ - 0.018072, - "n" - ], - [ - 0.054080, - " " - ], - [ - 0.030071, - "e" - ], - [ - 0.012071, - "x" - ], - [ - 0.078103, - "p" - ], - [ - 0.096067, - "e" - ], - [ - 0.072081, - "r" - ], - [ - 0.012054, - "i" - ], - [ - 0.096131, - "m" - ], - [ - 0.030072, - "e" - ], - [ - 0.054076, - "n" - ], - [ - 0.054077, - "t" - ], - [ - 0.048077, - "a" - ], - [ - 0.108132, - "l" - ], - [ - 0.090109, - " " - ], - [ - 0.054078, - "p" - ], - [ - 0.102112, - "l" - ], - [ - 0.024004, - "a" - ], - [ - 0.096102, - "t" - ], - [ - 0.054061, - "f" - ], - [ - 0.066098, - "o" - ], - [ - 0.030074, - "r" - ], - [ - 0.006071, - "m" - ], - [ - 0.108132, - "." - ], - [ - 0.060080, - "\u001b" - ], - [ - 0.108130, - "[" - ], - [ - 0.042073, - "3" - ], - [ - 0.090113, - "9" - ], - [ - 0.024057, - "m" - ], - [ - 0.066007, - "\r\n" - ], - [ - 0.078179, - "~ \u003e" - ], - [ - 0.001195, - " " - ], - [ - 0.042076, - "\u001b" - ], - [ - 0.066088, - "[" - ], - [ - 0.006082, - "9" - ], - [ - 0.102119, - "2" - ], - [ - 0.102123, - "m" - ], - [ - 0.006074, - "B" - ], - [ - 0.072061, - "u" - ], - [ - 0.060066, - "t" - ], - [ - 0.066073, - " " - ], - [ - 0.036059, - "t" - ], - [ - 0.060090, - "r" - ], - [ - 0.096119, - "y" - ], - [ - 0.036071, - " " - ], - [ - 0.030070, - "i" - ], - [ - 0.078103, - "t" - ], - [ - 0.006069, - " " - ], - [ - 0.096118, - "o" - ], - [ - 0.096118, - "u" - ], - [ - 0.054044, - "t" - ], - [ - 0.012058, - " " - ], - [ - 0.006055, - "a" - ], - [ - 0.108115, - "n" - ], - [ - 0.012085, - "d" - ], - [ - 0.090113, - " " - ], - [ - 0.078100, - "s" - ], - [ - 0.036074, - "e" - ], - [ - 0.060082, - "n" - ], - [ - 0.030073, - "d" - ], - [ - 0.018074, - " " - ], - [ - 0.012069, - "u" - ], - [ - 0.048076, - "s" - ], - [ - 0.030028, - " " - ], - [ - 0.018056, - "a" - ], - [ - 0.030056, - " " - ], - [ - 0.108116, - "f" - ], - [ - 0.012098, - "e" - ], - [ - 0.078100, - "e" - ], - [ - 0.090111, - "d" - ], - [ - 0.078100, - "b" - ], - [ - 0.078103, - "a" - ], - [ - 0.090111, - "c" - ], - [ - 0.048072, - "k" - ], - [ - 0.090076, - "!" - ], - [ - 0.018055, - "\u001b" - ], - [ - 0.036057, - "[" - ], - [ - 0.054062, - "3" - ], - [ - 0.042061, - "9" - ], - [ - 0.042101, - "m" - ], - [ - 0.048072, - "\r\n" - ] - ] -} \ No newline at end of file diff --git a/tools/hermit_openmp.json b/tools/hermit_openmp.json deleted file mode 100644 index 233fec47e..000000000 --- a/tools/hermit_openmp.json +++ /dev/null @@ -1,6126 +0,0 @@ -{ - "version": 1, - "width": 80, - "height": 25, - "duration": 100.784728, - "command": "./demo.sh", - "title": "HermitCore OpenMP Demo", - "env": { - "TERM": "xterm-256color", - "SHELL": "/bin/bash" - }, - "stdout": [ - [ - 0.016490, - "\u001b[3;J\u001b[H\u001b[2J" - ], - [ - 0.000293, - "~ \u003e" - ], - [ - 0.014212, - " " - ], - [ - 0.036097, - "\u001b" - ], - [ - 0.012126, - "[" - ], - [ - 0.096163, - "9" - ], - [ - 0.018081, - "2" - ], - [ - 0.018069, - "m" - ], - [ - 0.030050, - "#" - ], - [ - 0.006067, - " " - ], - [ - 0.024107, - "H" - ], - [ - 0.018125, - "e" - ], - [ - 0.042109, - "r" - ], - [ - 0.096159, - "m" - ], - [ - 0.066121, - "i" - ], - [ - 0.006118, - "t" - ], - [ - 0.090077, - "C" - ], - [ - 0.024090, - "o" - ], - [ - 0.012075, - "f" - ], - [ - 0.204284, - "\u0008 \u0008" - ], - [ - 0.066122, - "r" - ], - [ - 0.048111, - "e" - ], - [ - 0.066127, - " " - ], - [ - 0.030105, - "e" - ], - [ - 0.072085, - "x" - ], - [ - 0.054101, - "t" - ], - [ - 0.012102, - "e" - ], - [ - 0.018106, - "n" - ], - [ - 0.102160, - "d" - ], - [ - 0.018107, - "s" - ], - [ - 0.024109, - " " - ], - [ - 0.084136, - "t" - ], - [ - 0.078135, - "h" - ], - [ - 0.090051, - "e" - ], - [ - 0.006113, - " " - ], - [ - 0.096143, - "m" - ], - [ - 0.090135, - "u" - ], - [ - 0.090167, - "l" - ], - [ - 0.108168, - "t" - ], - [ - 0.072119, - "i" - ], - [ - 0.012108, - "-" - ], - [ - 0.096038, - "k" - ], - [ - 0.024086, - "e" - ], - [ - 0.066090, - "r" - ], - [ - 0.030099, - "n" - ], - [ - 0.090162, - "e" - ], - [ - 0.078137, - "l" - ], - [ - 0.054110, - " " - ], - [ - 0.048100, - "a" - ], - [ - 0.072141, - "p" - ], - [ - 0.042083, - "p" - ], - [ - 0.084156, - "r" - ], - [ - 0.066110, - "o" - ], - [ - 0.084139, - "a" - ], - [ - 0.042080, - "c" - ], - [ - 0.066144, - "h" - ], - [ - 0.048111, - " " - ], - [ - 0.072130, - "a" - ], - [ - 0.054098, - "n" - ], - [ - 0.096121, - "d" - ], - [ - 0.054086, - " " - ], - [ - 0.108176, - "c" - ], - [ - 0.042111, - "o" - ], - [ - 0.018107, - "m" - ], - [ - 0.042108, - "b" - ], - [ - 0.036108, - "i" - ], - [ - 0.066134, - "n" - ], - [ - 0.030076, - "e" - ], - [ - 0.102101, - "s" - ], - [ - 0.042090, - " " - ], - [ - 0.018093, - "i" - ], - [ - 0.018114, - "t" - ], - [ - 0.012100, - " " - ], - [ - 0.012112, - "w" - ], - [ - 0.024109, - "i" - ], - [ - 0.024112, - "t" - ], - [ - 0.090121, - "h" - ], - [ - 0.036050, - "\u001b" - ], - [ - 0.036097, - "[" - ], - [ - 0.096150, - "3" - ], - [ - 0.084157, - "9" - ], - [ - 0.018108, - "m" - ], - [ - 0.048110, - "\r\n" - ], - [ - 0.108524, - "~ \u003e" - ], - [ - 0.000877, - " " - ], - [ - 0.090114, - "\u001b" - ], - [ - 0.102158, - "[" - ], - [ - 0.054110, - "9" - ], - [ - 0.048107, - "2" - ], - [ - 0.072128, - "m" - ], - [ - 0.090157, - "#" - ], - [ - 0.072138, - " " - ], - [ - 0.084054, - "u" - ], - [ - 0.102124, - "n" - ], - [ - 0.012074, - "i" - ], - [ - 0.078098, - "k" - ], - [ - 0.024131, - "e" - ], - [ - 0.066114, - "r" - ], - [ - 0.018124, - "n" - ], - [ - 0.108171, - "e" - ], - [ - 0.048121, - "l" - ], - [ - 0.036040, - " " - ], - [ - 0.084115, - "f" - ], - [ - 0.060078, - "e" - ], - [ - 0.054145, - "a" - ], - [ - 0.060088, - "t" - ], - [ - 0.030125, - "u" - ], - [ - 0.048109, - "r" - ], - [ - 0.006108, - "e" - ], - [ - 0.024083, - "s" - ], - [ - 0.018109, - " " - ], - [ - 0.030014, - "w" - ], - [ - 0.096132, - "h" - ], - [ - 0.066070, - "i" - ], - [ - 0.018107, - "v" - ], - [ - 0.024097, - "\u0008 \u0008" - ], - [ - 0.174250, - "l" - ], - [ - 0.012106, - "e" - ], - [ - 0.042090, - " " - ], - [ - 0.012138, - "p" - ], - [ - 0.006042, - "r" - ], - [ - 0.078105, - "o" - ], - [ - 0.084088, - "v" - ], - [ - 0.108195, - "i" - ], - [ - 0.090146, - "d" - ], - [ - 0.048108, - "i" - ], - [ - 0.060118, - "n" - ], - [ - 0.012115, - "g" - ], - [ - 0.024090, - " " - ], - [ - 0.048077, - "b" - ], - [ - 0.060082, - "e" - ], - [ - 0.060065, - "t" - ], - [ - 0.024106, - "t" - ], - [ - 0.102167, - "e" - ], - [ - 0.102162, - "r" - ], - [ - 0.084145, - " " - ], - [ - 0.030115, - "p" - ], - [ - 0.108109, - "r" - ], - [ - 0.012070, - "o" - ], - [ - 0.024070, - "g" - ], - [ - 0.072131, - "r" - ], - [ - 0.024075, - "a" - ], - [ - 0.078152, - "m" - ], - [ - 0.102152, - "m" - ], - [ - 0.096173, - "a" - ], - [ - 0.084141, - "b" - ], - [ - 0.054040, - "i" - ], - [ - 0.072093, - "l" - ], - [ - 0.036098, - "i" - ], - [ - 0.006065, - "t" - ], - [ - 0.006097, - "y" - ], - [ - 0.060132, - " " - ], - [ - 0.102158, - "a" - ], - [ - 0.072105, - "n" - ], - [ - 0.060151, - "d" - ], - [ - 0.042083, - " " - ], - [ - 0.006072, - "s" - ], - [ - 0.066093, - "c" - ], - [ - 0.042086, - "a" - ], - [ - 0.018083, - "l" - ], - [ - 0.006105, - "a" - ], - [ - 0.012096, - "b" - ], - [ - 0.090165, - "i" - ], - [ - 0.078137, - "l" - ], - [ - 0.036093, - "i" - ], - [ - 0.096091, - "t" - ], - [ - 0.030076, - "y" - ], - [ - 0.042051, - "\u001b" - ], - [ - 0.054092, - "[" - ], - [ - 0.018108, - "3" - ], - [ - 0.006125, - "9" - ], - [ - 0.096154, - "m" - ], - [ - 0.006112, - "\r\n" - ], - [ - 0.096624, - "~ \u003e" - ], - [ - 0.000829, - " " - ], - [ - 0.054110, - "\u001b" - ], - [ - 0.102160, - "[" - ], - [ - 0.030080, - "9" - ], - [ - 0.036121, - "2" - ], - [ - 0.030105, - "m" - ], - [ - 0.024109, - "#" - ], - [ - 0.042099, - " " - ], - [ - 0.066020, - "f" - ], - [ - 0.060077, - "o" - ], - [ - 0.030064, - "r" - ], - [ - 0.078151, - " " - ], - [ - 0.078114, - "h" - ], - [ - 0.042095, - "i" - ], - [ - 0.012122, - "e" - ], - [ - 0.006101, - "r" - ], - [ - 0.096177, - "a" - ], - [ - 0.054100, - "r" - ], - [ - 0.054072, - "c" - ], - [ - 0.096150, - "h" - ], - [ - 0.072148, - "i" - ], - [ - 0.036112, - "c" - ], - [ - 0.060117, - "a" - ], - [ - 0.090149, - "l" - ], - [ - 0.072128, - " " - ], - [ - 0.054103, - "s" - ], - [ - 0.018022, - "y" - ], - [ - 0.090105, - "s" - ], - [ - 0.036090, - "t" - ], - [ - 0.054101, - "e" - ], - [ - 0.096151, - "m" - ], - [ - 0.078124, - "s" - ], - [ - 0.102175, - "." - ], - [ - 0.090149, - "\u001b" - ], - [ - 0.108131, - "[" - ], - [ - 0.030054, - "3" - ], - [ - 0.012085, - "9" - ], - [ - 0.018098, - "m" - ], - [ - 0.066130, - "\r\n" - ], - [ - 0.072639, - "~ \u003e\r\n~ \u003e" - ], - [ - 0.000893, - " " - ], - [ - 0.072091, - "\u001b" - ], - [ - 0.102107, - "[" - ], - [ - 0.066102, - "9" - ], - [ - 0.030095, - "2" - ], - [ - 0.042083, - "m" - ], - [ - 0.042126, - "#" - ], - [ - 0.042101, - " " - ], - [ - 0.090164, - "B" - ], - [ - 0.030107, - "y" - ], - [ - 0.018102, - " " - ], - [ - 0.066099, - "s" - ], - [ - 0.072145, - "t" - ], - [ - 0.060085, - "a" - ], - [ - 0.006108, - "r" - ], - [ - 0.060117, - "t" - ], - [ - 0.018107, - "i" - ], - [ - 0.048106, - "n" - ], - [ - 0.102131, - "g" - ], - [ - 0.078096, - " " - ], - [ - 0.084099, - "a" - ], - [ - 0.018089, - " " - ], - [ - 0.066110, - "H" - ], - [ - 0.072134, - "g" - ], - [ - 0.120179, - "\u0008 \u0008" - ], - [ - 0.198255, - "e" - ], - [ - 0.036120, - "r" - ], - [ - 0.048011, - "m" - ], - [ - 0.030065, - "i" - ], - [ - 0.102138, - "t" - ], - [ - 0.006115, - "C" - ], - [ - 0.054119, - "o" - ], - [ - 0.024113, - "r" - ], - [ - 0.036102, - "e" - ], - [ - 0.006126, - " " - ], - [ - 0.018096, - "a" - ], - [ - 0.060121, - "p" - ], - [ - 0.096047, - "p" - ], - [ - 0.036067, - "l" - ], - [ - 0.060097, - "i" - ], - [ - 0.048119, - "c" - ], - [ - 0.054141, - "a" - ], - [ - 0.102159, - "t" - ], - [ - 0.018110, - "i" - ], - [ - 0.048112, - "o" - ], - [ - 0.054126, - "n" - ], - [ - 0.096028, - "," - ], - [ - 0.096139, - " " - ], - [ - 0.018070, - "c" - ], - [ - 0.066104, - "o" - ], - [ - 0.102176, - "r" - ], - [ - 0.072132, - "e" - ], - [ - 0.078101, - "s" - ], - [ - 0.078142, - " " - ], - [ - 0.060119, - "a" - ], - [ - 0.084018, - "r" - ], - [ - 0.072108, - "e" - ], - [ - 0.042055, - " " - ], - [ - 0.042138, - "b" - ], - [ - 0.024078, - "e" - ], - [ - 0.042129, - " " - ], - [ - 0.048097, - "s" - ], - [ - 0.054099, - "p" - ], - [ - 0.108189, - "e" - ], - [ - 0.102109, - "r" - ], - [ - 0.042089, - "a" - ], - [ - 0.078100, - "t" - ], - [ - 0.018106, - "e" - ], - [ - 0.006094, - "d" - ], - [ - 0.042114, - " " - ], - [ - 0.102176, - "f" - ], - [ - 0.066126, - "r" - ], - [ - 0.006100, - "o" - ], - [ - 0.054116, - "m" - ], - [ - 0.054090, - " " - ], - [ - 0.084094, - "L" - ], - [ - 0.090182, - "i" - ], - [ - 0.060091, - "n" - ], - [ - 0.090163, - "u" - ], - [ - 0.048107, - "x" - ], - [ - 0.054111, - " " - ], - [ - 0.090134, - "a" - ], - [ - 0.060100, - "n" - ], - [ - 0.048068, - "d" - ], - [ - 0.018111, - "\u001b" - ], - [ - 0.108184, - "[" - ], - [ - 0.054113, - "3" - ], - [ - 0.060116, - "9" - ], - [ - 0.054114, - "m" - ], - [ - 0.036119, - "\r\n" - ], - [ - 0.036422, - "~ \u003e" - ], - [ - 0.001002, - " " - ], - [ - 0.030122, - "\u001b" - ], - [ - 0.096152, - "[" - ], - [ - 0.048110, - "9" - ], - [ - 0.018097, - "2" - ], - [ - 0.108177, - "m" - ], - [ - 0.018062, - "#" - ], - [ - 0.078083, - " " - ], - [ - 0.090148, - "a" - ], - [ - 0.078160, - " " - ], - [ - 0.078103, - "u" - ], - [ - 0.078123, - "n" - ], - [ - 0.012123, - "i" - ], - [ - 0.030115, - "k" - ], - [ - 0.102101, - "e" - ], - [ - 0.012107, - "r" - ], - [ - 0.042130, - "n" - ], - [ - 0.060119, - "e" - ], - [ - 0.024105, - "l" - ], - [ - 0.108168, - " " - ], - [ - 0.054111, - "i" - ], - [ - 0.024110, - "s" - ], - [ - 0.096146, - " " - ], - [ - 0.030107, - "b" - ], - [ - 0.054087, - "e" - ], - [ - 0.066106, - " " - ], - [ - 0.024116, - "b" - ], - [ - 0.096172, - "o" - ], - [ - 0.108167, - "o" - ], - [ - 0.054113, - "t" - ], - [ - 0.096142, - "e" - ], - [ - 0.096119, - "d" - ], - [ - 0.066155, - " " - ], - [ - 0.102155, - "o" - ], - [ - 0.048082, - "n" - ], - [ - 0.018123, - " " - ], - [ - 0.090147, - "t" - ], - [ - 0.006118, - "h" - ], - [ - 0.018064, - "e" - ], - [ - 0.042087, - "s" - ], - [ - 0.102124, - "e" - ], - [ - 0.108201, - " " - ], - [ - 0.102156, - "c" - ], - [ - 0.030123, - "o" - ], - [ - 0.012111, - "r" - ], - [ - 0.012107, - "e" - ], - [ - 0.108138, - "s" - ], - [ - 0.084157, - " " - ], - [ - 0.066118, - "w" - ], - [ - 0.018098, - "i" - ], - [ - 0.072159, - "t" - ], - [ - 0.030106, - "h" - ], - [ - 0.108176, - " " - ], - [ - 0.030109, - "t" - ], - [ - 0.078080, - "h" - ], - [ - 0.006053, - "e" - ], - [ - 0.108195, - " " - ], - [ - 0.042078, - "a" - ], - [ - 0.030101, - "p" - ], - [ - 0.036126, - "p" - ], - [ - 0.048105, - "l" - ], - [ - 0.096149, - "i" - ], - [ - 0.048104, - "c" - ], - [ - 0.012074, - "a" - ], - [ - 0.042050, - "t" - ], - [ - 0.006067, - "i" - ], - [ - 0.012086, - "o" - ], - [ - 0.006090, - "n" - ], - [ - 0.018120, - "." - ], - [ - 0.048127, - "\u001b" - ], - [ - 0.054110, - "[" - ], - [ - 0.090146, - "3" - ], - [ - 0.078116, - "9" - ], - [ - 0.060058, - "m" - ], - [ - 0.048095, - "\r\n" - ], - [ - 0.060455, - "~ \u003e" - ], - [ - 0.000975, - " " - ], - [ - 0.102175, - "\u001b" - ], - [ - 0.042081, - "[" - ], - [ - 0.030122, - "9" - ], - [ - 0.066117, - "2" - ], - [ - 0.066071, - "m" - ], - [ - 0.048116, - "#" - ], - [ - 0.060139, - " " - ], - [ - 0.090140, - "C" - ], - [ - 0.066125, - "o" - ], - [ - 0.072135, - "n" - ], - [ - 0.042103, - "s" - ], - [ - 0.108153, - "\u0008 \u0008" - ], - [ - 0.186224, - "s" - ], - [ - 0.072149, - "e" - ], - [ - 0.042095, - "q" - ], - [ - 0.090165, - "u" - ], - [ - 0.006106, - "e" - ], - [ - 0.030106, - "n" - ], - [ - 0.084142, - "t" - ], - [ - 0.096046, - "l" - ], - [ - 0.030094, - "y" - ], - [ - 0.054039, - "," - ], - [ - 0.048136, - " " - ], - [ - 0.024127, - "H" - ], - [ - 0.072146, - "e" - ], - [ - 0.108164, - "r" - ], - [ - 0.066122, - "m" - ], - [ - 0.024107, - "i" - ], - [ - 0.042056, - "t" - ], - [ - 0.042107, - "C" - ], - [ - 0.024034, - "o" - ], - [ - 0.066153, - "r" - ], - [ - 0.066138, - "e" - ], - [ - 0.006130, - " " - ], - [ - 0.048096, - "i" - ], - [ - 0.012122, - "s" - ], - [ - 0.006124, - " " - ], - [ - 0.072099, - "a" - ], - [ - 0.090181, - " " - ], - [ - 0.030104, - "s" - ], - [ - 0.006128, - "i" - ], - [ - 0.012077, - "n" - ], - [ - 0.096169, - "p" - ], - [ - 0.060119, - "\u0008 \u0008" - ], - [ - 0.018104, - "g" - ], - [ - 0.048096, - "l" - ], - [ - 0.090112, - "e" - ], - [ - 0.096165, - "-" - ], - [ - 0.090168, - "a" - ], - [ - 0.036121, - "d" - ], - [ - 0.090165, - "d" - ], - [ - 0.006100, - "r" - ], - [ - 0.012122, - "e" - ], - [ - 0.018068, - "s" - ], - [ - 0.108149, - "s" - ], - [ - 0.060131, - " " - ], - [ - 0.096153, - "s" - ], - [ - 0.078162, - "p" - ], - [ - 0.066122, - "a" - ], - [ - 0.042111, - "c" - ], - [ - 0.078129, - "e" - ], - [ - 0.054017, - " " - ], - [ - 0.054086, - "o" - ], - [ - 0.084130, - "p" - ], - [ - 0.018113, - "e" - ], - [ - 0.012096, - "r" - ], - [ - 0.078153, - "a" - ], - [ - 0.060117, - "t" - ], - [ - 0.030109, - "i" - ], - [ - 0.090157, - "n" - ], - [ - 0.018066, - "g" - ], - [ - 0.090149, - " " - ], - [ - 0.096173, - "s" - ], - [ - 0.036111, - "y" - ], - [ - 0.012110, - "s" - ], - [ - 0.024112, - "t" - ], - [ - 0.036104, - "e" - ], - [ - 0.108166, - "m" - ], - [ - 0.054067, - " " - ], - [ - 0.006101, - "w" - ], - [ - 0.024125, - "h" - ], - [ - 0.090157, - "i" - ], - [ - 0.072133, - "c" - ], - [ - 0.054110, - "h" - ], - [ - 0.090147, - "\u001b" - ], - [ - 0.108163, - "[" - ], - [ - 0.060045, - "3" - ], - [ - 0.096180, - "9" - ], - [ - 0.024127, - "m" - ], - [ - 0.090137, - "\r\n" - ], - [ - 0.090657, - "~ \u003e" - ], - [ - 0.000880, - " " - ], - [ - 0.036049, - "\u001b" - ], - [ - 0.018049, - "[" - ], - [ - 0.018068, - "9" - ], - [ - 0.072117, - "2" - ], - [ - 0.006060, - "m" - ], - [ - 0.030104, - "#" - ], - [ - 0.030130, - " " - ], - [ - 0.054113, - "p" - ], - [ - 0.108159, - "r" - ], - [ - 0.036135, - "o" - ], - [ - 0.036064, - "m" - ], - [ - 0.078100, - "i" - ], - [ - 0.048106, - "s" - ], - [ - 0.078151, - "e" - ], - [ - 0.066123, - " " - ], - [ - 0.036111, - "a" - ], - [ - 0.018105, - " " - ], - [ - 0.090135, - "l" - ], - [ - 0.096165, - "o" - ], - [ - 0.084103, - "w" - ], - [ - 0.024118, - "e" - ], - [ - 0.090103, - "r" - ], - [ - 0.090118, - " " - ], - [ - 0.006126, - "O" - ], - [ - 0.030111, - "S" - ], - [ - 0.054111, - " " - ], - [ - 0.078157, - "n" - ], - [ - 0.102052, - "o" - ], - [ - 0.072112, - "i" - ], - [ - 0.042077, - "s" - ], - [ - 0.054094, - "e" - ], - [ - 0.108167, - " " - ], - [ - 0.012100, - "a" - ], - [ - 0.054116, - "n" - ], - [ - 0.018105, - "d" - ], - [ - 0.012108, - " " - ], - [ - 0.024069, - "b" - ], - [ - 0.030031, - "e" - ], - [ - 0.054095, - "t" - ], - [ - 0.078097, - "t" - ], - [ - 0.012109, - "e" - ], - [ - 0.066138, - "r" - ], - [ - 0.078138, - " " - ], - [ - 0.030102, - "s" - ], - [ - 0.066139, - "c" - ], - [ - 0.006117, - "a" - ], - [ - 0.072093, - "l" - ], - [ - 0.072073, - "a" - ], - [ - 0.006065, - "b" - ], - [ - 0.006065, - "i" - ], - [ - 0.102181, - "l" - ], - [ - 0.042126, - "i" - ], - [ - 0.042111, - "t" - ], - [ - 0.024103, - "y" - ], - [ - 0.048108, - "." - ], - [ - 0.030084, - "\u001b" - ], - [ - 0.054082, - "[" - ], - [ - 0.084086, - "3" - ], - [ - 0.036089, - "9" - ], - [ - 0.072090, - "m" - ], - [ - 0.102149, - "\r\n" - ], - [ - 0.042454, - "~ \u003e\r\n~ \u003e" - ], - [ - 0.000937, - " " - ], - [ - 0.066154, - "\u001b" - ], - [ - 0.084038, - "[" - ], - [ - 0.072087, - "9" - ], - [ - 0.030068, - "2" - ], - [ - 0.024122, - "m" - ], - [ - 0.060077, - "#" - ], - [ - 0.006127, - " " - ], - [ - 0.084144, - "N" - ], - [ - 0.108165, - "o" - ], - [ - 0.048117, - "w" - ], - [ - 0.054102, - "," - ], - [ - 0.030094, - " " - ], - [ - 0.036033, - "a" - ], - [ - 0.072139, - " " - ], - [ - 0.084114, - "q" - ], - [ - 0.012122, - "u" - ], - [ - 0.018099, - "i" - ], - [ - 0.018130, - "c" - ], - [ - 0.096163, - "k" - ], - [ - 0.018091, - " " - ], - [ - 0.006071, - "t" - ], - [ - 0.054073, - "e" - ], - [ - 0.012098, - "s" - ], - [ - 0.018140, - "t" - ], - [ - 0.012104, - " " - ], - [ - 0.108141, - "v" - ], - [ - 0.090165, - "i" - ], - [ - 0.042100, - "a" - ], - [ - 0.090109, - " " - ], - [ - 0.066084, - "H" - ], - [ - 0.084119, - "e" - ], - [ - 0.042096, - "l" - ], - [ - 0.036109, - "l" - ], - [ - 0.048076, - "o" - ], - [ - 0.072148, - "W" - ], - [ - 0.060127, - "o" - ], - [ - 0.108167, - "r" - ], - [ - 0.072107, - "l" - ], - [ - 0.030068, - "d" - ], - [ - 0.102160, - "\u001b" - ], - [ - 0.006056, - "[" - ], - [ - 0.084115, - "3" - ], - [ - 0.018127, - "9" - ], - [ - 0.036107, - "m" - ], - [ - 0.048116, - "\r\n" - ], - [ - 0.102623, - "~ \u003e" - ], - [ - 0.000860, - " " - ], - [ - 0.060136, - "h" - ], - [ - 0.096141, - "e" - ], - [ - 0.042125, - "r" - ], - [ - 0.060115, - "m" - ], - [ - 0.108183, - "i" - ], - [ - 0.102312, - "t" - ], - [ - 0.053816, - "/" - ], - [ - 0.048049, - "u" - ], - [ - 0.024133, - "s" - ], - [ - 0.030095, - "r" - ], - [ - 0.060119, - "/" - ], - [ - 0.096146, - "t" - ], - [ - 0.102181, - "e" - ], - [ - 0.096150, - "s" - ], - [ - 0.030016, - "t" - ], - [ - 0.102142, - "s" - ], - [ - 0.096153, - "/" - ], - [ - 0.024067, - "h" - ], - [ - 0.072151, - "e" - ], - [ - 0.090148, - "l" - ], - [ - 0.096156, - "l" - ], - [ - 0.078112, - "o" - ], - [ - 0.048069, - "\r\n" - ], - [ - 0.215985, - "Hello World!!!\r\n" - ], - [ - 0.011429, - "~ \u003e" - ], - [ - 0.000598, - " " - ], - [ - 0.078090, - "\u001b" - ], - [ - 0.072111, - "[" - ], - [ - 0.102162, - "9" - ], - [ - 0.048090, - "2" - ], - [ - 0.018122, - "m" - ], - [ - 0.036072, - "#" - ], - [ - 0.036122, - " " - ], - [ - 0.102145, - "L" - ], - [ - 0.048100, - "i" - ], - [ - 0.072098, - "n" - ], - [ - 0.060088, - "u" - ], - [ - 0.036058, - "x" - ], - [ - 0.072150, - "'" - ], - [ - 0.060120, - " " - ], - [ - 0.042107, - "k" - ], - [ - 0.018112, - "e" - ], - [ - 0.090148, - "r" - ], - [ - 0.102114, - "n" - ], - [ - 0.030050, - "e" - ], - [ - 0.054071, - "l" - ], - [ - 0.102160, - "s" - ], - [ - 0.042079, - " " - ], - [ - 0.042130, - "u" - ], - [ - 0.054109, - "\u0008 \u0008" - ], - [ - 0.066121, - "m" - ], - [ - 0.048107, - "e" - ], - [ - 0.108156, - "s" - ], - [ - 0.030046, - "t" - ], - [ - 0.108121, - "\u0008 \u0008" - ], - [ - 0.084141, - "s" - ], - [ - 0.084146, - "a" - ], - [ - 0.066128, - "g" - ], - [ - 0.090154, - "e" - ], - [ - 0.072118, - "s" - ], - [ - 0.006100, - " " - ], - [ - 0.096065, - "s" - ], - [ - 0.090125, - "h" - ], - [ - 0.024073, - "o" - ], - [ - 0.024127, - "w" - ], - [ - 0.048131, - " " - ], - [ - 0.048094, - "t" - ], - [ - 0.096176, - "h" - ], - [ - 0.066088, - "a" - ], - [ - 0.090150, - "t" - ], - [ - 0.096039, - " " - ], - [ - 0.042070, - "C" - ], - [ - 0.108114, - "P" - ], - [ - 0.024097, - "U" - ], - [ - 0.078154, - " " - ], - [ - 0.084147, - "1" - ], - [ - 0.030094, - " " - ], - [ - 0.090167, - "i" - ], - [ - 0.078126, - "s" - ], - [ - 0.012044, - " " - ], - [ - 0.042049, - "u" - ], - [ - 0.066101, - "n" - ], - [ - 0.048108, - "p" - ], - [ - 0.066122, - "l" - ], - [ - 0.108170, - "u" - ], - [ - 0.102177, - "g" - ], - [ - 0.018120, - "g" - ], - [ - 0.096135, - "e" - ], - [ - 0.078103, - "d" - ], - [ - 0.042106, - " " - ], - [ - 0.054095, - "f" - ], - [ - 0.096155, - "r" - ], - [ - 0.054120, - "o" - ], - [ - 0.096141, - "m" - ], - [ - 0.054132, - " " - ], - [ - 0.072115, - "L" - ], - [ - 0.102039, - "i" - ], - [ - 0.036074, - "n" - ], - [ - 0.054072, - "u" - ], - [ - 0.042123, - "x" - ], - [ - 0.042095, - "." - ], - [ - 0.024100, - "\u001b" - ], - [ - 0.042106, - "[" - ], - [ - 0.096142, - "3" - ], - [ - 0.060131, - "9" - ], - [ - 0.084127, - "m" - ], - [ - 0.018042, - "\r\n" - ], - [ - 0.024469, - "~ \u003e" - ], - [ - 0.000988, - " " - ], - [ - 0.012115, - "\u001b" - ], - [ - 0.036113, - "[" - ], - [ - 0.066109, - "9" - ], - [ - 0.102162, - "2" - ], - [ - 0.042034, - "m" - ], - [ - 0.030075, - "#" - ], - [ - 0.012071, - " " - ], - [ - 0.066143, - "A" - ], - [ - 0.024114, - "f" - ], - [ - 0.108192, - "t" - ], - [ - 0.072131, - "e" - ], - [ - 0.012110, - "r" - ], - [ - 0.024082, - " " - ], - [ - 0.072082, - "t" - ], - [ - 0.060088, - "h" - ], - [ - 0.072091, - "e" - ], - [ - 0.006127, - " " - ], - [ - 0.096121, - "t" - ], - [ - 0.024122, - "e" - ], - [ - 0.048106, - "r" - ], - [ - 0.072128, - "m" - ], - [ - 0.030094, - "i" - ], - [ - 0.096127, - "n" - ], - [ - 0.012068, - "a" - ], - [ - 0.072095, - "t" - ], - [ - 0.024103, - "i" - ], - [ - 0.036095, - "o" - ], - [ - 0.084143, - "n" - ], - [ - 0.006116, - " " - ], - [ - 0.108154, - "o" - ], - [ - 0.108177, - "f" - ], - [ - 0.018048, - " " - ], - [ - 0.072077, - "t" - ], - [ - 0.018091, - "h" - ], - [ - 0.054100, - "e" - ], - [ - 0.096165, - " " - ], - [ - 0.096181, - "H" - ], - [ - 0.060122, - "e" - ], - [ - 0.102165, - "r" - ], - [ - 0.078107, - "m" - ], - [ - 0.066066, - "i" - ], - [ - 0.006065, - "t" - ], - [ - 0.042115, - "C" - ], - [ - 0.018113, - "o" - ], - [ - 0.054087, - "r" - ], - [ - 0.024129, - "e" - ], - [ - 0.060121, - " " - ], - [ - 0.018101, - "a" - ], - [ - 0.078147, - "p" - ], - [ - 0.054040, - "p" - ], - [ - 0.030054, - "l" - ], - [ - 0.024086, - "i" - ], - [ - 0.090135, - "c" - ], - [ - 0.066109, - "a" - ], - [ - 0.084168, - "t" - ], - [ - 0.042104, - "i" - ], - [ - 0.078134, - "o" - ], - [ - 0.024118, - "n" - ], - [ - 0.096102, - "," - ], - [ - 0.102116, - " " - ], - [ - 0.078118, - "C" - ], - [ - 0.048092, - "P" - ], - [ - 0.024090, - "U" - ], - [ - 0.084168, - " " - ], - [ - 0.042105, - "1" - ], - [ - 0.078136, - " " - ], - [ - 0.054112, - "i" - ], - [ - 0.018050, - "s" - ], - [ - 0.048067, - "\u001b" - ], - [ - 0.012084, - "[" - ], - [ - 0.060121, - "3" - ], - [ - 0.060100, - "9" - ], - [ - 0.102165, - "m" - ], - [ - 0.018102, - "\r\n" - ], - [ - 0.066566, - "~ \u003e" - ], - [ - 0.000930, - " " - ], - [ - 0.108151, - "\u001b" - ], - [ - 0.066096, - "[" - ], - [ - 0.108180, - "9" - ], - [ - 0.108162, - "2" - ], - [ - 0.036125, - "m" - ], - [ - 0.018114, - "#" - ], - [ - 0.072040, - " " - ], - [ - 0.048092, - "r" - ], - [ - 0.006032, - "e" - ], - [ - 0.096153, - "-" - ], - [ - 0.036111, - "r" - ], - [ - 0.060120, - "e" - ], - [ - 0.024107, - "g" - ], - [ - 0.102155, - "i" - ], - [ - 0.066135, - "s" - ], - [ - 0.036152, - "t" - ], - [ - 0.006099, - "e" - ], - [ - 0.036032, - "r" - ], - [ - 0.024106, - "e" - ], - [ - 0.102146, - "d" - ], - [ - 0.060105, - " " - ], - [ - 0.048117, - "t" - ], - [ - 0.084128, - "o" - ], - [ - 0.066152, - " " - ], - [ - 0.048068, - "t" - ], - [ - 0.090108, - "h" - ], - [ - 0.006118, - "e" - ], - [ - 0.102160, - " " - ], - [ - 0.048107, - "L" - ], - [ - 0.096153, - "i" - ], - [ - 0.090147, - "n" - ], - [ - 0.042116, - "u" - ], - [ - 0.054086, - "x" - ], - [ - 0.090116, - " " - ], - [ - 0.042076, - "s" - ], - [ - 0.084159, - "y" - ], - [ - 0.108134, - "s" - ], - [ - 0.006130, - "t" - ], - [ - 0.024111, - "e" - ], - [ - 0.108169, - "m" - ], - [ - 0.096110, - "." - ], - [ - 0.054052, - "\u001b" - ], - [ - 0.054089, - "[" - ], - [ - 0.006087, - "3" - ], - [ - 0.042061, - "9" - ], - [ - 0.006125, - "m" - ], - [ - 0.036109, - "\r\n" - ], - [ - 0.048464, - "~ \u003e" - ], - [ - 0.000961, - " " - ], - [ - 0.084049, - "d" - ], - [ - 0.054055, - "m" - ], - [ - 0.054094, - "e" - ], - [ - 0.054087, - "s" - ], - [ - 0.012107, - "g" - ], - [ - 0.036094, - " " - ], - [ - 0.036123, - "|" - ], - [ - 0.024117, - " " - ], - [ - 0.078133, - "t" - ], - [ - 0.012114, - "a" - ], - [ - 0.018047, - "i" - ], - [ - 0.030085, - "l" - ], - [ - 0.054068, - " " - ], - [ - 0.084152, - "-" - ], - [ - 0.108159, - "1" - ], - [ - 0.012109, - "0" - ], - [ - 0.024118, - "\r\n" - ], - [ - 0.050142, - "[ 313.983584] smpboot: CPU 1 is now offline\r\n[ 313.984377] Isle 0 tries to boot HermitCore on CPU 1 (apicid 2, boot code size 0x5000)\r\n[ 313.984400] Loading HermitCore's kernel image with a size of 2992 KiB\r\n[ 314.008022] CPU: 2299 MHz, TSC: 2299 MHz\r\n[ 314.108255] HermitCore requires 138 ms (317925425 ticks) to boot the system\r\n[ 314.108343] IPv6: ADDRCONF(NETDEV_CHANGE): mmnif: link becomes ready\r\n[ 314.132200] Try to shutdown HermitCore on isle 0\r\n[ 314.134472] x86: Booting SMP configuration:\r\n[ 314.134696] smpboot: Booting Node 0 Processor 1 APIC 0x2\r\n[ 314.142062] HermitCore 0 is down!\r\n" - ], - [ - 0.000258, - "~ \u003e" - ], - [ - 0.000636, - " " - ], - [ - 0.024144, - "\u001b" - ], - [ - 0.090107, - "[" - ], - [ - 0.078044, - "9" - ], - [ - 0.042077, - "2" - ], - [ - 0.078100, - "m" - ], - [ - 0.048103, - "#" - ], - [ - 0.012115, - " " - ], - [ - 0.084159, - "H" - ], - [ - 0.096155, - "e" - ], - [ - 0.036106, - "r" - ], - [ - 0.108152, - "m" - ], - [ - 0.018036, - "i" - ], - [ - 0.048068, - "t" - ], - [ - 0.018085, - "C" - ], - [ - 0.012092, - "o" - ], - [ - 0.060118, - "r" - ], - [ - 0.102149, - "e" - ], - [ - 0.030123, - "'" - ], - [ - 0.072139, - "s" - ], - [ - 0.048078, - " " - ], - [ - 0.054117, - "k" - ], - [ - 0.090121, - "e" - ], - [ - 0.078096, - "r" - ], - [ - 0.036105, - "n" - ], - [ - 0.090137, - "e" - ], - [ - 0.048124, - "l" - ], - [ - 0.006098, - " " - ], - [ - 0.048132, - "m" - ], - [ - 0.024115, - "e" - ], - [ - 0.054098, - "s" - ], - [ - 0.084103, - "a" - ], - [ - 0.114226, - "\u0008 \u0008" - ], - [ - 0.174220, - "s" - ], - [ - 0.024125, - "a" - ], - [ - 0.030107, - "g" - ], - [ - 0.084164, - "e" - ], - [ - 0.054068, - " " - ], - [ - 0.108123, - "i" - ], - [ - 0.102146, - "s" - ], - [ - 0.096170, - " " - ], - [ - 0.042127, - "p" - ], - [ - 0.102154, - "u" - ], - [ - 0.102158, - "b" - ], - [ - 0.048099, - "l" - ], - [ - 0.072089, - "i" - ], - [ - 0.006066, - "s" - ], - [ - 0.048067, - "h" - ], - [ - 0.054111, - "e" - ], - [ - 0.060122, - "d" - ], - [ - 0.036113, - " " - ], - [ - 0.078151, - "a" - ], - [ - 0.060125, - "t" - ], - [ - 0.078130, - " " - ], - [ - 0.006032, - "/" - ], - [ - 0.102121, - "s" - ], - [ - 0.084154, - "y" - ], - [ - 0.048082, - "s" - ], - [ - 0.030115, - "/" - ], - [ - 0.036125, - "h" - ], - [ - 0.006111, - "e" - ], - [ - 0.066125, - "r" - ], - [ - 0.066116, - "m" - ], - [ - 0.072051, - "i" - ], - [ - 0.048107, - "t" - ], - [ - 0.084088, - "/" - ], - [ - 0.102184, - "i" - ], - [ - 0.030105, - "s" - ], - [ - 0.090120, - "l" - ], - [ - 0.096174, - "e" - ], - [ - 0.048107, - "0" - ], - [ - 0.066123, - "/" - ], - [ - 0.042072, - "l" - ], - [ - 0.030085, - "o" - ], - [ - 0.030105, - "g" - ], - [ - 0.084118, - "\u001b" - ], - [ - 0.054128, - "[" - ], - [ - 0.108157, - "3" - ], - [ - 0.030125, - "9" - ], - [ - 0.054118, - "m" - ], - [ - 0.090080, - "\r\n" - ], - [ - 0.102487, - "~ \u003e" - ], - [ - 0.001043, - " " - ], - [ - 0.102151, - "c" - ], - [ - 0.102167, - "a" - ], - [ - 0.018105, - "t" - ], - [ - 0.018033, - " " - ], - [ - 0.030066, - "/" - ], - [ - 0.060069, - "s" - ], - [ - 0.108172, - "y" - ], - [ - 0.102159, - "s" - ], - [ - 0.048116, - "/" - ], - [ - 0.060119, - "h" - ], - [ - 0.066094, - "e" - ], - [ - 0.042125, - "r" - ], - [ - 0.102099, - "m" - ], - [ - 0.030086, - "i" - ], - [ - 0.048055, - "t" - ], - [ - 0.054130, - "/" - ], - [ - 0.066074, - "i" - ], - [ - 0.048126, - "s" - ], - [ - 0.060115, - "l" - ], - [ - 0.030082, - "e" - ], - [ - 0.102178, - "0" - ], - [ - 0.042086, - "/" - ], - [ - 0.096086, - "l" - ], - [ - 0.084156, - "o" - ], - [ - 0.096122, - "g" - ], - [ - 0.024078, - "\r\n" - ], - [ - 0.037160, - "cpuid level 15\r\nPaging features: PSE (2/4Mb) PAE PGE PAT PSE36 NX PSE (1Gb) LM\r\nPhysical adress-width: 46 bits\r\nLinear adress-width: 48 bits\r\nSysenter instruction: available\r\nSyscall instruction: available\r\nSet XCR0 to 0x7\r\nCore 2 set per_core offset to 0x80\r\nCore id is set to 2\r\nFound and initialized FPU!\r\nCPU features: SSE SSE2 SSE3 SSE4.1 SSE4.2 AVX AVX2 FMA MOVBE X2APIC FPU FXSR XSAVE OSXSAVE VMX RDTSCP FSGSBASE MWAIT DCA \r\nExt_Save_Area_2: offset 576, size 256\r\nExt_Save_Area_3: offset 0, size 0\r\nExt_Save_Area_4: offset 0, size 0\r\nSystem supports Enhanced SpeedStep Technology\r\nLinux doesn't enable Enhanced SpeedStep Technology\r\nCR0 0x80040033, CR4 0x1506a0\r\nsize of xsave_t: 832\r\nIA32_MISC_ENABLE 0x4000840089\r\nIA32_PLATFORM_ID 0x0\r\nIA32_CR_PAT 0x407010600070106\r\nPAT use per default writeback.\r\nMTRR is enabled.\r\nFixed-range MTRR is enabled.\r\nMTRR used per default writeback.\r\nmemory_init: base 0x55f800000, image_size 0x50f538, limit 0x85f800000\r\nfree list starts at 0x55fe00000, limit 0x85f800000\r\nvma_init: reserve vma region 0x800000 - 0xe00000\r\nFound MP config table at 0xfd620\r\nSystem uses Multiprocessing Specification 1.4\r\nMP features 1: 0\r\nVirtual-Wire mode implemented\r\nFound IOAPIC at 0xfec00000\r\nFound IOAPIC at 0xfec01000\r\nFound IOAPIC at 0xfec40000\r\nFound 20 cores\r\nFound APIC at 0xfee00000\r\nMaximum LVT Entry: 0x6\r\nAPIC Version: 0x15\r\nEOI-broadcast: available\r\nBoot processor 2 (ID 4)\r\nAPIC calibration determined already an ICR of 0xf4091\r\nThis is Hermit 5f66a0-dirty, build date 9306900\r\nIsle 0 of 2 possible isles\r\nKernel starts at 0x800000 and ends at 0xd0f538\r\nTLS image starts at 0xaec040 and ends at 0xaec040\r\nKernel BBS starts at 0xaec040 and ends at 0xd0f538\r\nPer core data starts at 0xaea040 and ends at 0xaec040\r\nPer core size 0x40\r\nProcessor frequency: 2299 MHz\r\nTotal memory: 12288 MiB\r\nCurrent allocated memory: 6208 KiB\r\nCurrent available memory: 12281 MiB\r\nCore 2 is the boot processor\r\nCPU 2 of isle 0 is now online (CR0 0x8004003b, CR4 0x1506a0)\r\nTask 1 use use the memory region [0xd0008 - 0xe0007] as kernel stack\r\nstart new task 1 on core 2 with stack address 0xd0008\r\nInitd is running\r\nTask 2 use use the memory region [0xfe008 - 0x10e007] as kernel stack\r\nstart new task 2 on core 2 with stack address 0xfe008\r\nsys_thread_new: create_kernel_task 0, id = 2, prio = 16\r\nLwIP's tcpip thread has task id 2\r\nTCP/IP initialized.\r\nnetif_set_ipaddr: netif address being changed\r\nnetif: IP address of interface ?? set to 192.168.28.2\r\nnetif: netmask of interface ?? set to 255.255.255.0\r\nnetif: GW address of interface ?? set to 192.168.28.1\r\nInitialize mmnif\r\nmmnif_init() : size of mm_rx_buffer_t : 1040\r\nmap header 0x7e8000 at 0x7e8000\r\nmap heap 0x7eb000 at 0x7eb000\r\nmap isle_locks 0x7e7000 at 0xf0000\r\nmmnif init complete\r\nnetif: added interface mm IP addr 192.168.28.2 netmask 255.255.255.0 gw 192.168.28.1\r\nnetif: setting default interface mm\r\nMap rcce_lock at 0xf1000 and rcce_mpb at 0xf1240\r\nTCP server listening.\r\nEstablish IP connection\r\nTerminate task: 1, return value 0\r\nReceive shutdown interrupt\r\nTry to shutdown HermitCore\r\nP-State 0x0 - 0x0, turbo 0x0\r\nPERF CTL 0xc00\r\nPERF STATUS 0x17e100001700\r\nShutdown LwIP\r\nDisable APIC timer\r\nDisable APIC\r\nCore 2, IRQ 14: 1 interrupts\r\nCore 2, IRQ 113: 1 interrupts\r\nCore 2, IRQ 122: 22 interrupts\r\nSystem goes down...\r\n\r\n" - ], - [ - 0.000230, - "~ \u003e" - ], - [ - 0.000672, - " " - ], - [ - 0.012121, - "\u001b" - ], - [ - 0.060119, - "[" - ], - [ - 0.084115, - "9" - ], - [ - 0.024094, - "2" - ], - [ - 0.084117, - "m" - ], - [ - 0.090128, - "#" - ], - [ - 0.060069, - " " - ], - [ - 0.096173, - "H" - ], - [ - 0.006105, - "e" - ], - [ - 0.036124, - "r" - ], - [ - 0.096152, - "m" - ], - [ - 0.042082, - "i" - ], - [ - 0.096159, - "t" - ], - [ - 0.084106, - "C" - ], - [ - 0.018076, - "o" - ], - [ - 0.108182, - "r" - ], - [ - 0.066148, - "e" - ], - [ - 0.078133, - " " - ], - [ - 0.102130, - "s" - ], - [ - 0.084166, - "u" - ], - [ - 0.096071, - "p" - ], - [ - 0.018069, - "p" - ], - [ - 0.078079, - "o" - ], - [ - 0.024114, - "r" - ], - [ - 0.072135, - "t" - ], - [ - 0.048122, - "s" - ], - [ - 0.054101, - " " - ], - [ - 0.030124, - "O" - ], - [ - 0.072139, - "p" - ], - [ - 0.006097, - "e" - ], - [ - 0.096113, - "n" - ], - [ - 0.042064, - "M" - ], - [ - 0.108168, - "P" - ], - [ - 0.054146, - " " - ], - [ - 0.078134, - "(" - ], - [ - 0.096142, - "i" - ], - [ - 0.048129, - "n" - ], - [ - 0.054067, - "c" - ], - [ - 0.048062, - "l" - ], - [ - 0.006070, - "u" - ], - [ - 0.108145, - "d" - ], - [ - 0.078165, - "i" - ], - [ - 0.066121, - "n" - ], - [ - 0.006101, - "g" - ], - [ - 0.084138, - " " - ], - [ - 0.072111, - "I" - ], - [ - 0.090149, - "n" - ], - [ - 0.090084, - "t" - ], - [ - 0.048141, - "e" - ], - [ - 0.108136, - "l" - ], - [ - 0.012128, - "'" - ], - [ - 0.072152, - "s" - ], - [ - 0.078132, - " " - ], - [ - 0.006099, - "O" - ], - [ - 0.024123, - "p" - ], - [ - 0.096173, - "e" - ], - [ - 0.042059, - "n" - ], - [ - 0.108198, - "M" - ], - [ - 0.072129, - "P" - ], - [ - 0.006109, - " " - ], - [ - 0.024126, - "R" - ], - [ - 0.096148, - "u" - ], - [ - 0.024067, - "n" - ], - [ - 0.084085, - "t" - ], - [ - 0.066127, - "i" - ], - [ - 0.072106, - "m" - ], - [ - 0.072115, - "e" - ], - [ - 0.036130, - ")" - ], - [ - 0.030087, - "." - ], - [ - 0.030126, - "\u001b" - ], - [ - 0.006119, - "[" - ], - [ - 0.030097, - "3" - ], - [ - 0.078104, - "9" - ], - [ - 0.030078, - "m" - ], - [ - 0.066104, - "\r\n" - ], - [ - 0.024631, - "~ \u003e" - ], - [ - 0.000839, - " " - ], - [ - 0.096168, - "\u001b" - ], - [ - 0.012085, - "[" - ], - [ - 0.030077, - "9" - ], - [ - 0.084085, - "2" - ], - [ - 0.048108, - "m" - ], - [ - 0.072117, - "#" - ], - [ - 0.108184, - " " - ], - [ - 0.102130, - "T" - ], - [ - 0.012095, - "h" - ], - [ - 0.096167, - "e" - ], - [ - 0.096032, - " " - ], - [ - 0.072100, - "b" - ], - [ - 0.054076, - "e" - ], - [ - 0.018106, - "n" - ], - [ - 0.084105, - "c" - ], - [ - 0.096170, - "h" - ], - [ - 0.084145, - "m" - ], - [ - 0.018109, - "a" - ], - [ - 0.108155, - "r" - ], - [ - 0.054029, - "k" - ], - [ - 0.054086, - " " - ], - [ - 0.030079, - "S" - ], - [ - 0.006093, - "T" - ], - [ - 0.048098, - "R" - ], - [ - 0.078152, - "E" - ], - [ - 0.072114, - "A" - ], - [ - 0.102153, - "M" - ], - [ - 0.018137, - " " - ], - [ - 0.078098, - "i" - ], - [ - 0.108156, - "s" - ], - [ - 0.066083, - " " - ], - [ - 0.084175, - "u" - ], - [ - 0.048107, - "s" - ], - [ - 0.024079, - "e" - ], - [ - 0.054104, - "d" - ], - [ - 0.060138, - " " - ], - [ - 0.078126, - "t" - ], - [ - 0.066084, - "o" - ], - [ - 0.066099, - " " - ], - [ - 0.006110, - "s" - ], - [ - 0.054115, - "h" - ], - [ - 0.012084, - "o" - ], - [ - 0.108192, - "w" - ], - [ - 0.072153, - " " - ], - [ - 0.096149, - "t" - ], - [ - 0.084035, - "h" - ], - [ - 0.018096, - "e" - ], - [ - 0.048060, - " " - ], - [ - 0.078117, - "m" - ], - [ - 0.102133, - "o" - ], - [ - 0.090170, - "d" - ], - [ - 0.078135, - "e" - ], - [ - 0.102162, - " " - ], - [ - 0.024097, - "o" - ], - [ - 0.030114, - "f" - ], - [ - 0.012075, - " " - ], - [ - 0.096137, - "o" - ], - [ - 0.030083, - "p" - ], - [ - 0.030127, - "e" - ], - [ - 0.048111, - "r" - ], - [ - 0.006100, - "a" - ], - [ - 0.012127, - "t" - ], - [ - 0.096152, - "i" - ], - [ - 0.036107, - "o" - ], - [ - 0.012104, - "n" - ], - [ - 0.006104, - "." - ], - [ - 0.108139, - "\u001b" - ], - [ - 0.018123, - "[" - ], - [ - 0.096154, - "3" - ], - [ - 0.012098, - "9" - ], - [ - 0.090152, - "m" - ], - [ - 0.006053, - "\r\n" - ], - [ - 0.108647, - "~ \u003e" - ], - [ - 0.000842, - " " - ], - [ - 0.006122, - "h" - ], - [ - 0.066095, - "e" - ], - [ - 0.012122, - "r" - ], - [ - 0.078134, - "m" - ], - [ - 0.060060, - "i" - ], - [ - 0.042090, - "t" - ], - [ - 0.036124, - "/" - ], - [ - 0.030112, - "u" - ], - [ - 0.084136, - "s" - ], - [ - 0.090146, - "r" - ], - [ - 0.018116, - "/" - ], - [ - 0.024106, - "b" - ], - [ - 0.030068, - "e" - ], - [ - 0.030052, - "n" - ], - [ - 0.090125, - "c" - ], - [ - 0.042054, - "h" - ], - [ - 0.096162, - "m" - ], - [ - 0.012129, - "a" - ], - [ - 0.054075, - "r" - ], - [ - 0.072127, - "k" - ], - [ - 0.006114, - "s" - ], - [ - 0.012093, - "/" - ], - [ - 0.096103, - "s" - ], - [ - 0.066100, - "t" - ], - [ - 0.006064, - "r" - ], - [ - 0.072131, - "e" - ], - [ - 0.042098, - "a" - ], - [ - 0.036129, - "m" - ], - [ - 0.024111, - "\r\n" - ], - [ - 0.315387, - "-------------------------------------------------------------\r\nSTREAM version $Revision: 5.10 $\r\n-------------------------------------------------------------\r\nThis system uses 8 bytes per array element.\r\n-------------------------------------------------------------\r\nArray size = 14000000 (elements), Offset = 0 (elements)\r\nMemory per array = 106.8 MiB (= 0.1 GiB).\r\nTotal memory required = 320.4 MiB (= 0.3 GiB).\r\nEach kernel will be executed 100 times.\r\n The *best* time for each kernel (excluding the first iteration)\r\n will be used to compute the reported bandwidth.\r\n-------------------------------------------------------------\r\nNumber of Threads requested = 1\r\nNumber of Threads counted = 1\r\n" - ], - [ - 0.042986, - "-------------------------------------------------------------\r\nYour clock granularity/precision appears to be 1 microseconds.\r\n" - ], - [ - 0.014022, - "Each test below will take on the order of 14328 microseconds.\r\n (= 14328 clock ticks)\r\nIncrease the size of the arrays if this shows that\r\nyou are not getting at least 20 clock ticks per test.\r\n-------------------------------------------------------------\r\nWARNING -- The above is only a rough guideline.\r\nFor best results, please be sure you know the\r\nprecision of your system timer.\r\n-------------------------------------------------------------\r\n" - ], - [ - 9.949986, - "Function Best Rate MB/s Avg time Min time Max time\r\nCopy: 17009.3 0.014487 0.013169 0.014894\r\nScale: 10632.8 0.022915 0.021067 0.023488\r\nAdd: 11705.8 0.030958 0.028704 0.031680\r\nTriad: 11638.0 0.031159 0.028871 0.031905\r\n-------------------------------------------------------------\r\n" - ], - [ - 0.074001, - "Solution Validates: avg error less than 1.000000e-13 on all three arrays\r\n-------------------------------------------------------------\r\n" - ], - [ - 0.010598, - "~ \u003e" - ], - [ - 0.000618, - " " - ], - [ - 0.072121, - "\u001b" - ], - [ - 0.006144, - "[" - ], - [ - 0.090147, - "9" - ], - [ - 0.096151, - "2" - ], - [ - 0.066128, - "m" - ], - [ - 0.060092, - "#" - ], - [ - 0.066105, - " " - ], - [ - 0.012074, - "P" - ], - [ - 0.012098, - "e" - ], - [ - 0.018103, - "r" - ], - [ - 0.096159, - " " - ], - [ - 0.036128, - "d" - ], - [ - 0.090147, - "e" - ], - [ - 0.060125, - "f" - ], - [ - 0.102067, - "a" - ], - [ - 0.102129, - "u" - ], - [ - 0.060099, - "l" - ], - [ - 0.108175, - "t" - ], - [ - 0.078134, - "," - ], - [ - 0.108166, - " " - ], - [ - 0.018114, - "o" - ], - [ - 0.084138, - "n" - ], - [ - 0.036020, - "l" - ], - [ - 0.060096, - "y" - ], - [ - 0.084152, - " " - ], - [ - 0.084195, - "C" - ], - [ - 0.096155, - "P" - ], - [ - 0.102129, - "U" - ], - [ - 0.018128, - " " - ], - [ - 0.030085, - "1" - ], - [ - 0.060080, - " " - ], - [ - 0.024083, - "i" - ], - [ - 0.036056, - "s" - ], - [ - 0.078141, - " " - ], - [ - 0.030110, - "u" - ], - [ - 0.030104, - "s" - ], - [ - 0.006129, - "e" - ], - [ - 0.078139, - "t" - ], - [ - 0.096163, - "\u0008 \u0008" - ], - [ - 0.162076, - "d" - ], - [ - 0.096101, - "." - ], - [ - 0.078093, - " " - ], - [ - 0.042083, - "T" - ], - [ - 0.066135, - "h" - ], - [ - 0.024123, - "i" - ], - [ - 0.102163, - "s" - ], - [ - 0.060117, - " " - ], - [ - 0.072148, - "c" - ], - [ - 0.090037, - "a" - ], - [ - 0.042078, - "n" - ], - [ - 0.054055, - " " - ], - [ - 0.054100, - "b" - ], - [ - 0.078120, - "e" - ], - [ - 0.060158, - " " - ], - [ - 0.084115, - "c" - ], - [ - 0.030121, - "h" - ], - [ - 0.060134, - "a" - ], - [ - 0.096121, - "n" - ], - [ - 0.006050, - "g" - ], - [ - 0.072093, - "e" - ], - [ - 0.024100, - "d" - ], - [ - 0.066121, - " " - ], - [ - 0.090149, - "b" - ], - [ - 0.072129, - "y" - ], - [ - 0.036108, - " " - ], - [ - 0.090157, - "s" - ], - [ - 0.054104, - "e" - ], - [ - 0.084079, - "t" - ], - [ - 0.078113, - "t" - ], - [ - 0.072142, - "i" - ], - [ - 0.066140, - "n" - ], - [ - 0.084144, - "g" - ], - [ - 0.090148, - "\u001b" - ], - [ - 0.036117, - "[" - ], - [ - 0.108101, - "3" - ], - [ - 0.078083, - "9" - ], - [ - 0.060095, - "m" - ], - [ - 0.036096, - "\r\n" - ], - [ - 0.024466, - "~ \u003e" - ], - [ - 0.001139, - " " - ], - [ - 0.054123, - "\u001b" - ], - [ - 0.078096, - "[" - ], - [ - 0.036090, - "9" - ], - [ - 0.048092, - "2" - ], - [ - 0.102168, - "m" - ], - [ - 0.108169, - "#" - ], - [ - 0.096153, - " " - ], - [ - 0.024114, - "t" - ], - [ - 0.102111, - "h" - ], - [ - 0.042086, - "e" - ], - [ - 0.066113, - " " - ], - [ - 0.108150, - "e" - ], - [ - 0.066120, - "n" - ], - [ - 0.096145, - "v" - ], - [ - 0.054132, - "i" - ], - [ - 0.018109, - "r" - ], - [ - 0.096146, - "o" - ], - [ - 0.054070, - "n" - ], - [ - 0.006067, - "m" - ], - [ - 0.006156, - "e" - ], - [ - 0.012122, - "n" - ], - [ - 0.072132, - "h" - ], - [ - 0.102179, - "\u0008 \u0008" - ], - [ - 0.210260, - "t" - ], - [ - 0.048067, - " " - ], - [ - 0.042104, - "v" - ], - [ - 0.090123, - "a" - ], - [ - 0.108216, - "r" - ], - [ - 0.042133, - "i" - ], - [ - 0.024099, - "a" - ], - [ - 0.030108, - "b" - ], - [ - 0.096141, - "l" - ], - [ - 0.024082, - "e" - ], - [ - 0.018091, - " " - ], - [ - 0.072123, - "H" - ], - [ - 0.024100, - "E" - ], - [ - 0.036118, - "R" - ], - [ - 0.060118, - "M" - ], - [ - 0.060107, - "I" - ], - [ - 0.024115, - "T" - ], - [ - 0.030131, - "_" - ], - [ - 0.072040, - "C" - ], - [ - 0.072108, - "P" - ], - [ - 0.102170, - "U" - ], - [ - 0.024092, - "S" - ], - [ - 0.018131, - "." - ], - [ - 0.042103, - "\u001b" - ], - [ - 0.060121, - "[" - ], - [ - 0.048131, - "3" - ], - [ - 0.108150, - "9" - ], - [ - 0.042070, - "m" - ], - [ - 0.018090, - "\r\n" - ], - [ - 0.006431, - "~ \u003e" - ], - [ - 0.001044, - " " - ], - [ - 0.048120, - "H" - ], - [ - 0.090160, - "E" - ], - [ - 0.060053, - "R" - ], - [ - 0.024090, - "M" - ], - [ - 0.072068, - "I" - ], - [ - 0.006093, - "T" - ], - [ - 0.102181, - "_" - ], - [ - 0.006108, - "C" - ], - [ - 0.048108, - "P" - ], - [ - 0.042110, - "U" - ], - [ - 0.054115, - "S" - ], - [ - 0.012111, - "=" - ], - [ - 0.054047, - "\"" - ], - [ - 0.042051, - "1" - ], - [ - 0.006082, - "-" - ], - [ - 0.036106, - "2" - ], - [ - 0.006051, - "\"" - ], - [ - 0.066141, - " " - ], - [ - 0.024106, - "h" - ], - [ - 0.006120, - "e" - ], - [ - 0.054091, - "r" - ], - [ - 0.024124, - "m" - ], - [ - 0.048071, - "i" - ], - [ - 0.072055, - "t" - ], - [ - 0.102106, - "/" - ], - [ - 0.084129, - "u" - ], - [ - 0.060133, - "s" - ], - [ - 0.024109, - "r" - ], - [ - 0.048105, - "/" - ], - [ - 0.084161, - "b" - ], - [ - 0.030082, - "e" - ], - [ - 0.090151, - "n" - ], - [ - 0.066093, - "c" - ], - [ - 0.084105, - "h" - ], - [ - 0.006099, - "m" - ], - [ - 0.030102, - "a" - ], - [ - 0.090147, - "r" - ], - [ - 0.102171, - "k" - ], - [ - 0.030099, - "s" - ], - [ - 0.024118, - "/" - ], - [ - 0.030092, - "s" - ], - [ - 0.078098, - "t" - ], - [ - 0.030078, - "r" - ], - [ - 0.078095, - "e" - ], - [ - 0.006094, - "a" - ], - [ - 0.036126, - "m" - ], - [ - 0.006110, - "\r\n" - ], - [ - 0.239402, - "-------------------------------------------------------------\r\nSTREAM version $Revision: 5.10 $\r\n-------------------------------------------------------------\r\nThis system uses 8 bytes per array element.\r\n-------------------------------------------------------------\r\nArray size = 14000000 (elements), Offset = 0 (elements)\r\nMemory per array = 106.8 MiB (= 0.1 GiB).\r\nTotal memory required = 320.4 MiB (= 0.3 GiB).\r\nEach kernel will be executed 100 times.\r\n The *best* time for each kernel (excluding the first iteration)\r\n will be used to compute the reported bandwidth.\r\n-------------------------------------------------------------\r\nNumber of Threads requested = 2\r\nNumber of Threads counted = 2\r\n" - ], - [ - 0.021989, - "-------------------------------------------------------------\r\nYour clock granularity/precision appears to be 1 microseconds.\r\n" - ], - [ - 0.007027, - "Each test below will take on the order of 7216 microseconds.\r\n (= 7216 clock ticks)\r\nIncrease the size of the arrays if this shows that\r\nyou are not getting at least 20 clock ticks per test.\r\n-------------------------------------------------------------\r\nWARNING -- The above is only a rough guideline.\r\nFor best results, please be sure you know the\r\nprecision of your system timer.\r\n-------------------------------------------------------------\r\n" - ], - [ - 4.905981, - "Function Best Rate MB/s Avg time Min time Max time\r\nCopy: 31062.8 0.007221 0.007211 0.007239\r\nScale: 20017.2 0.011217 0.011190 0.011279\r\nAdd: 21990.2 0.015300 0.015280 0.015386\r\nTriad: 21952.8 0.015338 0.015306 0.015372\r\n-------------------------------------------------------------\r\n" - ], - [ - 0.072995, - "Solution Validates: avg error less than 1.000000e-13 on all three arrays\r\n-------------------------------------------------------------\r\n" - ], - [ - 0.017583, - "~ \u003e" - ], - [ - 0.000913, - " " - ], - [ - 0.012091, - "\u001b" - ], - [ - 0.018121, - "[" - ], - [ - 0.060115, - "9" - ], - [ - 0.060109, - "2" - ], - [ - 0.054057, - "m" - ], - [ - 0.030084, - "#" - ], - [ - 0.078102, - " " - ], - [ - 0.066122, - "I" - ], - [ - 0.102140, - "n" - ], - [ - 0.024107, - " " - ], - [ - 0.036093, - "t" - ], - [ - 0.042122, - "h" - ], - [ - 0.036071, - "i" - ], - [ - 0.090117, - "s" - ], - [ - 0.090038, - " " - ], - [ - 0.018059, - "e" - ], - [ - 0.054064, - "x" - ], - [ - 0.072122, - "a" - ], - [ - 0.096138, - "m" - ], - [ - 0.036121, - "p" - ], - [ - 0.054110, - "l" - ], - [ - 0.060120, - "e" - ], - [ - 0.054110, - " " - ], - [ - 0.084126, - "C" - ], - [ - 0.012044, - "P" - ], - [ - 0.060084, - "U" - ], - [ - 0.096121, - "s" - ], - [ - 0.066111, - " " - ], - [ - 0.030085, - "1" - ], - [ - 0.018124, - "-" - ], - [ - 0.096164, - "2" - ], - [ - 0.024106, - " " - ], - [ - 0.102167, - "a" - ], - [ - 0.108040, - "r" - ], - [ - 0.030095, - "e" - ], - [ - 0.090110, - " " - ], - [ - 0.096146, - "b" - ], - [ - 0.078152, - "o" - ], - [ - 0.042101, - "o" - ], - [ - 0.084159, - "t" - ], - [ - 0.024107, - "e" - ], - [ - 0.078133, - "d" - ], - [ - 0.036082, - " " - ], - [ - 0.084176, - "t" - ], - [ - 0.096143, - "o" - ], - [ - 0.054127, - " " - ], - [ - 0.084118, - "r" - ], - [ - 0.078161, - "u" - ], - [ - 0.072151, - "n" - ], - [ - 0.090016, - " " - ], - [ - 0.048068, - "S" - ], - [ - 0.096111, - "T" - ], - [ - 0.036110, - "R" - ], - [ - 0.066122, - "E" - ], - [ - 0.042109, - "A" - ], - [ - 0.078155, - "M" - ], - [ - 0.060116, - "." - ], - [ - 0.102184, - "\u001b" - ], - [ - 0.024050, - "[" - ], - [ - 0.030090, - "3" - ], - [ - 0.066146, - "9" - ], - [ - 0.018074, - "m" - ], - [ - 0.042127, - "\r\n" - ], - [ - 0.078524, - "~ \u003e\r\n~ \u003e" - ], - [ - 0.001040, - " " - ], - [ - 0.018089, - "\u001b" - ], - [ - 0.006051, - "[" - ], - [ - 0.072165, - "9" - ], - [ - 0.036107, - "2" - ], - [ - 0.006078, - "m" - ], - [ - 0.084164, - "H" - ], - [ - 0.078124, - "e" - ], - [ - 0.108144, - "r" - ], - [ - 0.006071, - "m" - ], - [ - 0.012064, - "i" - ], - [ - 0.006087, - "t" - ], - [ - 0.090137, - "C" - ], - [ - 0.108168, - "o" - ], - [ - 0.012112, - "r" - ], - [ - 0.066129, - "e" - ], - [ - 0.018083, - " " - ], - [ - 0.060145, - "(" - ], - [ - 0.060080, - "\u001b" - ], - [ - 0.066102, - "[" - ], - [ - 0.024077, - "3" - ], - [ - 0.072113, - "1" - ], - [ - 0.072105, - "m" - ], - [ - 0.108182, - "h" - ], - [ - 0.006102, - "t" - ], - [ - 0.096183, - "t" - ], - [ - 0.084134, - "p" - ], - [ - 0.084108, - ":" - ], - [ - 0.090159, - "/" - ], - [ - 0.006099, - "/" - ], - [ - 0.090152, - "w" - ], - [ - 0.012113, - "w" - ], - [ - 0.024114, - "w" - ], - [ - 0.108175, - "." - ], - [ - 0.072086, - "h" - ], - [ - 0.060066, - "e" - ], - [ - 0.030086, - "r" - ], - [ - 0.084131, - "m" - ], - [ - 0.024119, - "i" - ], - [ - 0.054105, - "t" - ], - [ - 0.084135, - "c" - ], - [ - 0.048132, - "o" - ], - [ - 0.018070, - "r" - ], - [ - 0.060097, - "e" - ], - [ - 0.018054, - "." - ], - [ - 0.030076, - "o" - ], - [ - 0.024051, - "r" - ], - [ - 0.006092, - "g" - ], - [ - 0.012092, - "\u001b" - ], - [ - 0.030108, - "[" - ], - [ - 0.090152, - "9" - ], - [ - 0.006113, - "2" - ], - [ - 0.096148, - "m" - ], - [ - 0.060111, - ")" - ], - [ - 0.012057, - " " - ], - [ - 0.072078, - "i" - ], - [ - 0.090105, - "s" - ], - [ - 0.048110, - " " - ], - [ - 0.084146, - "a" - ], - [ - 0.030121, - "n" - ], - [ - 0.036108, - " " - ], - [ - 0.072135, - "e" - ], - [ - 0.054122, - "x" - ], - [ - 0.084077, - "p" - ], - [ - 0.018095, - "e" - ], - [ - 0.006055, - "r" - ], - [ - 0.006083, - "i" - ], - [ - 0.072111, - "m" - ], - [ - 0.030101, - "e" - ], - [ - 0.018113, - "n" - ], - [ - 0.096140, - "t" - ], - [ - 0.024128, - "a" - ], - [ - 0.102147, - "l" - ], - [ - 0.006071, - " " - ], - [ - 0.036076, - "p" - ], - [ - 0.102159, - "l" - ], - [ - 0.030111, - "a" - ], - [ - 0.024099, - "t" - ], - [ - 0.078153, - "f" - ], - [ - 0.024108, - "o" - ], - [ - 0.036106, - "r" - ], - [ - 0.012110, - "m" - ], - [ - 0.024077, - "." - ], - [ - 0.012071, - "\u001b" - ], - [ - 0.036095, - "[" - ], - [ - 0.042056, - "3" - ], - [ - 0.042102, - "9" - ], - [ - 0.084158, - "m" - ], - [ - 0.054103, - "\r\n" - ], - [ - 0.072593, - "~ \u003e" - ], - [ - 0.000811, - " " - ], - [ - 0.036086, - "\u001b" - ], - [ - 0.024070, - "[" - ], - [ - 0.090169, - "9" - ], - [ - 0.102153, - "2" - ], - [ - 0.024139, - "m" - ], - [ - 0.060123, - "B" - ], - [ - 0.054131, - "u" - ], - [ - 0.084103, - "t" - ], - [ - 0.096111, - " " - ], - [ - 0.012057, - "t" - ], - [ - 0.108200, - "r" - ], - [ - 0.030108, - "y" - ], - [ - 0.036097, - " " - ], - [ - 0.102119, - "i" - ], - [ - 0.060160, - "t" - ], - [ - 0.090134, - " " - ], - [ - 0.066101, - "o" - ], - [ - 0.084108, - "u" - ], - [ - 0.006095, - "t" - ], - [ - 0.090152, - " " - ], - [ - 0.024082, - "a" - ], - [ - 0.084161, - "n" - ], - [ - 0.030106, - "d" - ], - [ - 0.072142, - " " - ], - [ - 0.078063, - "s" - ], - [ - 0.042095, - "e" - ], - [ - 0.048030, - "n" - ], - [ - 0.048085, - "d" - ], - [ - 0.102195, - " " - ], - [ - 0.078126, - "u" - ], - [ - 0.024128, - "s" - ], - [ - 0.066125, - " " - ], - [ - 0.084155, - "a" - ], - [ - 0.042062, - " " - ], - [ - 0.036065, - "f" - ], - [ - 0.012085, - "e" - ], - [ - 0.054099, - "e" - ], - [ - 0.078136, - "d" - ], - [ - 0.054104, - "b" - ], - [ - 0.018123, - "a" - ], - [ - 0.078151, - "c" - ], - [ - 0.048110, - "k" - ], - [ - 0.018099, - "!" - ], - [ - 0.108104, - "\u001b" - ], - [ - 0.072171, - "[" - ], - [ - 0.072146, - "3" - ], - [ - 0.048109, - "9" - ], - [ - 0.006106, - "m" - ], - [ - 0.018110, - "\r\n" - ] - ] -} \ No newline at end of file diff --git a/tools/init.sh b/tools/init.sh index 624d4d447..8e2093a64 100755 --- a/tools/init.sh +++ b/tools/init.sh @@ -1,6 +1,6 @@ #!/bin/sh -PROXY=/hermit/tools/proxy +PROXY=/hermit/bin/proxy ELF_OSABI_OFFSET=7 ELF_OSABI="\\x42" diff --git a/tools/proxy.c b/tools/proxy.c index b028a708b..58aaef55e 100644 --- a/tools/proxy.c +++ b/tools/proxy.c @@ -47,6 +47,8 @@ #include #include +#include "proxy.h" + #define MAX_PATH 255 #define MAX_ARGS 1024 #define INADDR(a, b, c, d) (struct in_addr) { .s_addr = ((((((d) << 8) | (c)) << 8) | (b)) << 8) | (a) } @@ -54,23 +56,27 @@ #define HERMIT_PORT 0x494E #define HERMIT_IP(isle) INADDR(192, 168, 28, isle + 2) #define HERMIT_MAGIC 0x7E317 -#define HERMIT_ELFOSABI 0x42 - -#define __HERMIT_exit 0 -#define __HERMIT_write 1 -#define __HERMIT_open 2 -#define __HERMIT_close 3 -#define __HERMIT_read 4 -#define __HERMIT_lseek 5 #define EVENT_SIZE (sizeof (struct inotify_event)) #define BUF_LEN (1024 * (EVENT_SIZE + 16)) +#if 0 +#define PROXY_DEBUG(fmt, ...) fprintf(stderr, fmt, ##__VA_ARGS__); +#else +#define PROXY_DEBUG(fmt, ...) {} +#endif + +typedef enum { + BAREMETAL = 0, + QEMU, + UHYVE +} monitor_t; + +static monitor_t monitor = BAREMETAL; static int sobufsize = 131072; static unsigned int isle_nr = 0; -static unsigned int qemu = 0; -static pid_t id = 0; static unsigned int port = HERMIT_PORT; +static char pidname[] = "/tmp/hpid-XXXXXX"; static char tmpname[] = "/tmp/hermit-XXXXXX"; static char cmdline[MAX_PATH] = ""; @@ -78,33 +84,51 @@ extern char **environ; static void stop_hermit(void); static void dump_log(void); -static int init_multi(char *path); -static int init_qemu(char *path); +static int multi_init(char *path); +static int qemu_init(char *path); -static void fini_env(void) +static void qemu_fini(void) { - if (qemu) { - int status = 0; + FILE* fp = NULL; - if (id) { - kill(id, SIGINT); - wait(&status); + // try to kill qemu + if (monitor == QEMU) + fp = fopen(pidname, "r"); + if (fp) { + pid_t id = -1; + + int ret = fscanf(fp, "%d", &id); + if (ret <= 0) + fprintf(stderr, "Unable to read Qemu's pid\n"); + fclose(fp); + unlink(pidname); + + if (id >= 0) { + int ret; + + do { + ret = kill(id, SIGINT); + sched_yield(); + } while((ret < 0) && (errno == ESRCH)); } + } - dump_log(); - puts(""); - unlink(tmpname); - } else { - dump_log(); - stop_hermit(); -} } + dump_log(); + unlink(tmpname); +} + +static void multi_fini(void) +{ + dump_log(); + stop_hermit(); +} static void exit_handler(int sig) { exit(0); } -static char* cpufreq(void) +static char* get_append_string(void) { char line[2048]; char* match; @@ -126,7 +150,7 @@ static char* cpufreq(void) ; *point = '\0'; - snprintf(cmdline, MAX_PATH, "-freq%s", match); + snprintf(cmdline, MAX_PATH, "\"-freq%s -proxy\"", match); fclose(fp); return cmdline; @@ -135,7 +159,7 @@ static char* cpufreq(void) return "-freq0"; } -static int init_env(char *path) +static int env_init(char *path) { char* str; struct sigaction sINT, sTERM; @@ -162,7 +186,10 @@ static int init_env(char *path) if (str) { if (strncmp(str, "qemu", 4) == 0) { - qemu = 1; + monitor = QEMU; + isle_nr = 0; + } else if (strncmp(str, "uhyve", 5) == 0) { + monitor = UHYVE; isle_nr = 0; } else { isle_nr = atoi(str); @@ -179,10 +206,15 @@ static int init_env(char *path) port = HERMIT_PORT; } - if (qemu) - return init_qemu(path); - else - return init_multi(path); + if (monitor == QEMU) { + atexit(qemu_fini); + return qemu_init(path); + } else if (monitor == UHYVE) { + return uhyve_init(path); + } else { + atexit(multi_fini); + return multi_init(path); + } } static int is_hermit_available(void) @@ -197,9 +229,12 @@ static int is_hermit_available(void) exit(1); } - if (qemu) + if (monitor == QEMU) { file = fopen(tmpname, "r"); - else { + if (!file) { + PROXY_DEBUG("%s isn't available\n", tmpname); + } + } else { char logname[MAX_PATH]; snprintf(logname, MAX_PATH, "/sys/hermit/isle%d/log", isle_nr); @@ -209,11 +244,14 @@ static int is_hermit_available(void) if (!file) return 0; + //PROXY_DEBUG("Open log file\n"); + while(getline(&line, &n, file) > 0) { if (strstr(line, "TCP server is listening.") != NULL) { ret = 1; break; } + //PROXY_DEBUG("%s\n", line); } fclose(file); @@ -237,11 +275,16 @@ static void wait_hermit_available(void) exit(1); } - if (qemu) + if (monitor == QEMU) wd = inotify_add_watch(fd, "/tmp", IN_MODIFY|IN_CREATE); else wd = inotify_add_watch(fd, "/sys/hermit", IN_MODIFY|IN_CREATE); + if (wd < 0) { + perror("inotify_add_watch"); + exit(1); + } + while(1) { int length = read(fd, buffer, BUF_LEN); @@ -255,11 +298,14 @@ static void wait_hermit_available(void) } //printf("HermitCore is available\n"); - inotify_rm_watch(fd, wd); + if (inotify_rm_watch(fd, wd) < 0) { + perror("inotify_rm_watch"); + exit(1); + } close(fd); } -static int init_qemu(char *path) +static int qemu_init(char *path) { int kvm, i = 0; char* str; @@ -268,16 +314,17 @@ static int init_qemu(char *path) char monitor_str[MAX_PATH]; char chardev_file[MAX_PATH]; char port_str[MAX_PATH]; + pid_t qemu_pid; char* qemu_str = "qemu-system-x86_64"; - char* qemu_argv[] = {qemu_str, "-nographic", "-smp", "1", "-m", "2G", "-net", "nic,model=rtl8139", "-net", hostfwd, "-chardev", chardev_file, "-device", "pci-serial,chardev=gnc0", "-monitor", monitor_str, "-kernel", loader_path, "-initrd", path, "-append", cpufreq(), NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL}; + char* qemu_argv[] = {qemu_str, "-daemonize", "-display", "none", "-smp", "1", "-m", "2G", "-pidfile", pidname, "-net", "nic,model=rtl8139", "-net", hostfwd, "-chardev", chardev_file, "-device", "pci-serial,chardev=gnc0", "-kernel", loader_path, "-initrd", path, "-append", get_append_string(), NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL}; str = getenv("HERMIT_CPUS"); if (str) - qemu_argv[3] = str; + qemu_argv[5] = str; str = getenv("HERMIT_MEM"); if (str) - qemu_argv[5] = str; + qemu_argv[7] = str; str = getenv("HERMIT_QEMU"); if (str) @@ -286,6 +333,12 @@ static int init_qemu(char *path) snprintf(hostfwd, MAX_PATH, "user,hostfwd=tcp:127.0.0.1:%u-:%u", port, port); snprintf(monitor_str, MAX_PATH, "telnet:127.0.0.1:%d,server,nowait", port+1); + if (mkstemp(pidname) < 0) + { + perror("mkstemp"); + exit(1); + } + if (mkstemp(tmpname) < 0) { perror("mkstemp"); @@ -307,7 +360,7 @@ static int init_qemu(char *path) int app_port = atoi(str); if (app_port > 0) { - for(i=0; qemu_argv[i] != NULL; i++) + for(; qemu_argv[i] != NULL; i++) ; snprintf(port_str, MAX_PATH, "tcp:%u::%u", app_port, app_port); @@ -325,7 +378,7 @@ static int init_qemu(char *path) if (kvm) { - for(i=0; qemu_argv[i] != NULL; i++) + for(; qemu_argv[i] != NULL; i++) ; qemu_argv[i] = "-machine"; @@ -333,23 +386,44 @@ static int init_qemu(char *path) qemu_argv[i+2] = "-cpu"; qemu_argv[i+3] = "host"; } /*else { - for(i=0; qemu_argv[i] != NULL; i++) + for(; qemu_argv[i] != NULL; i++) ; qemu_argv[i] = "-cpu"; qemu_argv[i+1] = "SandyBridge"; }*/ + str = getenv("HERMIT_MONITOR"); + if (str && (strcmp(str, "0") != 0)) + { + for(; qemu_argv[i] != NULL; i++) + ; + + qemu_argv[i] = "-monitor"; + qemu_argv[i+1] = monitor_str; + } + str = getenv("HERMIT_DEBUG"); if (str && (strcmp(str, "0") != 0)) { - for(i=0; qemu_argv[i] != NULL; i++) + for(; qemu_argv[i] != NULL; i++) ; // add flag to start gdbserver on TCP port 1234 qemu_argv[i] = "-s"; } + str = getenv("HERMIT_CAPTURE_NET"); + if (str && (strcmp(str, "0") != 0)) + { + for(; qemu_argv[i] != NULL; i++) + ; + + // add flags to capture the network traffic + qemu_argv[i] = "-net"; + qemu_argv[i+1] = "dump"; + } + str = getenv("HERMIT_VERBOSE"); if (str && (strcmp(str, "0") != 0)) { @@ -357,24 +431,24 @@ static int init_qemu(char *path) for(i=0; qemu_argv[i] != NULL; i++) printf("%s ", qemu_argv[i]); - - // add flags to create dump of the network traffic - qemu_argv[i] = "-net"; - qemu_argv[i+1] = "dump"; - printf("%s %s\n", qemu_argv[i], qemu_argv[i+1]); - + printf("\n"); fflush(stdout); } - id = fork(); - if (id == 0) + qemu_pid = fork(); + if (qemu_pid == 0) { execvp(qemu_str, qemu_argv); fprintf(stderr, "Didn't find qemu\n"); exit(1); + } else if (qemu_pid < 0) { + perror("fork"); + exit(1); } + PROXY_DEBUG("Create VM with pid %d\n", qemu_pid); + // move the parent process to the end of the queue // => child would be scheduled next sched_yield(); @@ -382,10 +456,12 @@ static int init_qemu(char *path) // wait until HermitCore is sucessfully booted wait_hermit_available(); + PROXY_DEBUG("VM is available\n"); + return 0; } -static int init_multi(char *path) +static int multi_init(char *path) { int ret; char* str; @@ -460,7 +536,7 @@ static void dump_log(void) if (!(str && (strcmp(str, "0") != 0))) return; - if (!qemu) + if (monitor == BAREMETAL) { char isle_path[MAX_PATH]; @@ -813,153 +889,174 @@ out: return 1; } -int main(int argc, char **argv) +int socket_loop(int argc, char **argv) { int i, j, ret, s; int32_t magic = HERMIT_MAGIC; struct sockaddr_in serv_name; - init_env(argv[1]); - atexit(fini_env); - #if 0 - // check if mmnif interface is available - if (!qemu) { - struct ifreq ethreq; + // check if mmnif interface is available + if (!qemu) { + struct ifreq ethreq; - memset(ðreq, 0, sizeof(ethreq)); - strncpy(ethreq.ifr_name, "mmnif", IFNAMSIZ); + memset(ðreq, 0, sizeof(ethreq)); + strncpy(ethreq.ifr_name, "mmnif", IFNAMSIZ); - while(1) { - /* this socket doesn't really matter, we just need a descriptor - * to perform the ioctl on */ - s = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP); - ioctl(s, SIOCGIFFLAGS, ðreq); - close(s); + while(1) { + /* this socket doesn't really matter, we just need a descriptor + * to perform the ioctl on */ + s = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP); + ioctl(s, SIOCGIFFLAGS, ðreq); + close(s); - if (ethreq.ifr_flags & (IFF_UP|IFF_RUNNING)) - break; + if (ethreq.ifr_flags & (IFF_UP|IFF_RUNNING)) + break; + } + sched_yield(); } - sched_yield(); - } #endif - /* create a socket */ - s = socket(PF_INET, SOCK_STREAM, 0); - if (s < 0) - { - perror("Proxy: socket creation error"); - exit(1); - } - - setsockopt(s, SOL_SOCKET, SO_RCVBUF, (char *) &sobufsize, sizeof(sobufsize)); - setsockopt(s, SOL_SOCKET, SO_SNDBUF, (char *) &sobufsize, sizeof(sobufsize)); - i = 1; - setsockopt(s, IPPROTO_TCP, TCP_NODELAY, (char *) &i, sizeof(i)); - i = 0; - setsockopt(s, SOL_SOCKET, SO_KEEPALIVE, (char *) &i, sizeof(i)); - - /* server address */ - memset((char *) &serv_name, 0x00, sizeof(serv_name)); - serv_name.sin_family = AF_INET; - if (qemu) - serv_name.sin_addr = INADDR(127, 0, 0, 1); - else - serv_name.sin_addr = HERMIT_IP(isle_nr); - serv_name.sin_port = htons(port); - - i = 0; -retry: - ret = connect(s, (struct sockaddr*)&serv_name, sizeof(serv_name)); - if (ret < 0) - { - i++; - if (i <= 10) { - usleep(10000); - goto retry; + /* create a socket */ + s = socket(PF_INET, SOCK_STREAM, 0); + if (s < 0) + { + perror("Proxy: socket creation error"); + exit(1); } - perror("Proxy -- connection error"); + + setsockopt(s, SOL_SOCKET, SO_RCVBUF, (char *) &sobufsize, sizeof(sobufsize)); + setsockopt(s, SOL_SOCKET, SO_SNDBUF, (char *) &sobufsize, sizeof(sobufsize)); + i = 1; + setsockopt(s, IPPROTO_TCP, TCP_NODELAY, (char *) &i, sizeof(i)); + i = 0; + setsockopt(s, SOL_SOCKET, SO_KEEPALIVE, (char *) &i, sizeof(i)); + + /* server address */ + memset((char *) &serv_name, 0x00, sizeof(serv_name)); + serv_name.sin_family = AF_INET; + if (monitor == QEMU) + serv_name.sin_addr = INADDR(127, 0, 0, 1); + else + serv_name.sin_addr = HERMIT_IP(isle_nr); + serv_name.sin_port = htons(port); + + i = 0; + retry: + ret = connect(s, (struct sockaddr*)&serv_name, sizeof(serv_name)); + if (ret < 0) + { + i++; + if (i <= 10) { + usleep(10000); + goto retry; + } + perror("Proxy -- connection error"); + close(s); + exit(1); + } + + ret = write(s, &magic, sizeof(magic)); + if (ret < 0) + goto out; + + // forward program arguments to HermitCore + // argv[0] is path of this proxy so we strip it + + argv++; + argc--; + + ret = write(s, &argc, sizeof(argc)); + if (ret < 0) + goto out; + + for(i=0; i +#ifndef __PROXY_H__ +#define __PROXY_H__ -#if 0 -int shmget(key_t key, size_t size, int shmflg) -{ - return 0; -} +#include -void *shmat(int shmid, const void *shmaddr, int shmflg) -{ - return NULL; -} +#define HERMIT_ELFOSABI 0x42 -int shmdt(const void *shmaddr) -{ - return 0; -} +#define __HERMIT_exit 0 +#define __HERMIT_write 1 +#define __HERMIT_open 2 +#define __HERMIT_close 3 +#define __HERMIT_read 4 +#define __HERMIT_lseek 5 + +int uhyve_init(char *path); +int uhyve_loop(void); -int shmctl(int shmid, int cmd, struct shmid_ds *buf) -{ - return 0; -} #endif diff --git a/tools/uhyve-cpu.h b/tools/uhyve-cpu.h new file mode 100644 index 000000000..4a0f23084 --- /dev/null +++ b/tools/uhyve-cpu.h @@ -0,0 +1,98 @@ +#ifndef __UHYVE_CPU_H__ +#define __UHYVE_CPU_H__ + +#ifndef _BITUL + +#ifdef __ASSEMBLY__ +#define _AC(X,Y) X +#define _AT(T,X) X +#else +#define __AC(X,Y) (X##Y) +#define _AC(X,Y) __AC(X,Y) +#define _AT(T,X) ((T)(X)) +#endif + +#define _BITUL(x) (_AC(1,UL) << (x)) +#define _BITULL(x) (_AC(1,ULL) << (x)) + +#endif + +/* + * EFLAGS bits + */ +#define X86_EFLAGS_CF 0x00000001 /* Carry Flag */ + +/* + * Basic CPU control in CR0 + */ +#define X86_CR0_PE_BIT 0 /* Protection Enable */ +#define X86_CR0_PE _BITUL(X86_CR0_PE_BIT) +#define X86_CR0_PG_BIT 31 /* Paging */ +#define X86_CR0_PG _BITUL(X86_CR0_PG_BIT) + +/* + * Intel CPU features in CR4 + */ +#define X86_CR4_PAE_BIT 5 /* enable physical address extensions */ +#define X86_CR4_PAE _BITUL(X86_CR4_PAE_BIT) + +/* + * Intel long mode page directory/table entries + */ +#define X86_PDPT_P_BIT 0 /* Present */ +#define X86_PDPT_P _BITUL(X86_PDPT_P_BIT) +#define X86_PDPT_RW_BIT 1 /* Writable */ +#define X86_PDPT_RW _BITUL(X86_PDPT_RW_BIT) +#define X86_PDPT_PS_BIT 7 /* Page size */ +#define X86_PDPT_PS _BITUL(X86_PDPT_PS_BIT) + +/* + * GDT and KVM segment manipulation + */ + +#define GDT_DESC_OFFSET(n) ((n) * 0x8) + +#define GDT_GET_BASE(x) ( \ + (((x) & 0xFF00000000000000) >> 32) | \ + (((x) & 0x000000FF00000000) >> 16) | \ + (((x) & 0x00000000FFFF0000) >> 16)) + +#define GDT_GET_LIMIT(x) (__u32)( \ + (((x) & 0x000F000000000000) >> 32) | \ + (((x) & 0x000000000000FFFF))) + +/* Constructor for a conventional segment GDT (or LDT) entry */ +/* This is a macro so it can be used in initializers */ +#define GDT_ENTRY(flags, base, limit) \ + ((((base) & _AC(0xff000000, ULL)) << (56-24)) | \ + (((flags) & _AC(0x0000f0ff, ULL)) << 40) | \ + (((limit) & _AC(0x000f0000, ULL)) << (48-16)) | \ + (((base) & _AC(0x00ffffff, ULL)) << 16) | \ + (((limit) & _AC(0x0000ffff, ULL)))) + +#define GDT_GET_G(x) (__u8)(((x) & 0x0080000000000000) >> 55) +#define GDT_GET_DB(x) (__u8)(((x) & 0x0040000000000000) >> 54) +#define GDT_GET_L(x) (__u8)(((x) & 0x0020000000000000) >> 53) +#define GDT_GET_AVL(x) (__u8)(((x) & 0x0010000000000000) >> 52) +#define GDT_GET_P(x) (__u8)(((x) & 0x0000800000000000) >> 47) +#define GDT_GET_DPL(x) (__u8)(((x) & 0x0000600000000000) >> 45) +#define GDT_GET_S(x) (__u8)(((x) & 0x0000100000000000) >> 44) +#define GDT_GET_TYPE(x)(__u8)(((x) & 0x00000F0000000000) >> 40) + +#define GDT_TO_KVM_SEGMENT(seg, gdt_table, sel) \ + do { \ + __u64 gdt_ent = gdt_table[sel]; \ + seg.base = GDT_GET_BASE(gdt_ent); \ + seg.limit = GDT_GET_LIMIT(gdt_ent); \ + seg.selector = sel * 8; \ + seg.type = GDT_GET_TYPE(gdt_ent); \ + seg.present = GDT_GET_P(gdt_ent); \ + seg.dpl = GDT_GET_DPL(gdt_ent); \ + seg.db = GDT_GET_DB(gdt_ent); \ + seg.s = GDT_GET_S(gdt_ent); \ + seg.l = GDT_GET_L(gdt_ent); \ + seg.g = GDT_GET_G(gdt_ent); \ + seg.avl = GDT_GET_AVL(gdt_ent); \ + } while (0) + +#endif diff --git a/tools/uhyve-syscalls.h b/tools/uhyve-syscalls.h new file mode 100644 index 000000000..7b7998e03 --- /dev/null +++ b/tools/uhyve-syscalls.h @@ -0,0 +1,64 @@ +/* Copyright (c) 2017, RWTH Aachen University + * Author(s): Daniel Krebs + * + * Permission to use, copy, modify, and/or distribute this software + * for any purpose with or without fee is hereby granted, provided + * that the above copyright notice and this permission notice appear + * in all copies. + * + * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL + * WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE + * AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR + * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS + * OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, + * NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN + * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + */ +#ifndef UHYVE_SYSCALLS_H +#define UHYVE_SYSCALLS_H + +#include +#include + +typedef enum { + UHYVE_PORT_WRITE = 0x499, + UHYVE_PORT_OPEN = 0x500, + UHYVE_PORT_CLOSE = 0x501, + UHYVE_PORT_READ = 0x502, + UHYVE_PORT_EXIT = 0x503, + UHYVE_PORT_LSEEK = 0x504 +} uhyve_syscall_t; + +typedef struct { + int fd; + const char* buf; + size_t len; +} __attribute__((packed)) uhyve_write_t; + +typedef struct { + const char* name; + int flags; + int mode; + int ret; +} __attribute__((packed)) uhyve_open_t; + +typedef struct { + int fd; + int ret; +} __attribute__((packed)) uhyve_close_t; + +typedef struct { + int fd; + char* buf; + size_t len; + ssize_t ret; +} __attribute__((packed)) uhyve_read_t; + +typedef struct { + int fd; + off_t offset; + int whence; +} __attribute__((packed)) uhyve_lseek_t; + +#endif // UHYVE_SYSCALLS_H diff --git a/tools/uhyve.c b/tools/uhyve.c new file mode 100644 index 000000000..da84a3276 --- /dev/null +++ b/tools/uhyve.c @@ -0,0 +1,1430 @@ +/* Copyright (c) 2015, IBM + * Author(s): Dan Williams + * Ricardo Koller + * Copyright (c) 2017, RWTH Aachen University + * Author(s): Stefan Lankes + * + * Permission to use, copy, modify, and/or distribute this software + * for any purpose with or without fee is hereby granted, provided + * that the above copyright notice and this permission notice appear + * in all copies. + * + * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL + * WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED + * WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE + * AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, INDIRECT, OR + * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS + * OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, + * NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN + * CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + */ + +/* We used several existing projects as guides + * kvmtest.c: http://lwn.net/Articles/658512/ + * Solo5: https://github.com/Solo5/solo5 + */ + +/* + * 15.1.2017: extend original version (https://github.com/Solo5/solo5) + * for HermitCore + * 25.2.2017: add SMP support to enable more than one core + * 24.4.2017: add checkpoint/restore support, + * remove memory limit + */ + +#define _GNU_SOURCE + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include "uhyve-cpu.h" +#include "uhyve-syscalls.h" +#include "proxy.h" + +// define this macro to create checkpoints with KVM's dirty log +//#define USE_DIRTY_LOG + +#define MAX_FNAME 256 +#define MAX_MSR_ENTRIES 25 + +#define GUEST_OFFSET 0x0 +#define CPUID_FUNC_PERFMON 0x0A +#define GUEST_PAGE_SIZE 0x200000 /* 2 MB pages in guest */ + +#define BOOT_GDT 0x1000 +#define BOOT_INFO 0x2000 +#define BOOT_PML4 0x10000 +#define BOOT_PDPTE 0x11000 +#define BOOT_PDE 0x12000 + +#define BOOT_GDT_NULL 0 +#define BOOT_GDT_CODE 1 +#define BOOT_GDT_DATA 2 +#define BOOT_GDT_MAX 3 + +#define KVM_32BIT_MAX_MEM_SIZE (1ULL << 32) +#define KVM_32BIT_GAP_SIZE (768 << 20) +#define KVM_32BIT_GAP_START (KVM_32BIT_MAX_MEM_SIZE - KVM_32BIT_GAP_SIZE) + +/// Page offset bits +#define PAGE_BITS 12 +#define PAGE_2M_BITS 21 +#define PAGE_SIZE (1L << PAGE_BITS) +/// Mask the page address without page map flags and XD flag +#if 0 +#define PAGE_MASK ((~0L) << PAGE_BITS) +#define PAGE_2M_MASK (~0L) << PAGE_2M_BITS) +#else +#define PAGE_MASK (((~0L) << PAGE_BITS) & ~PG_XD) +#define PAGE_2M_MASK (((~0L) << PAGE_2M_BITS) & ~PG_XD) +#endif + +// Page is present +#define PG_PRESENT (1 << 0) +// Page is read- and writable +#define PG_RW (1 << 1) +// Page is addressable from userspace +#define PG_USER (1 << 2) +// Page write through is activated +#define PG_PWT (1 << 3) +// Page cache is disabled +#define PG_PCD (1 << 4) +// Page was recently accessed (set by CPU) +#define PG_ACCESSED (1 << 5) +// Page is dirty due to recent write-access (set by CPU) +#define PG_DIRTY (1 << 6) +// Huge page: 4MB (or 2MB, 1GB) +#define PG_PSE (1 << 7) +// Page attribute table +#define PG_PAT PG_PSE +#if 1 +/* @brief Global TLB entry (Pentium Pro and later) + * + * HermitCore is a single-address space operating system + * => CR3 never changed => The flag isn't required for HermitCore + */ +#define PG_GLOBAL 0 +#else +#define PG_GLOBAL (1 << 8) +#endif +// This table is a self-reference and should skipped by page_map_copy() +#define PG_SELF (1 << 9) + +/// Disable execution for this page +#define PG_XD (1L << 63) + +#define BITS 64 +#define PHYS_BITS 52 +#define VIRT_BITS 48 +#define PAGE_MAP_BITS 9 +#define PAGE_LEVELS 4 + +#define kvm_ioctl(fd, cmd, arg) ({ \ + const int ret = ioctl(fd, cmd, arg); \ + if(ret == -1) \ + err(1, "KVM: ioctl " #cmd " failed"); \ + ret; \ + }) + +static bool restart = false; +static bool cap_tsc_deadline = false; +static bool cap_irqchip = false; +static bool cap_adjust_clock_stable = false; +static bool verbose = false; +static bool full_checkpoint = false; +static uint32_t ncores = 1; +static uint8_t* guest_mem = NULL; +static uint8_t* klog = NULL; +static uint8_t* mboot = NULL; +static size_t guest_size = 0x20000000ULL; +static uint64_t elf_entry; +static pthread_t* vcpu_threads = NULL; +static int* vcpu_fds = NULL; +static int kvm = -1, vmfd = -1; +static uint32_t no_checkpoint = 0; +static pthread_mutex_t kvm_lock = PTHREAD_MUTEX_INITIALIZER; +static pthread_barrier_t barrier; +static __thread struct kvm_run *run = NULL; +static __thread int vcpufd = -1; +static __thread uint32_t cpuid = 0; + +static uint64_t memparse(const char *ptr) +{ + // local pointer to end of parsed string + char *endptr; + + // parse number + uint64_t size = strtoull(ptr, &endptr, 0); + + // parse size extension, intentional fall-through + switch (*endptr) { + case 'E': + case 'e': + size <<= 10; + case 'P': + case 'p': + size <<= 10; + case 'T': + case 't': + size <<= 10; + case 'G': + case 'g': + size <<= 10; + case 'M': + case 'm': + size <<= 10; + case 'K': + case 'k': + size <<= 10; + endptr++; + default: + break; + } + + return size; +} + +// Just close file descriptor if not already done +static inline void close_fd(int* fd) +{ + if (*fd != -1) { + close(*fd); + *fd = -1; + } +} + +static void uhyve_exit(void* arg) +{ + if (pthread_mutex_trylock(&kvm_lock)) + { + close_fd(&vcpufd); + return; + } + + // only the main thread will execute this + if (vcpu_threads) { + for(uint32_t i=0; i '9')) && (*match != '\0') ) + match++; + + freq = (uint32_t) atoi(match); + break; + } + } + + fclose(fp); + } + + return freq; +} + +static ssize_t pread_in_full(int fd, void *buf, size_t count, off_t offset) +{ + ssize_t total = 0; + char *p = buf; + + if (count > SSIZE_MAX) { + errno = E2BIG; + return -1; + } + + while (count > 0) { + ssize_t nr; + + nr = pread(fd, p, count, offset); + if (nr == 0) + return total; + else if (nr == -1 && errno == EINTR) + continue; + else if (nr == -1) + return -1; + + count -= nr; + total += nr; + p += nr; + offset += nr; + } + + return total; +} + +static int load_kernel(uint8_t* mem, char* path) +{ + Elf64_Ehdr hdr; + Elf64_Phdr *phdr = NULL; + size_t buflen; + int fd, ret; + int first_load = 1; + + fd = open(path, O_RDONLY); + if (fd == -1) + { + perror("Unable to open file"); + return -1; + } + + ret = pread_in_full(fd, &hdr, sizeof(hdr), 0); + if (ret < 0) + goto out; + + // check if the program is a HermitCore file + if (hdr.e_ident[EI_MAG0] != ELFMAG0 + || hdr.e_ident[EI_MAG1] != ELFMAG1 + || hdr.e_ident[EI_MAG2] != ELFMAG2 + || hdr.e_ident[EI_MAG3] != ELFMAG3 + || hdr.e_ident[EI_CLASS] != ELFCLASS64 + || hdr.e_ident[EI_OSABI] != HERMIT_ELFOSABI + || hdr.e_type != ET_EXEC || hdr.e_machine != EM_X86_64) { + fprintf(stderr, "Inavlide HermitCore file!\n"); + goto out; + } + + elf_entry = hdr.e_entry; + + buflen = hdr.e_phentsize * hdr.e_phnum; + phdr = malloc(buflen); + if (!phdr) { + fprintf(stderr, "Not enough memory\n"); + goto out; + } + + ret = pread_in_full(fd, phdr, buflen, hdr.e_phoff); + if (ret < 0) + goto out; + + /* + * Load all segments with type "LOAD" from the file at offset + * p_offset, and copy that into in memory. + */ + for (Elf64_Half ph_i = 0; ph_i < hdr.e_phnum; ph_i++) + { + uint64_t paddr = phdr[ph_i].p_paddr; + size_t offset = phdr[ph_i].p_offset; + size_t filesz = phdr[ph_i].p_filesz; + size_t memsz = phdr[ph_i].p_memsz; + + if (phdr[ph_i].p_type != PT_LOAD) + continue; + + //printf("Kernel location 0x%zx, file size 0x%zx, memory size 0x%zx\n", paddr, filesz, memsz); + + ret = pread_in_full(fd, mem+paddr-GUEST_OFFSET, filesz, offset); + if (ret < 0) + goto out; + if (!klog) + klog = mem+paddr+0x5000-GUEST_OFFSET; + if (!mboot) + mboot = mem+paddr-GUEST_OFFSET; + + if (first_load) { + first_load = 0; + + // initialize kernel + *((uint64_t*) (mem+paddr-GUEST_OFFSET + 0x08)) = paddr; // physical start address + *((uint64_t*) (mem+paddr-GUEST_OFFSET + 0x10)) = guest_size; // physical limit + *((uint32_t*) (mem+paddr-GUEST_OFFSET + 0x18)) = get_cpufreq(); + *((uint32_t*) (mem+paddr-GUEST_OFFSET + 0x24)) = 1; // number of used cpus + *((uint32_t*) (mem+paddr-GUEST_OFFSET + 0x30)) = 0; // apicid + *((uint32_t*) (mem+paddr-GUEST_OFFSET + 0x60)) = 1; // numa nodes + *((uint32_t*) (mem+paddr-GUEST_OFFSET + 0x94)) = 1; // announce uhyve + } + *((uint64_t*) (mem+paddr-GUEST_OFFSET + 0x38)) += memsz; // total kernel size + } + +out: + if (phdr) + free(phdr); + + close(fd); + + return 0; +} + +static int load_checkpoint(uint8_t* mem, char* path) +{ + char fname[MAX_FNAME]; + size_t location; + size_t paddr = elf_entry; + int ret; + struct timeval begin, end; + uint32_t i; + + if (verbose) + gettimeofday(&begin, NULL); + + if (!klog) + klog = mem+paddr+0x5000-GUEST_OFFSET; + if (!mboot) + mboot = mem+paddr-GUEST_OFFSET; + + +#ifdef USE_DIRTY_LOG + /* + * if we use KVM's dirty page logging, we have to load + * the elf image because most parts are readonly sections + * and aren't able to detect by KVM's dirty page logging + * technique. + */ + ret = load_kernel(mem, path); + if (ret) + return ret; +#endif + + i = full_checkpoint ? no_checkpoint : 0; + for(; i<=no_checkpoint; i++) + { + snprintf(fname, MAX_FNAME, "checkpoint/chk%u_mem.dat", i); + + FILE* f = fopen(fname, "r"); + if (f == NULL) + return -1; + + /*struct kvm_irqchip irqchip; + if (fread(&irqchip, sizeof(irqchip), 1, f) != 1) + err(1, "fread failed"); + if (cap_irqchip && (i == no_checkpoint-1)) + kvm_ioctl(vmfd, KVM_SET_IRQCHIP, &irqchip);*/ + + struct kvm_clock_data clock; + if (fread(&clock, sizeof(clock), 1, f) != 1) + err(1, "fread failed"); + // only the last checkpoint has to set the clock + if (cap_adjust_clock_stable && (i == no_checkpoint)) { + struct kvm_clock_data data = {}; + + data.clock = clock.clock; + kvm_ioctl(vmfd, KVM_SET_CLOCK, &data); + } + +#if 0 + if (fread(guest_mem, guest_size, 1, f) != 1) + err(1, "fread failed"); +#else + + while (fread(&location, sizeof(location), 1, f) == 1) { + //printf("location 0x%zx\n", location); + if (location & PG_PSE) + ret = fread((size_t*) (mem + (location & PAGE_2M_MASK)), (1UL << PAGE_2M_BITS), 1, f); + else + ret = fread((size_t*) (mem + (location & PAGE_MASK)), (1UL << PAGE_BITS), 1, f); + + if (ret != 1) { + fprintf(stderr, "Unable to read checkpoint: ret = %d", ret); + err(1, "fread failed"); + } + } +#endif + + fclose(f); + } + + if (verbose) { + gettimeofday(&end, NULL); + size_t msec = (end.tv_sec - begin.tv_sec) * 1000; + msec += (end.tv_usec - begin.tv_usec) / 1000; + fprintf(stderr, "Load checkpoint %u in %zd ms\n", no_checkpoint, msec); + } + + return 0; +} + +static inline void show_dtable(const char *name, struct kvm_dtable *dtable) +{ + fprintf(stderr, " %s %016zx %08hx\n", name, (size_t) dtable->base, (uint16_t) dtable->limit); +} + +static inline void show_segment(const char *name, struct kvm_segment *seg) +{ + fprintf(stderr, " %s %04hx %016zx %08x %02hhx %x %x %x %x %x %x %x\n", + name, (uint16_t) seg->selector, (size_t) seg->base, (uint32_t) seg->limit, + (uint8_t) seg->type, seg->present, seg->dpl, seg->db, seg->s, seg->l, seg->g, seg->avl); +} + +static void show_registers(int id, struct kvm_regs* regs, struct kvm_sregs* sregs) +{ + size_t cr0, cr2, cr3; + size_t cr4, cr8; + size_t rax, rbx, rcx; + size_t rdx, rsi, rdi; + size_t rbp, r8, r9; + size_t r10, r11, r12; + size_t r13, r14, r15; + size_t rip, rsp; + size_t rflags; + int i; + + rflags = regs->rflags; + rip = regs->rip; rsp = regs->rsp; + rax = regs->rax; rbx = regs->rbx; rcx = regs->rcx; + rdx = regs->rdx; rsi = regs->rsi; rdi = regs->rdi; + rbp = regs->rbp; r8 = regs->r8; r9 = regs->r9; + r10 = regs->r10; r11 = regs->r11; r12 = regs->r12; + r13 = regs->r13; r14 = regs->r14; r15 = regs->r15; + + fprintf(stderr, "\n Dump state of CPU %d\n", id); + fprintf(stderr, "\n Registers:\n"); + fprintf(stderr, " ----------\n"); + fprintf(stderr, " rip: %016zx rsp: %016zx flags: %016zx\n", rip, rsp, rflags); + fprintf(stderr, " rax: %016zx rbx: %016zx rcx: %016zx\n", rax, rbx, rcx); + fprintf(stderr, " rdx: %016zx rsi: %016zx rdi: %016zx\n", rdx, rsi, rdi); + fprintf(stderr, " rbp: %016zx r8: %016zx r9: %016zx\n", rbp, r8, r9); + fprintf(stderr, " r10: %016zx r11: %016zx r12: %016zx\n", r10, r11, r12); + fprintf(stderr, " r13: %016zx r14: %016zx r15: %016zx\n", r13, r14, r15); + + cr0 = sregs->cr0; cr2 = sregs->cr2; cr3 = sregs->cr3; + cr4 = sregs->cr4; cr8 = sregs->cr8; + + fprintf(stderr, " cr0: %016zx cr2: %016zx cr3: %016zx\n", cr0, cr2, cr3); + fprintf(stderr, " cr4: %016zx cr8: %016zx\n", cr4, cr8); + fprintf(stderr, "\n Segment registers:\n"); + fprintf(stderr, " ------------------\n"); + fprintf(stderr, " register selector base limit type p dpl db s l g avl\n"); + show_segment("cs ", &sregs->cs); + show_segment("ss ", &sregs->ss); + show_segment("ds ", &sregs->ds); + show_segment("es ", &sregs->es); + show_segment("fs ", &sregs->fs); + show_segment("gs ", &sregs->gs); + show_segment("tr ", &sregs->tr); + show_segment("ldt", &sregs->ldt); + show_dtable("gdt", &sregs->gdt); + show_dtable("idt", &sregs->idt); + + fprintf(stderr, "\n APIC:\n"); + fprintf(stderr, " -----\n"); + fprintf(stderr, " efer: %016zx apic base: %016zx\n", + (size_t) sregs->efer, (size_t) sregs->apic_base); + + fprintf(stderr, "\n Interrupt bitmap:\n"); + fprintf(stderr, " -----------------\n"); + for (i = 0; i < (KVM_NR_INTERRUPTS + 63) / 64; i++) + fprintf(stderr, " %016zx", (size_t) sregs->interrupt_bitmap[i]); + fprintf(stderr, "\n"); +} + +static int print_registers(void) +{ + struct kvm_regs regs; + struct kvm_sregs sregs; + + kvm_ioctl(vcpufd, KVM_GET_SREGS, &sregs); + kvm_ioctl(vcpufd, KVM_GET_REGS, ®s); + + show_registers(cpuid, ®s, &sregs); +} + +/// Filter CPUID functions that are not supported by the hypervisor and enable +/// features according to our needs. +static void filter_cpuid(struct kvm_cpuid2 *kvm_cpuid) +{ + for (uint32_t i = 0; i < kvm_cpuid->nent; i++) { + struct kvm_cpuid_entry2 *entry = &kvm_cpuid->entries[i]; + + switch (entry->function) { + case 1: + // CPUID to define basic cpu features + entry->ecx |= (1U << 31); // propagate that we are running on a hypervisor + if (cap_tsc_deadline) + entry->ecx |= (1U << 24); // enable TSC deadline feature + entry->edx |= (1U << 5); // enable msr support + break; + + case CPUID_FUNC_PERFMON: + // disable it + entry->eax = 0x00; + break; + + default: + // Keep the CPUID function as-is + break; + }; + } +} + +static void setup_system_64bit(struct kvm_sregs *sregs) +{ + sregs->cr0 |= X86_CR0_PE; + sregs->efer |= EFER_LME; +} + +static void setup_system_page_tables(struct kvm_sregs *sregs, uint8_t *mem) +{ + uint64_t *pml4 = (uint64_t *) (mem + BOOT_PML4); + uint64_t *pdpte = (uint64_t *) (mem + BOOT_PDPTE); + uint64_t *pde = (uint64_t *) (mem + BOOT_PDE); + uint64_t paddr; + + /* + * For simplicity we currently use 2MB pages and only a single + * PML4/PDPTE/PDE. + */ + + memset(pml4, 0x00, 4096); + memset(pdpte, 0x00, 4096); + memset(pde, 0x00, 4096); + + *pml4 = BOOT_PDPTE | (X86_PDPT_P | X86_PDPT_RW); + *pdpte = BOOT_PDE | (X86_PDPT_P | X86_PDPT_RW); + for (paddr = 0; paddr < 0x20000000ULL; paddr += GUEST_PAGE_SIZE, pde++) + *pde = paddr | (X86_PDPT_P | X86_PDPT_RW | X86_PDPT_PS); + + sregs->cr3 = BOOT_PML4; + sregs->cr4 |= X86_CR4_PAE; + sregs->cr0 |= X86_CR0_PG; +} + +static void setup_system_gdt(struct kvm_sregs *sregs, + uint8_t *mem, + uint64_t off) +{ + uint64_t *gdt = (uint64_t *) (mem + off); + struct kvm_segment data_seg, code_seg; + + /* flags, base, limit */ + gdt[BOOT_GDT_NULL] = GDT_ENTRY(0, 0, 0); + gdt[BOOT_GDT_CODE] = GDT_ENTRY(0xA09B, 0, 0xFFFFF); + gdt[BOOT_GDT_DATA] = GDT_ENTRY(0xC093, 0, 0xFFFFF); + + sregs->gdt.base = off; + sregs->gdt.limit = (sizeof(uint64_t) * BOOT_GDT_MAX) - 1; + + GDT_TO_KVM_SEGMENT(code_seg, gdt, BOOT_GDT_CODE); + GDT_TO_KVM_SEGMENT(data_seg, gdt, BOOT_GDT_DATA); + + sregs->cs = code_seg; + sregs->ds = data_seg; + sregs->es = data_seg; + sregs->fs = data_seg; + sregs->gs = data_seg; + sregs->ss = data_seg; +} + +static void setup_system(int vcpufd, uint8_t *mem, uint32_t id) +{ + static struct kvm_sregs sregs; + + // all cores use the same startup code + // => all cores use the same sregs + // => only the boot processor has to initialize sregs + if (id == 0) { + kvm_ioctl(vcpufd, KVM_GET_SREGS, &sregs); + + /* Set all cpu/mem system structures */ + setup_system_gdt(&sregs, mem, BOOT_GDT); + setup_system_page_tables(&sregs, mem); + setup_system_64bit(&sregs); + } + + kvm_ioctl(vcpufd, KVM_SET_SREGS, &sregs); +} + +static void setup_cpuid(int kvm, int vcpufd) +{ + struct kvm_cpuid2 *kvm_cpuid; + unsigned int max_entries = 100; + + // allocate space for cpuid we get from KVM + kvm_cpuid = calloc(1, sizeof(*kvm_cpuid) + (max_entries * sizeof(kvm_cpuid->entries[0]))); + kvm_cpuid->nent = max_entries; + + kvm_ioctl(kvm, KVM_GET_SUPPORTED_CPUID, kvm_cpuid); + + // set features + filter_cpuid(kvm_cpuid); + kvm_ioctl(vcpufd, KVM_SET_CPUID2, kvm_cpuid); + + free(kvm_cpuid); +} + +static int vcpu_loop(void) +{ + int ret; + + if (restart) { + pthread_barrier_wait(&barrier); + if (cpuid == 0) + no_checkpoint++; + } + + while (1) { + ret = ioctl(vcpufd, KVM_RUN, NULL); + + if(ret == -1) { + switch(errno) { + case EINTR: + continue; + + case EFAULT: { + struct kvm_regs regs; + kvm_ioctl(vcpufd, KVM_GET_REGS, ®s); + err(1, "KVM: host/guest translation fault: rip=0x%llx", regs.rip); + } + + default: + err(1, "KVM: ioctl KVM_RUN in vcpu_loop failed"); + break; + } + } + + /* handle requests */ + switch (run->exit_reason) { + case KVM_EXIT_HLT: + fprintf(stderr, "Guest has halted the CPU, this is considered as a normal exit.\n"); + return 0; + + case KVM_EXIT_MMIO: + err(1, "KVM: unhandled KVM_EXIT_MMIO at 0x%llx\n", run->mmio.phys_addr); + break; + + case KVM_EXIT_IO: + //printf("port 0x%x\n", run->io.port); + switch (run->io.port) { + case UHYVE_PORT_WRITE: { + unsigned data = *((unsigned*)((size_t)run+run->io.data_offset)); + uhyve_write_t* uhyve_write = (uhyve_write_t*) (guest_mem+data); + + uhyve_write->len = write(uhyve_write->fd, guest_mem+(size_t)uhyve_write->buf, uhyve_write->len); + break; + } + + case UHYVE_PORT_READ: { + unsigned data = *((unsigned*)((size_t)run+run->io.data_offset)); + uhyve_read_t* uhyve_read = (uhyve_read_t*) (guest_mem+data); + + uhyve_read->ret = read(uhyve_read->fd, guest_mem+(size_t)uhyve_read->buf, uhyve_read->len); + break; + } + + case UHYVE_PORT_EXIT: { + unsigned data = *((unsigned*)((size_t)run+run->io.data_offset)); + + if (cpuid) + pthread_exit((int*)(guest_mem+data)); + else + exit(*(int*)(guest_mem+data)); + break; + } + + case UHYVE_PORT_OPEN: { + unsigned data = *((unsigned*)((size_t)run+run->io.data_offset)); + uhyve_open_t* uhyve_open = (uhyve_open_t*) (guest_mem+data); + + uhyve_open->ret = open((const char*)guest_mem+(size_t)uhyve_open->name, uhyve_open->flags, uhyve_open->mode); + break; + } + + case UHYVE_PORT_CLOSE: { + unsigned data = *((unsigned*)((size_t)run+run->io.data_offset)); + uhyve_close_t* uhyve_close = (uhyve_close_t*) (guest_mem+data); + + if (uhyve_close->fd > 2) + uhyve_close->ret = close(uhyve_close->fd); + else + uhyve_close->ret = 0; + break; + } + + case UHYVE_PORT_LSEEK: { + unsigned data = *((unsigned*)((size_t)run+run->io.data_offset)); + uhyve_lseek_t* uhyve_lseek = (uhyve_lseek_t*) (guest_mem+data); + + uhyve_lseek->offset = lseek(uhyve_lseek->fd, uhyve_lseek->offset, uhyve_lseek->whence); + break; + } + default: + err(1, "KVM: unhandled KVM_EXIT_IO at port 0x%x, direction %d\n", run->io.port, run->io.direction); + break; + } + break; + + case KVM_EXIT_FAIL_ENTRY: + err(1, "KVM: entry failure: hw_entry_failure_reason=0x%llx\n", + run->fail_entry.hardware_entry_failure_reason); + break; + + case KVM_EXIT_INTERNAL_ERROR: + err(1, "KVM: internal error exit: suberror = 0x%x\n", run->internal.suberror); + break; + + case KVM_EXIT_SHUTDOWN: + err(1, "KVM: receive shutdown command\n"); + break; + + case KVM_EXIT_DEBUG: + print_registers(); + default: + fprintf(stderr, "KVM: unhandled exit: exit_reason = 0x%x\n", run->exit_reason); + exit(EXIT_FAILURE); + } + } + + close(vcpufd); + vcpufd = -1; + + return 0; +} + +static int vcpu_init(void) +{ + struct kvm_mp_state mp_state = { KVM_MP_STATE_RUNNABLE }; + struct kvm_regs regs = { + .rip = elf_entry, // entry point to HermitCore + .rflags = 0x2, // POR value required by x86 architecture + }; + + vcpu_fds[cpuid] = vcpufd = kvm_ioctl(vmfd, KVM_CREATE_VCPU, cpuid); + + /* Map the shared kvm_run structure and following data. */ + size_t mmap_size = (size_t) kvm_ioctl(kvm, KVM_GET_VCPU_MMAP_SIZE, NULL); + + if (mmap_size < sizeof(*run)) + err(1, "KVM: invalid VCPU_MMAP_SIZE: %zd", mmap_size); + + run = mmap(NULL, mmap_size, PROT_READ | PROT_WRITE, MAP_SHARED, vcpufd, 0); + if (run == MAP_FAILED) + err(1, "KVM: VCPU mmap failed"); + + setup_cpuid(kvm, vcpufd); + + if (restart) { + char fname[MAX_FNAME]; + struct kvm_sregs sregs; + struct kvm_fpu fpu; + struct { + struct kvm_msrs info; + struct kvm_msr_entry entries[MAX_MSR_ENTRIES]; + } msr_data; + struct kvm_lapic_state lapic; + struct kvm_xsave xsave; + struct kvm_xcrs xcrs; + struct kvm_vcpu_events events; + + snprintf(fname, MAX_FNAME, "checkpoint/chk%u_core%u.dat", no_checkpoint, cpuid); + + FILE* f = fopen(fname, "r"); + if (f == NULL) + err(1, "fopen: unable to open file"); + + if (fread(&sregs, sizeof(sregs), 1, f) != 1) + err(1, "fread failed\n"); + if (fread(®s, sizeof(regs), 1, f) != 1) + err(1, "fread failed\n"); + if (fread(&fpu, sizeof(fpu), 1, f) != 1) + err(1, "fread failed\n"); + if (fread(&msr_data, sizeof(msr_data), 1, f) != 1) + err(1, "fread failed\n"); + if (fread(&lapic, sizeof(lapic), 1, f) != 1) + err(1, "fread failed\n"); + if (fread(&xsave, sizeof(xsave), 1, f) != 1) + err(1, "fread failed\n"); + if (fread(&xcrs, sizeof(xcrs), 1, f) != 1) + err(1, "fread failed\n"); + if (fread(&events, sizeof(events), 1, f) != 1) + err(1, "fread failed\n"); + if (fread(&mp_state, sizeof(mp_state), 1, f) != 1) + err(1, "fread failed\n"); + + fclose(f); + + kvm_ioctl(vcpufd, KVM_SET_SREGS, &sregs); + kvm_ioctl(vcpufd, KVM_SET_REGS, ®s); + kvm_ioctl(vcpufd, KVM_SET_MSRS, &msr_data); + kvm_ioctl(vcpufd, KVM_SET_XCRS, &xcrs); + kvm_ioctl(vcpufd, KVM_SET_MP_STATE, &mp_state); + kvm_ioctl(vcpufd, KVM_SET_LAPIC, &lapic); + kvm_ioctl(vcpufd, KVM_SET_FPU, &fpu); + kvm_ioctl(vcpufd, KVM_SET_XSAVE, &xsave); + kvm_ioctl(vcpufd, KVM_SET_VCPU_EVENTS, &events); + } else { + // be sure that the multiprocessor is runable + kvm_ioctl(vcpufd, KVM_SET_MP_STATE, &mp_state); + + /* Setup registers and memory. */ + setup_system(vcpufd, guest_mem, cpuid); + kvm_ioctl(vcpufd, KVM_SET_REGS, ®s); + + // only one core is able to enter startup code + // => the wait for the predecessor core + while (*((volatile uint32_t*) (mboot + 0x20)) < cpuid) + pthread_yield(); + *((volatile uint32_t*) (mboot + 0x30)) = cpuid; + } + + return 0; +} + +static void save_cpu_state(void) +{ + struct { + struct kvm_msrs info; + struct kvm_msr_entry entries[MAX_MSR_ENTRIES]; + } msr_data; + struct kvm_msr_entry *msrs = msr_data.entries; + struct kvm_regs regs; + struct kvm_sregs sregs; + struct kvm_fpu fpu; + struct kvm_lapic_state lapic; + struct kvm_xsave xsave; + struct kvm_xcrs xcrs; + struct kvm_vcpu_events events; + struct kvm_mp_state mp_state; + char fname[MAX_FNAME]; + int n = 0; + + /* define the list of required MSRs */ + msrs[n++].index = MSR_IA32_APICBASE; + msrs[n++].index = MSR_IA32_SYSENTER_CS; + msrs[n++].index = MSR_IA32_SYSENTER_ESP; + msrs[n++].index = MSR_IA32_SYSENTER_EIP; + msrs[n++].index = MSR_IA32_CR_PAT; + msrs[n++].index = MSR_IA32_MISC_ENABLE; + msrs[n++].index = MSR_IA32_TSC; + msrs[n++].index = MSR_CSTAR; + msrs[n++].index = MSR_STAR; + msrs[n++].index = MSR_EFER; + msrs[n++].index = MSR_LSTAR; + msrs[n++].index = MSR_GS_BASE; + msrs[n++].index = MSR_FS_BASE; + msrs[n++].index = MSR_KERNEL_GS_BASE; + //msrs[n++].index = MSR_IA32_FEATURE_CONTROL; + msr_data.info.nmsrs = n; + + kvm_ioctl(vcpufd, KVM_GET_SREGS, &sregs); + kvm_ioctl(vcpufd, KVM_GET_REGS, ®s); + kvm_ioctl(vcpufd, KVM_GET_MSRS, &msr_data); + kvm_ioctl(vcpufd, KVM_GET_XCRS, &xcrs); + kvm_ioctl(vcpufd, KVM_GET_LAPIC, &lapic); + kvm_ioctl(vcpufd, KVM_GET_FPU, &fpu); + kvm_ioctl(vcpufd, KVM_GET_XSAVE, &xsave); + kvm_ioctl(vcpufd, KVM_GET_VCPU_EVENTS, &events); + kvm_ioctl(vcpufd, KVM_GET_MP_STATE, &mp_state); + + snprintf(fname, MAX_FNAME, "checkpoint/chk%u_core%u.dat", no_checkpoint, cpuid); + + FILE* f = fopen(fname, "w"); + if (f == NULL) { + err(1, "fopen: unable to open file\n"); + } + + if (fwrite(&sregs, sizeof(sregs), 1, f) != 1) + err(1, "fwrite failed\n"); + if (fwrite(®s, sizeof(regs), 1, f) != 1) + err(1, "fwrite failed\n"); + if (fwrite(&fpu, sizeof(fpu), 1, f) != 1) + err(1, "fwrite failed\n"); + if (fwrite(&msr_data, sizeof(msr_data), 1, f) != 1) + err(1, "fwrite failed\n"); + if (fwrite(&lapic, sizeof(lapic), 1, f) != 1) + err(1, "fwrite failed\n"); + if (fwrite(&xsave, sizeof(xsave), 1, f) != 1) + err(1, "fwrite failed\n"); + if (fwrite(&xcrs, sizeof(xcrs), 1, f) != 1) + err(1, "fwrite failed\n"); + if (fwrite(&events, sizeof(events), 1, f) != 1) + err(1, "fwrite failed\n"); + if (fwrite(&mp_state, sizeof(mp_state), 1, f) != 1) + err(1, "fwrite failed\n"); + + fclose(f); +} + +static void sigusr_handler(int signum) +{ + pthread_barrier_wait(&barrier); + + save_cpu_state(); + + pthread_barrier_wait(&barrier); +} + +static void* uhyve_thread(void* arg) +{ + size_t ret; + struct sigaction sa; + + pthread_cleanup_push(uhyve_exit, NULL); + + cpuid = (size_t) arg; + + /* Install timer_handler as the signal handler for SIGVTALRM. */ + memset(&sa, 0x00, sizeof(sa)); + sa.sa_handler = &sigusr_handler; + sigaction(SIGRTMIN, &sa, NULL); + + // create new cpu + vcpu_init(); + + // run cpu loop until thread gets killed + ret = vcpu_loop(); + + pthread_cleanup_pop(1); + + return (void*) ret; +} + +void sigterm_handler(int signum) +{ + pthread_exit(0); +} + +int uhyve_init(char *path) +{ + char* v = getenv("HERMIT_VERBOSE"); + if (v && (strcmp(v, "0") != 0)) + verbose = true; + + signal(SIGTERM, sigterm_handler); + + // register routine to close the VM + atexit(uhyve_atexit); + + FILE* f = fopen("checkpoint/chk_config.txt", "r"); + if (f != NULL) { + int tmp = 0; + restart = true; + + fscanf(f, "number of cores: %u\n", &ncores); + fscanf(f, "memory size: 0x%zx\n", &guest_size); + fscanf(f, "checkpoint number: %u\n", &no_checkpoint); + fscanf(f, "entry point: 0x%zx", &elf_entry); + fscanf(f, "full checkpoint: %d", &tmp); + full_checkpoint = tmp ? true : false; + + if (verbose) + fprintf(stderr, "Restart from checkpoint %u (ncores %d, mem size 0x%zx)\n", no_checkpoint, ncores, guest_size); + fclose(f); + } else { + const char* hermit_memory = getenv("HERMIT_MEM"); + if (hermit_memory) + guest_size = memparse(hermit_memory); + + const char* hermit_cpus = getenv("HERMIT_CPUS"); + if (hermit_cpus) + ncores = (uint32_t) atoi(hermit_cpus); + + const char* full_chk = getenv("HERMIT_FULLCHECKPOINT"); + if (full_chk && (strcmp(full_chk, "0") != 0)) + full_checkpoint = true; + } + + vcpu_threads = (pthread_t*) calloc(ncores, sizeof(pthread_t)); + if (!vcpu_threads) + err(1, "Not enough memory"); + + vcpu_fds = (int*) calloc(ncores, sizeof(int)); + if (!vcpu_fds) + err(1, "Not enough memory"); + + kvm = open("/dev/kvm", O_RDWR | O_CLOEXEC); + if (kvm < 0) + err(1, "Could not open: /dev/kvm"); + + /* Make sure we have the stable version of the API */ + int kvm_api_version = kvm_ioctl(kvm, KVM_GET_API_VERSION, NULL); + if (kvm_api_version != 12) + err(1, "KVM: API version is %d, uhyve requires version 12", kvm_api_version); + + /* Create the virtual machine */ + vmfd = kvm_ioctl(kvm, KVM_CREATE_VM, 0); + + uint64_t identity_base = 0xfffbc000; + if (ioctl(vmfd, KVM_CHECK_EXTENSION, KVM_CAP_SYNC_MMU) > 0) { + /* Allows up to 16M BIOSes. */ + identity_base = 0xfeffc000; + + kvm_ioctl(vmfd, KVM_SET_IDENTITY_MAP_ADDR, &identity_base); + } + kvm_ioctl(vmfd, KVM_SET_TSS_ADDR, identity_base + 0x1000); + + /* + * Allocate page-aligned guest memory. + * + * TODO: support of huge pages + */ + if (guest_size < KVM_32BIT_GAP_START) { + guest_mem = mmap(NULL, guest_size, PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_ANONYMOUS, -1, 0); + if (guest_mem == MAP_FAILED) + err(1, "mmap failed"); + } else { + guest_size += + KVM_32BIT_GAP_SIZE; + guest_mem = mmap(NULL, guest_size, PROT_READ | PROT_WRITE, MAP_PRIVATE | MAP_ANONYMOUS, -1, 0); + if (guest_mem == MAP_FAILED) + err(1, "mmap failed"); + + /* + * We mprotect the gap PROT_NONE so that if we accidently write to it, we will know. + */ + mprotect(guest_mem + KVM_32BIT_GAP_START, KVM_32BIT_GAP_SIZE, PROT_NONE); + } + + const char* merge = getenv("HERMIT_MERGEABLE"); + if (merge && (strcmp(merge, "0") != 0)) { + /* + * The KSM feature is intended for applications that generate + * many instances of the same data (e.g., virtualization systems + * such as KVM). It can consume a lot of processing power! + */ + madvise(guest_mem, guest_size, MADV_MERGEABLE); + if (verbose) + fprintf(stderr, "VM uses KSN feature \"mergeable\" to reduce the memory footprint.\n"); + } + + struct kvm_userspace_memory_region kvm_region = { + .slot = 0, + .guest_phys_addr = GUEST_OFFSET, + .memory_size = guest_size, + .userspace_addr = (uint64_t) guest_mem, +#ifdef USE_DIRTY_LOG + .flags = KVM_MEM_LOG_DIRTY_PAGES, +#else + .flags = 0, +#endif + }; + + if (guest_size <= KVM_32BIT_GAP_START - GUEST_OFFSET) { + kvm_ioctl(vmfd, KVM_SET_USER_MEMORY_REGION, &kvm_region); + } else { + kvm_region.memory_size = KVM_32BIT_GAP_START - GUEST_OFFSET; + kvm_ioctl(vmfd, KVM_SET_USER_MEMORY_REGION, &kvm_region); + + kvm_region.slot = 1; + kvm_region.guest_phys_addr = KVM_32BIT_GAP_START+KVM_32BIT_GAP_SIZE; + kvm_region.memory_size = guest_size - KVM_32BIT_GAP_SIZE - KVM_32BIT_GAP_START + GUEST_OFFSET; + kvm_ioctl(vmfd, KVM_SET_USER_MEMORY_REGION, &kvm_region); + } + + kvm_ioctl(vmfd, KVM_CREATE_IRQCHIP, NULL); + +#ifdef KVM_CAP_X2APIC_API + // enable x2APIC support + struct kvm_enable_cap cap = { + .cap = KVM_CAP_X2APIC_API, + .flags = 0, + .args[0] = KVM_X2APIC_API_USE_32BIT_IDS|KVM_X2APIC_API_DISABLE_BROADCAST_QUIRK, + }; + kvm_ioctl(vmfd, KVM_ENABLE_CAP, &cap); +#endif + + // try to detect KVM extensions + cap_tsc_deadline = kvm_ioctl(vmfd, KVM_CHECK_EXTENSION, KVM_CAP_TSC_DEADLINE_TIMER) <= 0 ? false : true; + cap_irqchip = kvm_ioctl(vmfd, KVM_CHECK_EXTENSION, KVM_CAP_IRQCHIP) <= 0 ? false : true; +#ifdef KVM_CLOCK_TSC_STABLE + cap_adjust_clock_stable = kvm_ioctl(vmfd, KVM_CHECK_EXTENSION, KVM_CAP_ADJUST_CLOCK) == KVM_CLOCK_TSC_STABLE ? true : false; +#endif + + if (restart) { + if (load_checkpoint(guest_mem, path) != 0) + exit(EXIT_FAILURE); + } else { + if (load_kernel(guest_mem, path) != 0) + exit(EXIT_FAILURE); + } + + pthread_barrier_init(&barrier, NULL, ncores); + cpuid = 0; + + // create first CPU, it will be the boot processor by default + return vcpu_init(); +} + +static void timer_handler(int signum) +{ + struct stat st = {0}; + const size_t flag = (!full_checkpoint && (no_checkpoint > 0)) ? PG_DIRTY : PG_ACCESSED; + char fname[MAX_FNAME]; + struct timeval begin, end; + + if (verbose) + gettimeofday(&begin, NULL); + + if (stat("checkpoint", &st) == -1) + mkdir("checkpoint", 0700); + + for(size_t i = 0; i < ncores; i++) + if (vcpu_threads[i] != pthread_self()) + pthread_kill(vcpu_threads[i], SIGRTMIN); + + pthread_barrier_wait(&barrier); + + save_cpu_state(); + + snprintf(fname, MAX_FNAME, "checkpoint/chk%u_mem.dat", no_checkpoint); + + FILE* f = fopen(fname, "w"); + if (f == NULL) { + err(1, "fopen: unable to open file"); + } + + /*struct kvm_irqchip irqchip = {}; + if (cap_irqchip) + kvm_ioctl(vmfd, KVM_GET_IRQCHIP, &irqchip); + else + memset(&irqchip, 0x00, sizeof(irqchip)); + if (fwrite(&irqchip, sizeof(irqchip), 1, f) != 1) + err(1, "fwrite failed");*/ + + struct kvm_clock_data clock = {}; + kvm_ioctl(vmfd, KVM_GET_CLOCK, &clock); + if (fwrite(&clock, sizeof(clock), 1, f) != 1) + err(1, "fwrite failed"); + +#if 0 + if (fwrite(guest_mem, guest_size, 1, f) != 1) + err(1, "fwrite failed"); +#elif defined(USE_DIRTY_LOG) + static struct kvm_dirty_log dlog = { + .slot = 0, + .dirty_bitmap = NULL + }; + size_t dirty_log_size = (guest_size >> PAGE_BITS) / sizeof(size_t); + + // do we create our first checkpoint + if (dlog.dirty_bitmap == NULL) + { + // besure that all paddings are zero + memset(&dlog, 0x00, sizeof(dlog)); + + dlog.dirty_bitmap = malloc(dirty_log_size * sizeof(size_t)); + if (dlog.dirty_bitmap == NULL) + err(1, "malloc failed!\n"); + } + memset(dlog.dirty_bitmap, 0x00, dirty_log_size * sizeof(size_t)); + + dlog.slot = 0; +nextslot: + kvm_ioctl(vmfd, KVM_GET_DIRTY_LOG, &dlog); + + for(size_t i=0; i KVM_32BIT_GAP_START - GUEST_OFFSET)) { + dlog.slot = 1; + memset(dlog.dirty_bitmap, 0x00, dirty_log_size * sizeof(size_t)); + goto nextslot; + } +#else + size_t* pml4 = (size_t*) (guest_mem+elf_entry+PAGE_SIZE); + for(size_t i=0; i<(1 << PAGE_MAP_BITS); i++) { + if ((pml4[i] & PG_PRESENT) != PG_PRESENT) + continue; + //printf("pml[%zd] 0x%zx\n", i, pml4[i]); + size_t* pdpt = (size_t*) (guest_mem+(pml4[i] & PAGE_MASK)); + for(size_t j=0; j<(1 << PAGE_MAP_BITS); j++) { + if ((pdpt[j] & PG_PRESENT) != PG_PRESENT) + continue; + //printf("\tpdpt[%zd] 0x%zx\n", j, pdpt[j]); + size_t* pgd = (size_t*) (guest_mem+(pdpt[j] & PAGE_MASK)); + for(size_t k=0; k<(1 << PAGE_MAP_BITS); k++) { + if ((pgd[k] & PG_PRESENT) != PG_PRESENT) + continue; + //printf("\t\tpgd[%zd] 0x%zx\n", k, pgd[k] & ~PG_XD); + if ((pgd[k] & PG_PSE) != PG_PSE) { + size_t* pgt = (size_t*) (guest_mem+(pgd[k] & PAGE_MASK)); + for(size_t l=0; l<(1 << PAGE_MAP_BITS); l++) { + if ((pgt[l] & (PG_PRESENT|flag)) == (PG_PRESENT|flag)) { + //printf("\t\t\t*pgt[%zd] 0x%zx, 4KB\n", l, pgt[l] & ~PG_XD); + if (!full_checkpoint) + pgt[l] = pgt[l] & ~(PG_DIRTY|PG_ACCESSED); + size_t pgt_entry = pgt[l] & ~PG_PSE; // because PAT use the same bit as PSE + if (fwrite(&pgt_entry, sizeof(size_t), 1, f) != 1) + err(1, "fwrite failed"); + if (fwrite((size_t*) (guest_mem + (pgt[l] & PAGE_MASK)), (1UL << PAGE_BITS), 1, f) != 1) + err(1, "fwrite failed"); + } + } + } else if ((pgd[k] & flag) == flag) { + //printf("\t\t*pgd[%zd] 0x%zx, 2MB\n", k, pgd[k] & ~PG_XD); + if (!full_checkpoint) + pgd[k] = pgd[k] & ~(PG_DIRTY|PG_ACCESSED); + if (fwrite(pgd+k, sizeof(size_t), 1, f) != 1) + err(1, "fwrite failed"); + if (fwrite((size_t*) (guest_mem + (pgd[k] & PAGE_2M_MASK)), (1UL << PAGE_2M_BITS), 1, f) != 1) + err(1, "fwrite failed"); + } + } + } + } +#endif + + fclose(f); + + pthread_barrier_wait(&barrier); + + // update configuration file + f = fopen("checkpoint/chk_config.txt", "w"); + if (f == NULL) { + err(1, "fopen: unable to open file"); + } + + fprintf(f, "number of cores: %u\n", ncores); + fprintf(f, "memory size: 0x%zx\n", guest_size); + fprintf(f, "checkpoint number: %u\n", no_checkpoint); + fprintf(f, "entry point: 0x%zx", elf_entry); + if (full_checkpoint) + fprintf(f, "full checkpoint: 1"); + else + fprintf(f, "full checkpoint: 0"); + + fclose(f); + + if (verbose) { + gettimeofday(&end, NULL); + size_t msec = (end.tv_sec - begin.tv_sec) * 1000; + msec += (end.tv_usec - begin.tv_usec) / 1000; + fprintf(stderr, "Create checkpoint %u in %zd ms\n", no_checkpoint, msec); + } + + no_checkpoint++; +} + +int uhyve_loop(void) +{ + const char* hermit_check = getenv("HERMIT_CHECKPOINT"); + int ts = 0; + + if (hermit_check) + ts = atoi(hermit_check); + + *((uint32_t*) (mboot+0x24)) = ncores; + + // First CPU is special because it will boot the system. Other CPUs will + // be booted linearily after the first one. + vcpu_threads[0] = pthread_self(); + + // start threads to create VCPUs + for(size_t i = 1; i < ncores; i++) + pthread_create(&vcpu_threads[i], NULL, uhyve_thread, (void*) i); + + if (ts > 0) + { + struct sigaction sa; + struct itimerval timer; + + /* Install timer_handler as the signal handler for SIGVTALRM. */ + memset(&sa, 0x00, sizeof(sa)); + sa.sa_handler = &timer_handler; + sigaction(SIGALRM, &sa, NULL); + + /* Configure the timer to expire after "ts" sec... */ + timer.it_value.tv_sec = ts; + timer.it_value.tv_usec = 0; + /* ... and every "ts" sec after that. */ + timer.it_interval.tv_sec = ts; + timer.it_interval.tv_usec = 0; + /* Start a virtual timer. It counts down whenever this process is executing. */ + setitimer(ITIMER_REAL, &timer, NULL); + } + + // Run first CPU + return vcpu_loop(); +} diff --git a/usr/Makefile b/usr/Makefile deleted file mode 100644 index 0d6f6b564..000000000 --- a/usr/Makefile +++ /dev/null @@ -1,117 +0,0 @@ -override TOPDIR = $(shell pwd) -ARCH = x86 -TARGET=x86_64-hermit -NJOBS=-j$(shell nproc) -#OMPRT=libgomp -OMPRT=libomp - -CROSSCOMPREFIX = x86_64-hermit -PREFIX = /opt/hermit -RM = rm -rf -CD = cd -CP = cp -MKDIR = mkdir -p -TMP = $(TOPDIR)/tmp -OPT = --disable-shared --disable-multilib --enable-lto --enable-newlib-hw-fp --enable-newlib-io-c99-formats --enable-newlib-multithread #--enable-newlib-reent-small -CLONE_DEPTH = --depth=50 -#CLONE_DEPTH = - -# Prettify output -V = 0 -ifeq ($V,0) - Q = @ - P = > /dev/null -endif - -default: - @echo Do not use default rule! - -examples: - @echo Build demo applications - $Q$(MAKE) ELFEDIT_FOR_TARGET=$(ELFEDIT_FOR_TARGET) CC_FOR_TARGET=$(CC_FOR_TARGET) CXX_FOR_TARGET=$(CXX_FOR_TARGET) CXXFLAGS_FOR_TARGET="$(CXXFLAGS_FOR_TARGET)" CFLAGS_FOR_TARGET="$(CFLAGS_FOR_TARGET) $(PROFILING_CFLAGS)" LDFLAGS_FOR_TARGET="$(LDFLAGS_FOR_TARGET) $(PROFILING_LDFLAGS)" OBJCOPY_FOR_TARGET=$(OBJCOPY_FOR_TARGET) GO_FOR_TARGET="$(GO_FOR_TARGET)" GOFLAGS_FOR_TARGET="$(GOFLAGS_FOR_TARGET)" -C tests depend - $Q$(MAKE) ELFEDIT_FOR_TARGET=$(ELFEDIT_FOR_TARGET) CC_FOR_TARGET=$(CC_FOR_TARGET) CXX_FOR_TARGET=$(CXX_FOR_TARGET) CXXFLAGS_FOR_TARGET="$(CXXFLAGS_FOR_TARGET)" CFLAGS_FOR_TARGET="$(CFLAGS_FOR_TARGET) $(PROFILING_CFLAGS)" LDFLAGS_FOR_TARGET="$(LDFLAGS_FOR_TARGET) $(PROFILING_LDFLAGS)" OBJCOPY_FOR_TARGET=$(OBJCOPY_FOR_TARGET) GO_FOR_TARGET="$(GO_FOR_TARGET)" GOFLAGS_FOR_TARGET="$(GOFLAGS_FOR_TARGET)" -C tests - $Q$(MAKE) ELFEDIT_FOR_TARGET=$(ELFEDIT_FOR_TARGET) CC_FOR_TARGET=$(CC_FOR_TARGET) CXX_FOR_TARGET=$(CXX_FOR_TARGET) CXXFLAGS_FOR_TARGET="$(CXXFLAGS_FOR_TARGET)" CFLAGS_FOR_TARGET="$(CFLAGS_FOR_TARGET) $(PROFILING_CFLAGS)" LDFLAGS_FOR_TARGET="$(LDFLAGS_FOR_TARGET) $(PROFILING_LDFLAGS)" OBJCOPY_FOR_TARGET=$(OBJCOPY_FOR_TARGET) -C benchmarks depend - $Q$(MAKE) ELFEDIT_FOR_TARGET=$(ELFEDIT_FOR_TARGET) CC_FOR_TARGET=$(CC_FOR_TARGET) CXX_FOR_TARGET=$(CXX_FOR_TARGET) CXXFLAGS_FOR_TARGET="$(CXXFLAGS_FOR_TARGET)" CFLAGS_FOR_TARGET="$(CFLAGS_FOR_TARGET) $(PROFILING_CFLAGS)" LDFLAGS_FOR_TARGET="$(LDFLAGS_FOR_TARGET) $(PROFILING_LDFLAGS)" OBJCOPY_FOR_TARGET=$(OBJCOPY_FOR_TARGET) -C benchmarks - #$Q$(MAKE) ELFEDIT_FOR_TARGET=$(ELFEDIT_FOR_TARGET) CC_FOR_TARGET=$(CC_FOR_TARGET) CXX_FOR_TARGET=$(CXX_FOR_TARGET) CXXFLAGS_FOR_TARGET="$(CXXFLAGS_FOR_TARGET)" CFLAGS_FOR_TARGET="$(CFLAGS_FOR_TARGET)" LDFLAGS_FOR_TARGET="$(LDFLAGS_FOR_TARGET)" OBJCOPY_FOR_TARGET=$(OBJCOPY_FOR_TARGET) -C openmpbench depend - $Q$(MAKE) ELFEDIT_FOR_TARGET=$(ELFEDIT_FOR_TARGET) CC_FOR_TARGET=$(CC_FOR_TARGET) CXX_FOR_TARGET=$(CXX_FOR_TARGET) CXXFLAGS_FOR_TARGET="$(CXXFLAGS_FOR_TARGET)" CFLAGS_FOR_TARGET="$(CFLAGS_FOR_TARGET) $(PROFILING_CFLAGS)" LDFLAGS_FOR_TARGET="$(LDFLAGS_FOR_TARGET) $(PROFILING_LDFLAGS)" OBJCOPY_FOR_TARGET=$(OBJCOPY_FOR_TARGET) -C openmpbench - -bootstrap: binutils gcc newlib pte $(TMP)/binutils $(TMP)/bootstrap - -binutils: - git clone $(CLONE_DEPTH) https://github.com/RWTH-OS/binutils.git - -gcc: - git clone $(CLONE_DEPTH) https://github.com/RWTH-OS/gcc.git - -pte: - git clone $(CLONE_DEPTH) https://github.com/RWTH-OS/pthread-embedded.git pte - $Q$(CD) pte; ./configure --prefix=$(PREFIX) - -newlib: - git clone $(CLONE_DEPTH) https://github.com/RWTH-OS/newlib.git - -$(TMP)/binutils: - @echo Build binutils - $Q$(MKDIR) $(TMP)/binutils - $Q$(CD) $(TMP)/binutils; $(TOPDIR)/binutils/configure --target=$(TARGET) --prefix=$(PREFIX) --with-sysroot --disable-multilib --disable-shared --disable-nls --disable-gdb --disable-libdecnumber --disable-readline --disable-sim --disable-libssp --enable-tls && $(MAKE) $(NJOBS) && $(MAKE) install - - -$(TMP)/bootstrap: - @echo Build bootstrap compiler - $Q$(MKDIR) $(TMP)/bootstrap - $Q$(CD) $(TMP)/bootstrap; $(TOPDIR)/gcc/configure --target=$(TARGET) --prefix=$(PREFIX) --without-headers --disable-multilib --with-isl --with-tune=generic --enable-languages=c,lto --disable-nls --disable-shared --disable-libssp --disable-libgomp --enable-threads=posix --enable-tls --enable-lto --disable-symvers && $(MAKE) $(NJOBS) all-gcc && $(MAKE) install-gcc - -toolchain: $(TMP)/newlib libpthread $(TMP)/gcc libs - -$(TMP)/newlib: - @echo Build newlib - $Q$(MKDIR) $(TMP)/newlib - $Q$(CD) $(TMP)/newlib; $(TOPDIR)/newlib/configure --target=$(TARGET) --prefix=$(PREFIX) $(OPT) && $(MAKE) $(NJOBS) && $(MAKE) install - -libpthread: - @echo Build libpthread - $Q$(MAKE) TARGET=$(TARGET) CC_FOR_TARGET=$(CC_FOR_TARGET) AR_FOR_TARGET=$(AR_FOR_TARGET) CFLAGS_FOR_TARGET+="-I. -Iplatform/hermit -Iplatform/helper -Wall $(PROFILING_CFLAGS)" -C pte depend - $Q$(MAKE) TARGET=$(TARGET) CC_FOR_TARGET=$(CC_FOR_TARGET) AR_FOR_TARGET=$(AR_FOR_TARGET) CFLAGS_FOR_TARGET+="-I. -Iplatform/hermit -Iplatform/helper -Wall $(PROFILING_CFLAGS)" -C pte - $Q$(MAKE) TARGET=$(TARGET) CC_FOR_TARGET=$(CC_FOR_TARGET) AR_FOR_TARGET=$(AR_FOR_TARGET) CFLAGS_FOR_TARGET+="-I. -Iplatform/hermit -Iplatform/helper -Wall $(PROFILING_CFLAGS)" -C pte install - $Q$(MAKE) TARGET=$(TARGET) CC_FOR_TARGET=$(CC_FOR_TARGET) AR_FOR_TARGET=$(AR_FOR_TARGET) CFLAGS_FOR_TARGET+="-I. -Iplatform/hermit -Iplatform/helper -Wall $(PROFILING_CFLAGS)" -C pte headers - -libs: - @echo Build Xray profiler - $Q$(MAKE) TARGET=$(TARGET) CC_FOR_TARGET=$(CC_FOR_TARGET) CFLAGS_FOR_TARGET="$(CFLAGS_FOR_TARGET)" LDFLAGS_FOR_TARGET="$(LDFLAGS_FOR_TARGET)" PREFIX=$(PREFIX) -C xray - @echo Build OpenMP Runtime and iRCCE - $Q$(MAKE) TARGET=$(TARGET) CXX_FOR_TARGET=$(CXX_FOR_TARGET) CXXFLAGS_FOR_TARGET="$(CXXFLAGS_FOR_TARGET)" CC_FOR_TARGET=$(CC_FOR_TARGET) AR_FOR_TARGET=$(AR_FOR_TARGET) CFLAGS_FOR_TARGET+="-I. -Wall -pthread $(PROFILING_CFLAGS)" PREFIX=$(PREFIX) -C $(OMPRT) depend - $Q$(MAKE) TARGET=$(TARGET) CXX_FOR_TARGET=$(CXX_FOR_TARGET) CXXFLAGS_FOR_TARGET="$(CXXFLAGS_FOR_TARGET)" CC_FOR_TARGET=$(CC_FOR_TARGET) AR_FOR_TARGET=$(AR_FOR_TARGET) CFLAGS_FOR_TARGET+="-I. -Wall -pthread $(PROFILING_CFLAGS)" PREFIX=$(PREFIX) -C $(OMPRT) - $Q$(MAKE) TARGET=$(TARGET) CC_FOR_TARGET=$(CC_FOR_TARGET) AR_FOR_TARGET=$(AR_FOR_TARGET) CFLAGS_FOR_TARGET+="-I. -Wall" PREFIX=$(PREFIX) -C ircce depend - $Q$(MAKE) TARGET=$(TARGET) CC_FOR_TARGET=$(CC_FOR_TARGET) AR_FOR_TARGET=$(AR_FOR_TARGET) CFLAGS_FOR_TARGET+="-I. -Wall" PREFIX=$(PREFIX) -C ircce - -install: - $Q$(MAKE) PREFIX=$(PREFIX) -C xray install - $Q$(MAKE) PREFIX=$(PREFIX) -C ircce install - $Q$(MAKE) PREFIX=$(PREFIX) -C $(OMPRT) install - -$(TMP)/gcc: - @echo Build final gcc - $Q$(RM) $(TMP)/gcc - $Q$(MKDIR) $(TMP)/gcc - $Q$(CD) $(TMP)/gcc; $(TOPDIR)/gcc/configure --target=$(TARGET) --prefix=$(PREFIX) --with-newlib --with-isl --disable-multilib --without-libatomic --with-tune=generic --enable-languages=c,c++,go,fortran,lto --disable-nls --disable-shared --disable-libssp --enable-threads=posix --disable-libgomp --enable-tls --enable-lto --disable-symvers && $(MAKE) $(NJOBS) && $(MAKE) install - -clean: - @echo Cleaning toolchain - $Q$(MAKE) -C $(OMPRT) clean - $Q$(MAKE) -C ircce clean - $Q$(MAKE) -C tests clean - $Q$(MAKE) -C benchmarks clean - $Q$(MAKE) -C openmpbench clean - $Q$(MAKE) -C xray clean - -veryclean: - @echo Propper cleaning of the toolchain - $Q$(MAKE) -C $(OMPRT) veryclean - $Q$(MAKE) -C ircce veryclean - $Q$(MAKE) -C tests veryclean - $Q$(MAKE) -C benchmarks veryclean - $Q$(MAKE) -C openmpbench veryclean - $Q$(RM) binutils gcc newlib pte - $Q$(RM) $(TMP) - -.PHONY: default all clean veryclean headers libpthread libs diff --git a/usr/benchmarks/CMakeLists.txt b/usr/benchmarks/CMakeLists.txt new file mode 100644 index 000000000..9aae06bcb --- /dev/null +++ b/usr/benchmarks/CMakeLists.txt @@ -0,0 +1,21 @@ +cmake_minimum_required(VERSION 3.7) +include(../../cmake/HermitCore-Application.cmake) + +project(hermit_benchmarks C) + +add_executable(basic basic.c) +target_link_libraries(basic pthread) + +add_executable(hg hg.c hist.c rdtsc.c run.c init.c opt.c report.c setup.c) + +add_executable(netio netio.c) + +add_executable(RCCE_pingpong RCCE_pingpong.c) +target_link_libraries(RCCE_pingpong ircce) + +add_executable(stream stream.c) +target_compile_options(stream PRIVATE -fopenmp) +target_link_libraries(stream -fopenmp) + +# deployment +install_local_targets(extra/benchmarks) diff --git a/usr/benchmarks/Makefile b/usr/benchmarks/Makefile deleted file mode 100644 index 0006125fe..000000000 --- a/usr/benchmarks/Makefile +++ /dev/null @@ -1,126 +0,0 @@ -ARCH = x86 -TARGET=x86_64-hermit -MAKE = make -override STRIP_DEBUG = --strip-debug #--strip-unneeded -KEEP_DEBUG = --only-keep-debug - -# Set your own cross compiler tool chain prefix here -CROSSCOMPREFIX = x86_64-hermit- - -CC_FOR_TARGET = $(CROSSCOMPREFIX)gcc -CXX_FOR_TARGET = $(CROSSCOMPREFIX)g++ -GCC_FOR_TARGET = $(CROSSCOMPREFIX)gcc -CPP_FOR_TARGET = $(CROSSCOMPREFIX)cpp -AR_FOR_TARGET = $(CROSSCOMPREFIX)ar -AS_FOR_TARGET = $(CROSSCOMPREFIX)as -LD_FOR_TARGET = $(CROSSCOMPREFIX)ld -NM_FOR_TARGET = $(CROSSCOMPREFIX)nm -OBJDUMP_FOR_TARGET = $(CROSSCOMPREFIX)objdump -OBJCOPY_FOR_TARGET = $(CROSSCOMPREFIX)objcopy -RANLIB_FOR_TARGET = $(CROSSCOMPREFIX)ranlib -STRIP_FOR_TARGET = $(CROSSCOMPREFIX)strip -READELF_FOR_TARGET = $(CROSSCOMPREFIX)readelf -ELFEDIT_FOR_TARGET = $(CROSSCOMPREFIX)elfedit - -# Prettify output -V = 0 -ifeq ($V,0) - Q = @ - P = > /dev/null -endif - -ICC_EXE = -#ICC_EXE = stream_icc - -# other implicit rules -%.o : %.c - @echo [CC] $@ - $Q$(CC_FOR_TARGET) -c $(CFLAGS_FOR_TARGET) -o $@ $< - -%.o: %.cpp - @echo [CXX] $@ - $Q$(CXX_FOR_TARGET) -c $(CXXFLAGS_FOR_TARGET) $(CFLAGS_FOR_TARGET) -o $@ $< - -%.o: %.f90 - @echo [F90] $@ - $Q$(FC_FOR_TARGET) -c $(FFLAGS_FOR_TARGET) -o $@ $< - -default: all - -all: stream hg netio RCCE_pingping RCCE_pingpong basic $(ICC_EXE) - -stream.o: stream.c - @echo [CC] $@ - $Q$(CC_FOR_TARGET) -c $(CFLAGS_FOR_TARGET) -fopenmp -o $@ $< - -stream: stream.o - @echo [LD] $@ - $Q$(CC_FOR_TARGET) -o $@ $< $(LDFLAGS_FOR_TARGET) $(CFLAGS_FOR_TARGET) -fopenmp - $Q$(OBJCOPY_FOR_TARGET) $(KEEP_DEBUG) $@ $@.sym - $Q$(OBJCOPY_FOR_TARGET) $(STRIP_DEBUG) $@ - $Qchmod a-x $@.sym - -stream_icc.o: stream.c - @echo [ICC] $@ - icc -m64 -c -o $@ -O3 -xHost -I$(TOPDIR)/hermit/usr/x86/x86_64-hermit/include/ -openmp -ffreestanding $< - $Q$(ELFEDIT_FOR_TARGET) --output-osabi HermitCore $@ - -stream_icc: stream_icc.o - @echo [LD] - $Q$(CC_FOR_TARGET) -o $@ $< $(LDFLAGS_FOR_TARGET) $(CFLAGS_FOR_TARGET) -fopenmp - $Q$(OBJCOPY_FOR_TARGET) $(KEEP_DEBUG) $@ $@.sym - $Q$(OBJCOPY_FOR_TARGET) $(STRIP_DEBUG) $@ - $Qchmod a-x $@.sym - -basic.o: basic.c - @echo [CC] $@ - $Q$(CC_FOR_TARGET) -c $(CFLAGS_FOR_TARGET) -pthread -o $@ $< - -basic: basic.o - @echo [LD] $@ - $Q$(CC_FOR_TARGET) -o $@ $< $(LDFLAGS_FOR_TARGET) $(CFLAGS_FOR_TARGET) -pthread - $Q$(OBJCOPY_FOR_TARGET) $(KEEP_DEBUG) $@ $@.sym - $Q$(OBJCOPY_FOR_TARGET) $(STRIP_DEBUG) $@ - $Qchmod a-x $@.sym - -RCCE_pingping: RCCE_pingping.o - @echo [LD] $@ - $Q$(CC_FOR_TARGET) -o $@ $< $(LDFLAGS_FOR_TARGET) $(CFLAGS_FOR_TARGET) -lircce - $Q$(OBJCOPY_FOR_TARGET) $(KEEP_DEBUG) $@ $@.sym - $Q$(OBJCOPY_FOR_TARGET) $(STRIP_DEBUG) $@ - $Qchmod a-x $@.sym - -RCCE_pingpong: RCCE_pingpong.o - @echo [LD] $@ - $Q$(CC_FOR_TARGET) -o $@ $< $(LDFLAGS_FOR_TARGET) $(CFLAGS_FOR_TARGET) -lircce - $Q$(OBJCOPY_FOR_TARGET) $(KEEP_DEBUG) $@ $@.sym - $Q$(OBJCOPY_FOR_TARGET) $(STRIP_DEBUG) $@ - $Qchmod a-x $@.sym - -netio: netio.o - @echo [LD] $@ - $Q$(CC_FOR_TARGET) -o $@ $< $(LDFLAGS_FOR_TARGET) $(CFLAGS_FOR_TARGET) - $Q$(OBJCOPY_FOR_TARGET) $(KEEP_DEBUG) $@ $@.sym - $Q$(OBJCOPY_FOR_TARGET) $(STRIP_DEBUG) $@ - $Qchmod a-x $@.sym - -hg: hg.o hist.o rdtsc.o run.o init.o opt.o report.o setup.o - @echo [LD] $@ - $Q$(CC_FOR_TARGET) -o $@ $< $(LDFLAGS_FOR_TARGET) $(CFLAGS_FOR_TARGET) hist.o rdtsc.o run.o init.o opt.o report.o setup.o - $Q$(OBJCOPY_FOR_TARGET) $(KEEP_DEBUG) $@ $@.sym - $Q$(OBJCOPY_FOR_TARGET) $(STRIP_DEBUG) $@ - $Qchmod a-x $@.sym - -clean: - @echo Cleaning benchmarks - $Q$(RM) stream hg netio RCCE_pingping RCCE_pingpong *.sym *.o *~ - -veryclean: - @echo Propper cleaning benchmarks - $Q$(RM) stream hg RCCE_pingping RCCE_pingpong *.sym *.o *~ - -depend: - $Q$(CC_FOR_TARGET) -MM $(CFLAGS_FOR_TARGET) *.c > Makefile.dep - --include Makefile.dep -# DO NOT DELETE diff --git a/usr/ircce/CMakeLists.txt b/usr/ircce/CMakeLists.txt new file mode 100644 index 000000000..95999a085 --- /dev/null +++ b/usr/ircce/CMakeLists.txt @@ -0,0 +1,18 @@ +cmake_minimum_required(VERSION 3.7) +include(../../cmake/HermitCore.cmake) + +project(hermit_ircce C) + +add_compile_options(${HERMIT_APP_FLAGS}) + +file(GLOB SOURCES *.c) + +add_library(ircce STATIC ${SOURCES}) + +# deployment +install(TARGETS ircce + DESTINATION ${TARGET_ARCH}/lib) +install(FILES + iRCCE.h iRCCE_lib.h RCCE_debug.h RCCE.h RCCE_lib.h rte_memcpy.h + DESTINATION + ${TARGET_ARCH}/include) diff --git a/usr/ircce/Makefile.in b/usr/ircce/Makefile.in deleted file mode 100644 index 321433e84..000000000 --- a/usr/ircce/Makefile.in +++ /dev/null @@ -1,56 +0,0 @@ -CROSSPREFIX = x86_64-hermit -MAKE = make -ARFLAGS_FOR_TARGET = rsv -CP = cp -C_source = $(wildcard *.c) -NAME = libircce.a -OBJS = $(C_source:.c=.o) - -prefix = @prefix@ -INSTALL = @INSTALL@ -INSTALL_PROGRAM = @INSTALL_PROGRAM@ -INSTALL_SCRIPT = @INSTALL_SCRIPT@ -INSTALL_DATA = @INSTALL_DATA@ - -# -# Prettify output -V = 0 -ifeq ($V,0) - Q = @ - P = > /dev/null -endif - -# other implicit rules -%.o : %.c - @echo [CC] $@ - $Q$(CC_FOR_TARGET) -c $(CFLAGS_FOR_TARGET) -o $@ $< - -default: all - -all: $(NAME) - -$(NAME): $(OBJS) - $Q$(AR_FOR_TARGET) $(ARFLAGS_FOR_TARGET) $@ $(OBJS) - -install: - $Q$(INSTALL_DATA) $(NAME) $(prefix)/$(CROSSPREFIX)/lib - $Q$(INSTALL_DATA) iRCCE.h $(prefix)/$(CROSSPREFIX)/include - $Q$(INSTALL_DATA) iRCCE_lib.h $(prefix)/$(CROSSPREFIX)/include - $Q$(INSTALL_DATA) RCCE_debug.h $(prefix)/$(CROSSPREFIX)/include - $Q$(INSTALL_DATA) RCCE.h $(prefix)/$(CROSSPREFIX)/include - $Q$(INSTALL_DATA) RCCE_lib.h $(prefix)/$(CROSSPREFIX)/include - $Q$(INSTALL_DATA) rte_memcpy.h $(prefix)/$(CROSSPREFIX)/include - -clean: - @echo Cleaning examples - $Q$(RM) $(NAME) *.o *~ - -veryclean: - @echo Propper cleaning examples - $Q$(RM) $(NAME) *.o *~ - -depend: - $Q$(CC_FOR_TARGET) -MM $(CFLAGS_FOR_TARGET) *.c > Makefile.dep - --include Makefile.dep -# DO NOT DELETE diff --git a/usr/libomp b/usr/libomp index 2046fa1ea..5ffb03a3d 160000 --- a/usr/libomp +++ b/usr/libomp @@ -1 +1 @@ -Subproject commit 2046fa1ea1587ba862e54e797433e1d726ab6ba8 +Subproject commit 5ffb03a3dca404d0988a9b026e77c7a642dc742b diff --git a/usr/openmpbench/CMakeLists.txt b/usr/openmpbench/CMakeLists.txt new file mode 100644 index 000000000..1aaa6c39e --- /dev/null +++ b/usr/openmpbench/CMakeLists.txt @@ -0,0 +1,21 @@ +cmake_minimum_required(VERSION 3.7) +include(../../cmake/HermitCore-Application.cmake) + +project(hermit_openmpbench C) + +add_executable(syncbench syncbench.c common.c) +target_link_libraries(syncbench PUBLIC -fopenmp) + +add_executable(taskbench taskbench.c common.c) +target_link_libraries(taskbench PUBLIC -fopenmp) + +add_library(common_sched STATIC common.c) +target_compile_definitions(common_sched PUBLIC -DSCHEDBENCH) +target_compile_options(common_sched PUBLIC -fopenmp) +target_link_libraries(common_sched PUBLIC -fopenmp) + +add_executable(schedbench schedbench.c) +target_link_libraries(schedbench common_sched) + +# deployment: exclude common_sched +install_local_targets(extra/benchmarks common_sched) diff --git a/usr/openmpbench/Makefile b/usr/openmpbench/Makefile deleted file mode 100644 index 937877e2f..000000000 --- a/usr/openmpbench/Makefile +++ /dev/null @@ -1,59 +0,0 @@ -include Makefile.defs - -# If CFLAGS_CRAY is empty set it to CFLAGS -ifeq ($(CFLAGS_CRAY),) -CFLAGS_CRAY = ${CFLAGS} -endif - -.c.o: - ${CC} ${CFLAGS} $(OMPFLAG) -c $*.c - -SYNCOBJS = syncbench.o common.o -SCHEDOBJS = schedbench.o common_sched.o -ARRAYOBJS = arraybench_$(IDA).o common.o -TASKOBJS = taskbench.o common.o -SCHEDFLAGS = -DSCHEDBENCH - -all: syncbench schedbench taskbench - -prog: arraybench_$(IDA) - -# We need to generate a linker map file so that Xray can resolve function names -LDFLAGS += -Wl,-Map=$@.map - -syncbench: $(SYNCOBJS) - $(CC) -o syncbench $(SYNCOBJS) $(LDFLAGS) $(CLOCKOBJS) $(LIBS) -lm - -# Rule to ensure the lower optimisation level is picked up for common.c -# with the Cray compiler -common.o: - ${CC} ${CFLAGS_CRAY} $(OMPFLAG) -c $*.c - -# Separate rule to build common_sched.o as we need to ensure the correct -# DEFAULT_DELAY_TIME is used. -common_sched.o: - ${CC} ${CFLAGS_CRAY} $(SCHEDFLAGS) $(OMPFLAG) -o common_sched.o -c common.c - -schedbench: $(SCHEDOBJS) - $(CC) -o schedbench $(SCHEDOBJS) $(LDFLAGS) $(CLOCKOBJS) $(LIBS) -lm - -# Multiple header files due to multiple array sizes, makes header file arraybench_*.h -arraybench_$(IDA).h: arraybench.h - $(CPP) -DIDA=$(IDA) $(OMPFLAG) -P arraybench.h -o $@ - -# Multiple object files due to multiple array sizes, makes object file arraybench_*.o -arraybench_$(IDA).o: arraybench_$(IDA).h arraybench.c - $(CC) $(CFLAGS) -DIDA=$(IDA) $(OMPFLAG) arraybench.c -c -o $@ - -# Multiple executables due to multiple array sizes, makes exe file arraybench_* -arraybench_$(IDA): $(ARRAYOBJS) $(CLOCKOBJS) arraybench.c - $(CC) -o $@ $(LDFLAGS) $(ARRAYOBJS) $(CLOCKOBJS) $(LIBS) -lm - -taskbench: $(TASKOBJS) - $(CC) -o taskbench $(TASKOBJS) $(LDFLAGS) $(OMPFLAG) $(CLOCKOBJS) $(LIBS) -lm - -clean: - -rm -rf *.o *.xray *.map syncbench schedbench arraybench_* taskbench - -veryclean: clean - -rm -rf OpenMPBench.* *.all diff --git a/usr/openmpbench/Makefile.defs b/usr/openmpbench/Makefile.defs deleted file mode 100644 index e8369b7c6..000000000 --- a/usr/openmpbench/Makefile.defs +++ /dev/null @@ -1,14 +0,0 @@ -# Uncomment the following line to use OpenMP 2.0 features -OMPFLAG = -DOMPVER2 -# Uncomment the following line to use OpenMP 3.0 features -#OMPFLAG = -DOMPVER2 -DOMPVER3 - -CC = $(CC_FOR_TARGET) -CFLAGS = -fopenmp $(CFLAGS_FOR_TARGET) -lm -LDFLAGS = -fopenmp $(LDFLAGS_FOR_TARGET) -lm -CPP = $(CPP_FOR_TARGET) -ELFEDIT = $(ELFEDIT_FOR_TARGET) -LIBS = - -override STRIP_DEBUG = --strip-debug #--strip-unneeded -KEEP_DEBUG = --only-keep-debug diff --git a/usr/openmpbench/Makefile.defs.hector.cray b/usr/openmpbench/Makefile.defs.hector.cray deleted file mode 100644 index a9c33a592..000000000 --- a/usr/openmpbench/Makefile.defs.hector.cray +++ /dev/null @@ -1,10 +0,0 @@ -# Uncomment the following line to use OpenMP 2.0 features -#OMPFLAG = -DOMPVER2 -# Uncomment the following line to use OpenMP 3.0 features -OMPFLAG = -DOMPVER2 -DOMPVER3 - -CC=cc -CFLAGS = -O1 -lm -LDFLAGS = -O0 -lm -CPP = /usr/bin/cpp -LIBS = diff --git a/usr/openmpbench/Makefile.defs.hector.pgi b/usr/openmpbench/Makefile.defs.hector.pgi deleted file mode 100644 index 346222856..000000000 --- a/usr/openmpbench/Makefile.defs.hector.pgi +++ /dev/null @@ -1,12 +0,0 @@ -# Uncomment the following line to use OpenMP 2.0 features -#OMPFLAG = -DOMPVER2 -# Uncomment the following line to use OpenMP 3.0 features -# Nested tasks don't work on HECToR Phase 3 for the PGI compiler -# and thus are disabled. -OMPFLAG = -DOMPVER2 -DOMPVER3 -DDISABLE_NESTED_TASKS_TESTS - -CC =cc -CFLAGS = -fast -mp=nonuma -lm -LDFLAGS = -fast -mp=nonuma -lm -CPP = /usr/bin/cpp -LIBS = \ No newline at end of file diff --git a/usr/openmpbench/Makefile.defs.magny0.gnu b/usr/openmpbench/Makefile.defs.magny0.gnu deleted file mode 100644 index d9f5c36b1..000000000 --- a/usr/openmpbench/Makefile.defs.magny0.gnu +++ /dev/null @@ -1,10 +0,0 @@ -# Uncomment the following line to use OpenMP 2.0 features -#OMPFLAG = -DOMPVER2 -# Uncomment the following line to use OpenMP 3.0 features -OMPFLAG = -DDISABLE_BARRIER_TEST -DOMPVER2 -DOMPVER3 - -CC = /usr/local/bin/gcc-4.6 -CFLAGS = -fopenmp -O1 -lm -LDFLAGS = -fopenmp -O1 -lm -CPP = /usr/bin/cpp -LIBS = \ No newline at end of file diff --git a/usr/openmpbench/Makefile.defs.magny0.sun b/usr/openmpbench/Makefile.defs.magny0.sun deleted file mode 100644 index 62cbbee68..000000000 --- a/usr/openmpbench/Makefile.defs.magny0.sun +++ /dev/null @@ -1,10 +0,0 @@ -# Uncomment the following line to use OpenMP 2.0 features -#OMPFLAG = -DOMPVER2 -# Uncomment the following line to use OpenMP 3.0 features -OMPFLAG = -DOMPVER2 -DOMPVER3 - -CC = /home/h012/fiona/SolarisStudio12.2-linux-x86-tar-ML/solstudio12.2/bin/suncc -CFLAGS = -xopenmp -xO3 -lm -LDFLAGS = -xopenmp -xO3 -lm -CPP = /usr/bin/cpp -LIBS = diff --git a/usr/openmpbench/Makefile.defs.stokes.gnu b/usr/openmpbench/Makefile.defs.stokes.gnu deleted file mode 100644 index 8b9f0acd1..000000000 --- a/usr/openmpbench/Makefile.defs.stokes.gnu +++ /dev/null @@ -1,10 +0,0 @@ -# Uncomment the following line to use OpenMP 2.0 features -#OMPFLAG = -DOMPVER2 -# Uncomment the following line to use OpenMP 3.0 features -OMPFLAG = -DDISABLE_BARRIER_TEST -DOMPVER2 -DOMPVER3 - -CC = gcc -CFLAGS = -fopenmp -O1 -lm -LDFLAGS = -fopenmp -O1 -lm -CPP = /usr/bin/cpp -LIBS = \ No newline at end of file diff --git a/usr/openmpbench/Makefile.defs.stokes.intel b/usr/openmpbench/Makefile.defs.stokes.intel deleted file mode 100644 index 4d26495b4..000000000 --- a/usr/openmpbench/Makefile.defs.stokes.intel +++ /dev/null @@ -1,10 +0,0 @@ -# Uncomment the following line to use OpenMP 2.0 features -#OMPFLAG = -DOMPVER2 -# Uncomment the following line to use OpenMP 3.0 features -OMPFLAG = -DDISABLE_BARRIER_TEST -DOMPVER2 -DOMPVER3 - -CC = icc -CFLAGS = -openmp -O1 -lm -LDFLAGS = -openmp -O1 -lm -CPP = /usr/bin/cpp -LIBS = \ No newline at end of file diff --git a/usr/openmpbench/syncbench.c b/usr/openmpbench/syncbench.c index b3f87e093..23fe78610 100644 --- a/usr/openmpbench/syncbench.c +++ b/usr/openmpbench/syncbench.c @@ -45,9 +45,9 @@ int main(int argc, char **argv) { struct XRayTraceCapture* trace = XRayInit( 20, // max. call depth - 32 * 1000 * 1000, // memory for report + 16 * 1000 * 1000, // memory for report 13, // frame count - "/hermit/usr/openmpbench/syncbench.map"); + "syncbench.map"); // Start Paraver tracing #ifdef PARAVERTRACE @@ -128,7 +128,7 @@ int main(int argc, char **argv) { #endif XRaySaveReport(trace, - "/hermit/usr/openmpbench/syncbench.xray", // report file + "syncbench.xray", // report file 0.05f, // Only output funcs that have higher runtime [%] 1000); // Only output funcs that have higher runtime [cycles] XRayShutdown(trace); diff --git a/usr/tests/CMakeLists.txt b/usr/tests/CMakeLists.txt new file mode 100644 index 000000000..e910a016c --- /dev/null +++ b/usr/tests/CMakeLists.txt @@ -0,0 +1,32 @@ +cmake_minimum_required(VERSION 3.7) +include(../../cmake/HermitCore-Application.cmake) + +project(hermit_tests C CXX Fortran Go) + +add_executable(hello hello.c) +add_executable(jacobi jacobi.c) +add_executable(hello++ hello++.cpp) +add_executable(hellof hellof.f90) +add_executable(pi pi.go) + +add_executable(test-malloc test-malloc.c) +add_executable(test-malloc-mt test-malloc-mt.c) +target_compile_options(test-malloc-mt PRIVATE -pthread) +target_link_libraries(test-malloc-mt pthread) + +add_executable(server server.go) +target_link_libraries(server netgo) + +add_executable(RCCE_minimum RCCE_minimum.c) +target_link_libraries(RCCE_minimum ircce) + +add_executable(thr_hello thr_hello.c) +target_compile_options(thr_hello PRIVATE -pthread) +target_link_libraries(thr_hello pthread) + +add_executable(signals signals.c) +target_compile_options(signals PRIVATE -pthread) +target_link_libraries(signals pthread) + +# deployment +install_local_targets(extra/tests) diff --git a/usr/tests/Makefile b/usr/tests/Makefile deleted file mode 100644 index 0c2d417eb..000000000 --- a/usr/tests/Makefile +++ /dev/null @@ -1,137 +0,0 @@ -ARCH = x86 -TARGET=x86_64-hermit -MAKE = make -override STRIP_DEBUG = --strip-debug #--strip-unneeded -KEEP_DEBUG = --only-keep-debug - -# Set your own cross compiler tool chain prefix here -CROSSCOMPREFIX = x86_64-hermit- - -CC_FOR_TARGET = $(CROSSCOMPREFIX)gcc -GO_FOR_TARGET = $(CROSSCOMPREFIX)gccgo -CXX_FOR_TARGET = $(CROSSCOMPREFIX)g++ -GCC_FOR_TARGET = $(CROSSCOMPREFIX)gcc -CPP_FOR_TARGET = $(CROSSCOMPREFIX)cpp -AR_FOR_TARGET = $(CROSSCOMPREFIX)ar -AS_FOR_TARGET = $(CROSSCOMPREFIX)as -LD_FOR_TARGET = $(CROSSCOMPREFIX)ld -NM_FOR_TARGET = $(CROSSCOMPREFIX)nm -OBJDUMP_FOR_TARGET = $(CROSSCOMPREFIX)objdump -OBJCOPY_FOR_TARGET = $(CROSSCOMPREFIX)objcopy -RANLIB_FOR_TARGET = $(CROSSCOMPREFIX)ranlib -STRIP_FOR_TARGET = $(CROSSCOMPREFIX)strip -READELF_FOR_TARGET = $(CROSSCOMPREFIX)readelf -ELFEDIT_FOR_TARGET = $(CROSSCOMPREFIX)elfedit - -# Prettify output -V = 0 -ifeq ($V,0) - Q = @ - P = > /dev/null -endif - -# other implicit rules -%.o : %.c - @echo [CC] $@ - $Q$(CC_FOR_TARGET) -c $(CFLAGS_FOR_TARGET) -o $@ $< - -%.o : %.go - @echo [GO] $@ - $Q$(GO_FOR_TARGET) -c $(GOFLAGS_FOR_TARGET) -o $@ $< - -%.o: %.cpp - @echo [CXX] $@ - $Q$(CXX_FOR_TARGET) -c $(CXXFLAGS_FOR_TARGET) -o $@ $< - -%.o: %.f90 - @echo [F90] $@ - $Q$(FC_FOR_TARGET) -c $(FCLAGS_FOR_TARGET) -o $@ $< - -default: all - -all: hello hello++ thr_hello jacobi hellof RCCE_minimum signals pi server - -hello++: hello++.o - @echo [LD] $@ - $Q$(CXX_FOR_TARGET) -o $@ $< $(LDFLAGS_FOR_TARGET) $(CXXFLAGS_FOR_TARGET) - $Q$(OBJCOPY_FOR_TARGET) $(KEEP_DEBUG) $@ $@.sym - $Q$(OBJCOPY_FOR_TARGET) $(STRIP_DEBUG) $@ - $Qchmod a-x $@.sym - -hello: hello.o - @echo [LD] $@ - $Q$(CC_FOR_TARGET) -o $@ $< $(LDFLAGS_FOR_TARGET) $(CFLAGS_FOR_TARGET) - $Q$(OBJCOPY_FOR_TARGET) $(KEEP_DEBUG) $@ $@.sym - $Q$(OBJCOPY_FOR_TARGET) $(STRIP_DEBUG) $@ - $Qchmod a-x $@.sym - -hellof: hellof.o - @echo [LD] $@ - $Q$(FC_FOR_TARGET) -o $@ $< $(LDFLAGS_FOR_TARGET) $(FFLAGS_FOR_TARGET) - $Q$(OBJCOPY_FOR_TARGET) $(KEEP_DEBUG) $@ $@.sym - $Q$(OBJCOPY_FOR_TARGET) $(STRIP_DEBUG) $@ - $Qchmod a-x $@.sym - -pi: pi.o - @echo [LD] $@ - $Q$(GO_FOR_TARGET) -pthread -o $@ $< $(LDFLAGS_FOR_TARGET) $(GOFLAGS_FOR_TARGET) - $Q$(OBJCOPY_FOR_TARGET) $(KEEP_DEBUG) $@ $@.sym - $Q$(OBJCOPY_FOR_TARGET) $(STRIP_DEBUG) $@ - $Qchmod a-x $@.sym - -server: server.o - @echo [LD] $@ - $Q$(GO_FOR_TARGET) -pthread -o $@ $< $(LDFLAGS_FOR_TARGET) $(GOFLAGS_FOR_TARGET) -lnetgo - $Q$(OBJCOPY_FOR_TARGET) $(KEEP_DEBUG) $@ $@.sym - $Q$(OBJCOPY_FOR_TARGET) $(STRIP_DEBUG) $@ - $Qchmod a-x $@.sym - -jacobi: jacobi.o - @echo [LD] $@ - $Q$(CC_FOR_TARGET) -o $@ $< $(LDFLAGS_FOR_TARGET) $(CFLAGS_FOR_TARGET) - $Q$(OBJCOPY_FOR_TARGET) $(KEEP_DEBUG) $@ $@.sym - $Q$(OBJCOPY_FOR_TARGET) $(STRIP_DEBUG) $@ - $Qchmod a-x $@.sym - -thr_hello.o: thr_hello.c - @echo [CC] $@ - $Q$(CC_FOR_TARGET) -c $(CFLAGS_FOR_TARGET) -pthread -o $@ $< - -thr_hello: thr_hello.o - @echo [LD] $@ - $Q$(CC_FOR_TARGET) -o $@ $< $(LDFLAGS_FOR_TARGET) $(CFLAGS_FOR_TARGET) -pthread - $Q$(OBJCOPY_FOR_TARGET) $(KEEP_DEBUG) $@ $@.sym - $Q$(OBJCOPY_FOR_TARGET) $(STRIP_DEBUG) $@ - $Qchmod a-x $@.sym - -signals.o: signals.c - @echo [CC] $@ - $Q$(CC_FOR_TARGET) -c $(CFLAGS_FOR_TARGET) -pthread -o $@ $< - -signals: signals.o - @echo [LD] $@ - $Q$(CC_FOR_TARGET) -o $@ $< $(LDFLAGS_FOR_TARGET) $(CFLAGS_FOR_TARGET) -pthread - $Q$(OBJCOPY_FOR_TARGET) $(KEEP_DEBUG) $@ $@.sym - $Q$(OBJCOPY_FOR_TARGET) $(STRIP_DEBUG) $@ - $Qchmod a-x $@.sym - -RCCE_minimum: RCCE_minimum.o - @echo [LD] $@ - $Q$(CC_FOR_TARGET) -o $@ $< $(LDFLAGS_FOR_TARGET) $(CFLAGS_FOR_TARGET) -lircce - $Q$(OBJCOPY_FOR_TARGET) $(KEEP_DEBUG) $@ $@.sym - $Q$(OBJCOPY_FOR_TARGET) $(STRIP_DEBUG) $@ - $Qchmod a-x $@.sym - -clean: - @echo Cleaning tests - $Q$(RM) hello hello++ hellof jacobi thr_hello RCCE_minimum signals pi server *.sym *.o *~ - -veryclean: - @echo Propper cleaning tests - $Q$(RM) hello hello++ hellof jacobi thr_hello RCCE_minimum pi server *.sym *.o *~ - -depend: - $Q$(CC_FOR_TARGET) -MM $(CFLAGS_FOR_TARGET) *.c > Makefile.dep - --include Makefile.dep -# DO NOT DELETE diff --git a/usr/tests/test-malloc-mt.c b/usr/tests/test-malloc-mt.c new file mode 100644 index 000000000..9e35d2de0 --- /dev/null +++ b/usr/tests/test-malloc-mt.c @@ -0,0 +1,67 @@ +#include +#include +#include +#include +#include +#include + +#ifndef NUM_THREADS +#define NUM_THREADS 3 +#endif + +#ifndef NUM_ITER +#define NUM_ITER 10000 +#endif + +#ifndef SIZE +#define SIZE 16384 +#endif + +__thread void* buf; + +static void* perform_work( void* argument ) +{ + int passed_in_value; + + passed_in_value = *( ( int* )argument ); + printf( "Hello World! It's me, thread %d with argument %d!\n", getpid(), passed_in_value ); + + /* optionally: insert more useful stuff here */ + for(int i=0; i +#include +#include +#include + +#ifndef NUM_ITER +#define NUM_ITER 100000 +#endif + +#ifndef SIZE +#define SIZE 16*1024 +#endif + +void* buf; + +int main(int argc, char** argv) +{ + /* optionally: insert more useful stuff here */ + + for(int i=0; i`. + +Then you must initialize XRay and already do some configuration: + +```c +struct XRayTraceCapture* XRayInit(int stack_size, + int buffer_size, + int frame_count, + const char* mapfilename); + +struct XRayTraceCapture* trace = XRayInit( + 5, // max. call depth in report + 4 * 1000 * 1000, // ring buffer size for profiling information + 10, // frame count + "/path/to/your/application.map"); +``` + +To find the hotspots in your code you might want to start with a relatively +small call depth (maybe 5) and increase it to gain a better understanding of the +detailed call hierarchy. The maximum call depth / stack size is 255. Keep the +buffer size as small as possible and increase on demand. + +Now you can wrap parts of your code into frames: + +```c +XRayStartFrame(trace); +do_work(); +XRayEndFrame(trace); + +XRayStartFrame(trace); +do_even_more_work(); +XRayEndFrame(trace); +``` + +And finally generate the report: + +```c +void XRaySaveReport(struct XRayTraceCapture* capture, + const char* filename, + float percent_cutoff, + int cycle_cutoff); + +XRaySaveReport(trace, + "/path/to/you/report/application.xray", // report file + 10.0f, // Only output funcs that have a higher runtime [%] + 2000); // Only output funcs that have a higher runtime [cycles] +XRayShutdown(trace); +``` + +Here you can do further filtering of the output. For a function call to be added +to the report, it's relative runtime (whole application) has be higher than +`percent_cutoff` and it's absolute runtime must be greater than `cycle_cutoff` +CPU cycles. + + +## Example + +See [usr/openmpbench/syncbench.c](https://github.com/RWTH-OS/HermitCore/blob/master/usr/openmpbench/syncbench.c). + + +## Analysis + +After tracing your code, you may want to analyse the report. While the XRay +report is already human-readable, it's hard to get an overview of the whole +trace. Therefore, it's possible to convert the XRay report to a format that +[kCacheGrind](https://kcachegrind.github.io) can read. You can find the tool +needed for conversion at `usr/xray/tools`. + +```bash +$ ./conv2kcg.py libgomp_trace.xray +INFO:Parsing Header is done. Found 1 frames +INFO:Found frame 'PARALLEL' data +INFO:Frame 'PARALLEL' complete +INFO:Report file 'libgomp_trace.xray' parsed completely. +INFO:Create callgrind file for frame 'PARALLEL' +INFO:Writing to: libgomp_trace_PARALLEL.callgrind +``` + +This will create the file `libgomp_trace_PARALLEL.callgrind` which can be opened +using kCacheGrind (Open dialog: set Filter to 'All Files'). diff --git a/usr/xray/xray.h b/usr/xray/xray.h index 6e0991f0c..aaa0e6c36 100644 --- a/usr/xray/xray.h +++ b/usr/xray/xray.h @@ -28,7 +28,7 @@ extern "C" { #endif #define XRAY_NO_INSTRUMENT __attribute__((no_instrument_function)) -#define XRAY_INLINE __attribute__((always_inline, no_instrument_function)) +#define XRAY_INLINE __attribute__((always_inline, no_instrument_function)) inline #if defined(XRAY)