ladybird/Kernel/CMakeLists.txt

737 lines
25 KiB
Text
Raw Normal View History

if (ENABLE_EXTRA_KERNEL_DEBUG_SYMBOLS)
add_compile_options(-Og)
add_compile_options(-ggdb3)
else()
add_compile_options(-O2)
endif()
if ("${SERENITY_ARCH}" STREQUAL "aarch64")
set(KERNEL_ARCH aarch64)
elseif ("${SERENITY_ARCH}" STREQUAL "i686")
set(KERNEL_ARCH i386)
elseif("${SERENITY_ARCH}" STREQUAL "x86_64")
set(KERNEL_ARCH x86_64)
endif()
set(KERNEL_HEAP_SOURCES
Heap/kmalloc.cpp
)
set(KERNEL_SOURCES
Kernel: Initial integration of Kernel Address Sanitizer (KASAN) KASAN is a dynamic analysis tool that finds memory errors. It focuses mostly on finding use-after-free and out-of-bound read/writes bugs. KASAN works by allocating a "shadow memory" region which is used to store whether each byte of memory is safe to access. The compiler then instruments the kernel code and a check is inserted which validates the state of the shadow memory region on every memory access (load or store). To fully integrate KASAN into the SerenityOS kernel we need to: a) Implement the KASAN interface to intercept the injected loads/stores. void __asan_load*(address); void __asan_store(address); b) Setup KASAN region and determine the shadow memory offset + translation. This might be challenging since Serenity is only 32bit at this time. Ex: Linux implements kernel address -> shadow address translation like: static inline void *kasan_mem_to_shadow(const void *addr) { return ((unsigned long)addr >> KASAN_SHADOW_SCALE_SHIFT) + KASAN_SHADOW_OFFSET; } c) Integrating KASAN with Kernel allocators. The kernel allocators need to be taught how to record allocation state in the shadow memory region. This commit only implements the initial steps of this long process: - A new (default OFF) CMake build flag `ENABLE_KERNEL_ADDRESS_SANITIZER` - Stubs out enough of the KASAN interface to allow the Kernel to link clean. Currently the KASAN kernel crashes on boot (triple fault because of the crash in strlen other sanitizer are seeing) but the goal here is to just get started, and this should help others jump in and continue making progress on KASAN. References: * ASAN Paper: https://static.googleusercontent.com/media/research.google.com/en//pubs/archive/37752.pdf * KASAN Docs: https://github.com/google/kasan * NetBSD KASAN Blog: https://blog.netbsd.org/tnf/entry/kernel_address_sanitizer_part_3 * LWN KASAN Article: https://lwn.net/Articles/612153/ * Tracking Issue #5351
2021-02-14 20:47:10 +00:00
AddressSanitizer.cpp
Bus/PCI/Controller/HostController.cpp
Bus/PCI/Controller/MemoryBackedHostBridge.cpp
Bus/PCI/Controller/VolumeManagementDevice.cpp
Bus/PCI/Access.cpp
Kernel/PCI: Simplify the entire subsystem A couple of things were changed: 1. Semantic changes - PCI segments are now called PCI domains, to better match what they are really. It's also the name that Linux gave, and it seems that Wikipedia also uses this name. We also remove PCI::ChangeableAddress, because it was used in the past but now it's no longer being used. 2. There are no WindowedMMIOAccess or MMIOAccess classes anymore, as they made a bunch of unnecessary complexity. Instead, Windowed access is removed entirely (this was tested, but never was benchmarked), so we are left with IO access and memory access options. The memory access option is essentially mapping the PCI bus (from the chosen PCI domain), to virtual memory as-is. This means that unless needed, at any time, there is only one PCI bus being mapped, and this is changed if access to another PCI bus in the same PCI domain is needed. For now, we don't support mapping of different PCI buses from different PCI domains at the same time, because basically it's still a non-issue for most machines out there. 2. OOM-safety is increased, especially when constructing the Access object. It means that we pre-allocating any needed resources, and we try to find PCI domains (if requested to initialize memory access) after we attempt to construct the Access object, so it's possible to fail at this point "gracefully". 3. All PCI API functions are now separated into a different header file, which means only "clients" of the PCI subsystem API will need to include that header file. 4. Functional changes - we only allow now to enumerate the bus after a hardware scan. This means that the old method "enumerate_hardware" is removed, so, when initializing an Access object, the initializing function must call rescan on it to force it to find devices. This makes it possible to fail rescan, and also to defer it after construction from both OOM-safety terms and hotplug capabilities.
2021-09-07 09:08:38 +00:00
Bus/PCI/API.cpp
Bus/PCI/Device.cpp
Bus/USB/UHCI/UHCIController.cpp
Bus/USB/UHCI/UHCIRootHub.cpp
Bus/USB/USBConfiguration.cpp
Bus/USB/USBController.cpp
Bus/USB/USBDevice.cpp
Bus/USB/USBHub.cpp
Bus/USB/USBManagement.cpp
Bus/USB/USBPipe.cpp
Bus/USB/USBTransfer.cpp
Bus/VirtIO/Console.cpp
Bus/VirtIO/ConsolePort.cpp
Bus/VirtIO/Device.cpp
Bus/VirtIO/Queue.cpp
Bus/VirtIO/RNG.cpp
CommandLine.cpp
Coredump.cpp
Credentials.cpp
Devices/AsyncDeviceRequest.cpp
Devices/Audio/AC97.cpp
Devices/Audio/Channel.cpp
Devices/Audio/Management.cpp
Devices/BlockDevice.cpp
Devices/CharacterDevice.cpp
Devices/ConsoleDevice.cpp
Devices/Device.cpp
Devices/DeviceControlDevice.cpp
Devices/DeviceManagement.cpp
Devices/FullDevice.cpp
Devices/KCOVDevice.cpp
Devices/KCOVInstance.cpp
Devices/MemoryDevice.cpp
Devices/NullDevice.cpp
Devices/PCISerialDevice.cpp
Devices/RandomDevice.cpp
Devices/SelfTTYDevice.cpp
Devices/SerialDevice.cpp
Devices/ZeroDevice.cpp
Devices/HID/HIDManagement.cpp
Devices/HID/KeyboardDevice.cpp
Devices/HID/MouseDevice.cpp
GlobalProcessExposed.cpp
Graphics/Bochs/GraphicsAdapter.cpp
Graphics/Bochs/QEMUDisplayConnector.cpp
Graphics/Console/BootFramebufferConsole.cpp
Graphics/Console/GenericFramebufferConsole.cpp
Graphics/Console/ContiguousFramebufferConsole.cpp
Graphics/Console/VGATextModeConsole.cpp
Graphics/DisplayConnector.cpp
Graphics/Generic/DisplayConnector.cpp
Graphics/GraphicsManagement.cpp
Graphics/Intel/NativeDisplayConnector.cpp
Graphics/Intel/NativeGraphicsAdapter.cpp
Graphics/VMWare/Console.cpp
Graphics/VMWare/GraphicsAdapter.cpp
Graphics/VMWare/DisplayConnector.cpp
Graphics/VirtIOGPU/DisplayConnector.cpp
Graphics/VirtIOGPU/Console.cpp
Graphics/VirtIOGPU/GPU3DDevice.cpp
Graphics/VirtIOGPU/GraphicsAdapter.cpp
Kernel: Introduce the IOWindow class This class is intended to replace all IOAddress usages in the Kernel codebase altogether. The idea is to ensure IO can be done in arch-specific manner that is determined mostly in compile-time, but to still be able to use most of the Kernel code in non-x86 builds. Specific devices that rely on x86-specific IO instructions are already placed in the Arch/x86 directory and are omitted for non-x86 builds. The reason this works so well is the fact that x86 IO space acts in a similar fashion to the traditional memory space being available in most CPU architectures - the x86 IO space is essentially just an array of bytes like the physical memory address space, but requires x86 IO instructions to load and store data. Therefore, many devices allow host software to interact with the hardware registers in both ways, with a noticeable trend even in the modern x86 hardware to move away from the old x86 IO space to exclusively using memory-mapped IO. Therefore, the IOWindow class encapsulates both methods for x86 builds. The idea is to allow PCI devices to be used in either way in x86 builds, so when trying to map an IOWindow on a PCI BAR, the Kernel will try to find the proper method being declared with the PCI BAR flags. For old PCI hardware on non-x86 builds this might turn into a problem as we can't use port mapped IO, so the Kernel will gracefully fail with ENOTSUP error code if that's the case, as there's really nothing we can do within such case. For general IO, the read{8,16,32} and write{8,16,32} methods are available as a convenient API for other places in the Kernel. There are simply no direct 64-bit IO API methods yet, as it's not needed right now and is not considered to be Arch-agnostic too - the x86 IO space doesn't support generating 64 bit cycle on IO bus and instead requires two 2 32-bit accesses. If for whatever reason it appears to be necessary to do IO in such manner, it could probably be added with some neat tricks to do so. It is recommended to use Memory::TypedMapping struct if direct 64 bit IO is actually needed.
2022-09-23 08:50:04 +00:00
IOWindow.cpp
SanCov.cpp
Storage/ATA/AHCI/Controller.cpp
Storage/ATA/AHCI/Port.cpp
Storage/ATA/AHCI/InterruptHandler.cpp
Storage/ATA/GenericIDE/Controller.cpp
Storage/ATA/GenericIDE/Channel.cpp
Kernel/Storage: Introduce new boot device addressing modes Before of this patch, we supported two methods to address a boot device: 1. Specifying root=/dev/hdXY, where X is a-z letter which corresponds to a boot device, and Y as number from 1 to 16, to indicate the partition number, which can be omitted to instruct the kernel to use a raw device rather than a partition on a raw device. 2. Specifying root=PARTUUID: with a GUID string of a GUID partition. In case of existing storage device with GPT partitions, this is most likely the safest option to ensure booting from persistent storage. While option 2 is more advanced and reliable, the first option has 2 caveats: 1. The string prefix "/dev/hd" doesn't mean anything beside a convention on Linux installations, that was taken into use in Serenity. In Serenity we don't mount DevTmpFS before we mount the boot device on /, so the kernel doesn't really access /dev anyway, so this convention is only a big misleading relic that can easily make the user to assume we access /dev early on boot. 2. This convention although resemble the simple linux convention, is quite limited in specifying a correct boot device across hardware setup changes, so option 2 was recommended to ensure the system is always bootable. With these caveats in mind, this commit tries to fix the problem with adding more addressing options as well as to remove the first option being mentioned above of addressing. To sum it up, there are 4 addressing options: 1. Hardware relative address - Each instance of StorageController is assigned with a index number relative to the type of hardware it handles which makes it possible to address storage devices with a prefix of the commandset ("ata" for ATA, "nvme" for NVMe, "ramdisk" for Plain memory), and then the number for the parent controller relative hardware index, another number LUN target_id, and a third number for LUN disk_id. 2. LUN address - Similar to the previous option, but instead we rely on the parent controller absolute index for the first number. 3. Block device major and minor numbers - by specifying the major and minor numbers, the kernel can simply try to get the corresponding block device and use it as the boot device. 4. GUID string, in the same fashion like before, so the user use the "PARTUUID:" string prefix and add the GUID of the GPT partition. For the new address modes 1 and 2, the user can choose to also specify a partition out of the selected boot device. To do that, the user needs to append the semicolon character and then add the string "partX" where X is to be changed for the partition number. We start counting from 0, and therefore the first partition number is 0 and not 1 in the kernel boot argument.
2022-08-05 17:32:26 +00:00
Storage/ATA/ATAController.cpp
Storage/ATA/ATADevice.cpp
Storage/ATA/ATADiskDevice.cpp
Storage/ATA/ATAPort.cpp
Storage/NVMe/NVMeController.cpp
Storage/NVMe/NVMeNameSpace.cpp
Storage/NVMe/NVMeInterruptQueue.cpp
Storage/NVMe/NVMePollQueue.cpp
Storage/NVMe/NVMeQueue.cpp
Storage/DiskPartition.cpp
Storage/StorageController.cpp
Storage/StorageDevice.cpp
Storage/StorageManagement.cpp
DoubleBuffer.cpp
FileSystem/AnonymousFile.cpp
FileSystem/BlockBasedFileSystem.cpp
FileSystem/Custody.cpp
FileSystem/DevPtsFS.cpp
FileSystem/DevTmpFS.cpp
FileSystem/Ext2FileSystem.cpp
FileSystem/FIFO.cpp
FileSystem/File.cpp
FileSystem/FileBackedFileSystem.cpp
FileSystem/FileSystem.cpp
FileSystem/Inode.cpp
FileSystem/InodeFile.cpp
FileSystem/InodeMetadata.cpp
FileSystem/InodeWatcher.cpp
FileSystem/ISO9660FileSystem.cpp
FileSystem/Mount.cpp
FileSystem/OpenFileDescription.cpp
FileSystem/Plan9FileSystem.cpp
FileSystem/ProcFS.cpp
FileSystem/SysFS.cpp
FileSystem/SysFS/Component.cpp
FileSystem/SysFS/Registry.cpp
FileSystem/SysFS/RootDirectory.cpp
FileSystem/SysFS/Subsystems/Bus/PCI/BusDirectory.cpp
FileSystem/SysFS/Subsystems/Bus/PCI/DeviceAttribute.cpp
FileSystem/SysFS/Subsystems/Bus/PCI/DeviceDirectory.cpp
FileSystem/SysFS/Subsystems/Bus/USB/BusDirectory.cpp
FileSystem/SysFS/Subsystems/Bus/USB/DeviceInformation.cpp
FileSystem/SysFS/Subsystems/Bus/Directory.cpp
FileSystem/SysFS/Subsystems/DeviceIdentifiers/BlockDevicesDirectory.cpp
FileSystem/SysFS/Subsystems/DeviceIdentifiers/CharacterDevicesDirectory.cpp
FileSystem/SysFS/Subsystems/DeviceIdentifiers/DeviceComponent.cpp
FileSystem/SysFS/Subsystems/DeviceIdentifiers/Directory.cpp
FileSystem/SysFS/Subsystems/DeviceIdentifiers/SymbolicLinkDeviceComponent.cpp
FileSystem/SysFS/Subsystems/Devices/Storage/DeviceAttribute.cpp
FileSystem/SysFS/Subsystems/Devices/Storage/DeviceDirectory.cpp
FileSystem/SysFS/Subsystems/Devices/Storage/Directory.cpp
FileSystem/SysFS/Subsystems/Devices/Graphics/Directory.cpp
FileSystem/SysFS/Subsystems/Devices/Graphics/DisplayConnector/Directory.cpp
FileSystem/SysFS/Subsystems/Devices/Graphics/DisplayConnector/DeviceDirectory.cpp
FileSystem/SysFS/Subsystems/Devices/Graphics/DisplayConnector/DeviceAttribute.cpp
FileSystem/SysFS/Subsystems/Devices/Directory.cpp
FileSystem/SysFS/Subsystems/Firmware/BIOS/Component.cpp
FileSystem/SysFS/Subsystems/Firmware/BIOS/Directory.cpp
FileSystem/SysFS/Subsystems/Firmware/Directory.cpp
FileSystem/SysFS/Subsystems/Firmware/PowerStateSwitch.cpp
FileSystem/TmpFS.cpp
FileSystem/VirtualFileSystem.cpp
Firmware/BIOS.cpp
Firmware/ACPI/Initialize.cpp
Firmware/ACPI/Parser.cpp
Firmware/MultiProcessor/Parser.cpp
FutexQueue.cpp
Interrupts/GenericInterruptHandler.cpp
Interrupts/IRQHandler.cpp
Interrupts/SharedIRQHandler.cpp
Interrupts/SpuriousInterruptHandler.cpp
Interrupts/UnhandledInterruptHandler.cpp
KBufferBuilder.cpp
KLexicalPath.cpp
KString.cpp
KSyms.cpp
Memory/AddressSpace.cpp
Memory/AnonymousVMObject.cpp
Memory/InodeVMObject.cpp
Memory/MemoryManager.cpp
Memory/PageDirectory.cpp
Memory/PhysicalPage.cpp
Memory/PhysicalRegion.cpp
Memory/PhysicalZone.cpp
Memory/PrivateInodeVMObject.cpp
Memory/Region.cpp
Memory/RegionTree.cpp
Memory/RingBuffer.cpp
Memory/ScatterGatherList.cpp
Memory/ScopedAddressSpaceSwitcher.cpp
Memory/SharedFramebufferVMObject.cpp
Memory/SharedInodeVMObject.cpp
Memory/VMObject.cpp
Memory/VirtualRange.cpp
MiniStdLib.cpp
Locking/LockRank.cpp
2021-07-18 07:10:27 +00:00
Locking/Mutex.cpp
Locking/Spinlock.cpp
Net/Intel/E1000ENetworkAdapter.cpp
Net/Intel/E1000NetworkAdapter.cpp
Net/NE2000/NetworkAdapter.cpp
Net/Realtek/RTL8139NetworkAdapter.cpp
Net/Realtek/RTL8168NetworkAdapter.cpp
Net/IPv4Socket.cpp
Net/LocalSocket.cpp
Net/LoopbackAdapter.cpp
Net/NetworkAdapter.cpp
Net/NetworkTask.cpp
Net/NetworkingManagement.cpp
Net/Routing.cpp
Net/Socket.cpp
Net/TCPSocket.cpp
Net/UDPSocket.cpp
Panic.cpp
PerformanceEventBuffer.cpp
Process.cpp
Kernel: Introduce the new ProcFS design The new ProcFS design consists of two main parts: 1. The representative ProcFS class, which is derived from the FS class. The ProcFS and its inodes are much more lean - merely 3 classes to represent the common type of inodes - regular files, symbolic links and directories. They're backed by a ProcFSExposedComponent object, which is responsible for the functional operation behind the scenes. 2. The backend of the ProcFS - the ProcFSComponentsRegistrar class and all derived classes from the ProcFSExposedComponent class. These together form the entire backend and handle all the functions you can expect from the ProcFS. The ProcFSExposedComponent derived classes split to 3 types in the manner of lifetime in the kernel: 1. Persistent objects - this category includes all basic objects, like the root folder, /proc/bus folder, main blob files in the root folders, etc. These objects are persistent and cannot die ever. 2. Semi-persistent objects - this category includes all PID folders, and subdirectories to the PID folders. It also includes exposed objects like the unveil JSON'ed blob. These object are persistent as long as the the responsible process they represent is still alive. 3. Dynamic objects - this category includes files in the subdirectories of a PID folder, like /proc/PID/fd/* or /proc/PID/stacks/*. Essentially, these objects are always created dynamically and when no longer in need after being used, they're deallocated. Nevertheless, the new allocated backend objects and inodes try to use the same InodeIndex if possible - this might change only when a thread dies and a new thread is born with a new thread stack, or when a file descriptor is closed and a new one within the same file descriptor number is opened. This is needed to actually be able to do something useful with these objects. The new design assures that many ProcFS instances can be used at once, with one backend for usage for all instances.
2021-06-12 01:23:58 +00:00
ProcessExposed.cpp
ProcessSpecificExposed.cpp
ProcessGroup.cpp
ProcessProcFSTraits.cpp
Random.cpp
Scheduler.cpp
StdLib.cpp
Syscall.cpp
Syscalls/anon_create.cpp
Syscalls/access.cpp
Syscalls/alarm.cpp
Syscalls/beep.cpp
Syscalls/chdir.cpp
Syscalls/chmod.cpp
Syscalls/chown.cpp
Syscalls/clock.cpp
Syscalls/debug.cpp
Syscalls/disown.cpp
Syscalls/dup2.cpp
Syscalls/emuctl.cpp
Syscalls/execve.cpp
Syscalls/exit.cpp
Syscalls/fallocate.cpp
Syscalls/fcntl.cpp
Syscalls/fork.cpp
2021-09-12 03:28:59 +00:00
Syscalls/fsync.cpp
Syscalls/ftruncate.cpp
Syscalls/futex.cpp
Syscalls/get_dir_entries.cpp
Syscalls/get_stack_bounds.cpp
Syscalls/getrandom.cpp
Syscalls/getuid.cpp
Syscalls/hostname.cpp
Syscalls/ioctl.cpp
Syscalls/keymap.cpp
Syscalls/kill.cpp
Syscalls/link.cpp
Syscalls/lseek.cpp
Syscalls/mkdir.cpp
Syscalls/mknod.cpp
Syscalls/mmap.cpp
Syscalls/mount.cpp
Syscalls/open.cpp
Syscalls/perf_event.cpp
Syscalls/pipe.cpp
Syscalls/pledge.cpp
Syscalls/poll.cpp
Syscalls/prctl.cpp
Syscalls/process.cpp
Syscalls/profiling.cpp
Syscalls/ptrace.cpp
Syscalls/purge.cpp
Syscalls/read.cpp
Syscalls/readlink.cpp
Syscalls/realpath.cpp
Syscalls/rename.cpp
Syscalls/resource.cpp
Syscalls/rmdir.cpp
Syscalls/sched.cpp
Syscalls/sendfd.cpp
Syscalls/setpgid.cpp
Syscalls/setuid.cpp
Syscalls/sigaction.cpp
Syscalls/socket.cpp
Syscalls/stat.cpp
Syscalls/statvfs.cpp
Syscalls/sync.cpp
Syscalls/sysconf.cpp
Syscalls/thread.cpp
Syscalls/times.cpp
Syscalls/umask.cpp
Syscalls/uname.cpp
Syscalls/unlink.cpp
Syscalls/unveil.cpp
Syscalls/utime.cpp
Syscalls/utimensat.cpp
Syscalls/waitid.cpp
Syscalls/inode_watcher.cpp
Syscalls/write.cpp
TTY/ConsoleManagement.cpp
TTY/MasterPTY.cpp
TTY/PTYMultiplexer.cpp
TTY/SlavePTY.cpp
TTY/TTY.cpp
TTY/VirtualConsole.cpp
Tasks/FinalizerTask.cpp
Tasks/SyncTask.cpp
Thread.cpp
ThreadBlockers.cpp
ThreadTracer.cpp
Time/TimeManagement.cpp
TimerQueue.cpp
UBSanitizer.cpp
UserOrKernelBuffer.cpp
WaitQueue.cpp
WorkQueue.cpp
kprintf.cpp
)
if ("${SERENITY_ARCH}" STREQUAL "i686" OR "${SERENITY_ARCH}" STREQUAL "x86_64")
set(KERNEL_SOURCES
${KERNEL_SOURCES}
Arch/x86/init.cpp
Arch/Processor.cpp
Arch/x86/common/Interrupts/APIC.cpp
Arch/x86/common/Interrupts/IOAPIC.cpp
Arch/x86/common/Interrupts/PIC.cpp
Arch/x86/common/CMOS.cpp
Arch/x86/common/DebugOutput.cpp
Arch/x86/common/Delay.cpp
Arch/x86/common/I8042Reboot.cpp
Arch/x86/common/PCSpeaker.cpp
Arch/x86/common/RTC.cpp
Arch/x86/common/ScopedCritical.cpp
Arch/x86/common/SmapDisabler.cpp
Arch/x86/common/Shutdown.cpp
Arch/x86/CurrentTime.cpp
Arch/x86/Hypervisor/BochsDisplayConnector.cpp
Arch/x86/Hypervisor/VMWareBackdoor.cpp
Arch/x86/ISABus/HID/PS2KeyboardDevice.cpp
Arch/x86/ISABus/HID/PS2MouseDevice.cpp
Arch/x86/ISABus/HID/VMWareMouseDevice.cpp
Arch/x86/ISABus/I8042Controller.cpp
Arch/x86/ISABus/IDEController.cpp
Kernel: Introduce the IOWindow class This class is intended to replace all IOAddress usages in the Kernel codebase altogether. The idea is to ensure IO can be done in arch-specific manner that is determined mostly in compile-time, but to still be able to use most of the Kernel code in non-x86 builds. Specific devices that rely on x86-specific IO instructions are already placed in the Arch/x86 directory and are omitted for non-x86 builds. The reason this works so well is the fact that x86 IO space acts in a similar fashion to the traditional memory space being available in most CPU architectures - the x86 IO space is essentially just an array of bytes like the physical memory address space, but requires x86 IO instructions to load and store data. Therefore, many devices allow host software to interact with the hardware registers in both ways, with a noticeable trend even in the modern x86 hardware to move away from the old x86 IO space to exclusively using memory-mapped IO. Therefore, the IOWindow class encapsulates both methods for x86 builds. The idea is to allow PCI devices to be used in either way in x86 builds, so when trying to map an IOWindow on a PCI BAR, the Kernel will try to find the proper method being declared with the PCI BAR flags. For old PCI hardware on non-x86 builds this might turn into a problem as we can't use port mapped IO, so the Kernel will gracefully fail with ENOTSUP error code if that's the case, as there's really nothing we can do within such case. For general IO, the read{8,16,32} and write{8,16,32} methods are available as a convenient API for other places in the Kernel. There are simply no direct 64-bit IO API methods yet, as it's not needed right now and is not considered to be Arch-agnostic too - the x86 IO space doesn't support generating 64 bit cycle on IO bus and instead requires two 2 32-bit accesses. If for whatever reason it appears to be necessary to do IO in such manner, it could probably be added with some neat tricks to do so. It is recommended to use Memory::TypedMapping struct if direct 64 bit IO is actually needed.
2022-09-23 08:50:04 +00:00
Arch/x86/ISABus/SerialDevice.cpp
Arch/x86/PCI/Controller/HostBridge.cpp
Arch/x86/PCI/IDELegacyModeController.cpp
Arch/x86/PCI/Initializer.cpp
Arch/x86/Time/APICTimer.cpp
Arch/x86/Time/HPET.cpp
Arch/x86/Time/HPETComparator.cpp
Arch/x86/Time/PIT.cpp
Arch/x86/Time/RTC.cpp
Arch/x86/VGA/IOArbiter.cpp
)
set(KERNEL_SOURCES
${KERNEL_SOURCES}
${CMAKE_CURRENT_SOURCE_DIR}/Arch/x86/${KERNEL_ARCH}/ASM_wrapper.cpp
${CMAKE_CURRENT_SOURCE_DIR}/Arch/x86/${KERNEL_ARCH}/Boot/ap_setup.S
${CMAKE_CURRENT_SOURCE_DIR}/Arch/x86/${KERNEL_ARCH}/InterruptEntry.cpp
${CMAKE_CURRENT_SOURCE_DIR}/Arch/x86/${KERNEL_ARCH}/Processor.cpp
)
set(KERNEL_SOURCES
${KERNEL_SOURCES}
${CMAKE_CURRENT_SOURCE_DIR}/Arch/x86/common/ASM_wrapper.cpp
${CMAKE_CURRENT_SOURCE_DIR}/Arch/x86/common/CPU.cpp
${CMAKE_CURRENT_SOURCE_DIR}/Arch/x86/common/CPUID.cpp
${CMAKE_CURRENT_SOURCE_DIR}/Arch/x86/common/CrashHandler.cpp
${CMAKE_CURRENT_SOURCE_DIR}/Arch/x86/common/InterruptManagement.cpp
${CMAKE_CURRENT_SOURCE_DIR}/Arch/x86/common/Interrupts.cpp
${CMAKE_CURRENT_SOURCE_DIR}/Arch/x86/common/PageDirectory.cpp
${CMAKE_CURRENT_SOURCE_DIR}/Arch/x86/common/Processor.cpp
${CMAKE_CURRENT_SOURCE_DIR}/Arch/x86/common/ProcessorInfo.cpp
${CMAKE_CURRENT_SOURCE_DIR}/Arch/x86/common/SafeMem.cpp
${CMAKE_CURRENT_SOURCE_DIR}/Arch/x86/common/TrapFrame.cpp
)
if("${SERENITY_ARCH}" STREQUAL "x86_64")
set(KERNEL_SOURCES
${KERNEL_SOURCES}
${CMAKE_CURRENT_SOURCE_DIR}/Arch/x86/${KERNEL_ARCH}/SyscallEntry.cpp
)
endif()
if ("${SERENITY_ARCH}" STREQUAL "i686")
set(KERNEL_SOURCES
${KERNEL_SOURCES}
${CMAKE_CURRENT_SOURCE_DIR}/Arch/x86/${KERNEL_ARCH}/Atomics.cpp
)
endif()
endif()
set(AK_SOURCES
../AK/GenericLexer.cpp
../AK/Hex.cpp
../AK/StringBuilder.cpp
../AK/StringUtils.cpp
../AK/StringView.cpp
../AK/Time.cpp
../AK/Format.cpp
../AK/UUID.cpp
)
set(EDID_SOURCES
../Userland/Libraries/LibEDID/DMT.cpp
../Userland/Libraries/LibEDID/EDID.cpp
../Userland/Libraries/LibEDID/VIC.cpp
)
set(ELF_SOURCES
2021-01-12 11:17:30 +00:00
../Userland/Libraries/LibELF/Image.cpp
../Userland/Libraries/LibELF/Validation.cpp
)
add_custom_command(
COMMAND "${SerenityOS_SOURCE_DIR}/Kernel/generate-version-file.sh" "${CMAKE_CURRENT_BINARY_DIR}/Version.h.tmp"
COMMAND "${CMAKE_COMMAND}" -E copy_if_different "${CMAKE_CURRENT_BINARY_DIR}/Version.h.tmp" "${CMAKE_CURRENT_BINARY_DIR}/Version.h"
COMMAND "${CMAKE_COMMAND}" -E remove "${CMAKE_CURRENT_BINARY_DIR}/Version.h.tmp"
WORKING_DIRECTORY "${SerenityOS_SOURCE_DIR}"
COMMENT "Generating SerenityOS version information"
OUTPUT "${CMAKE_CURRENT_BINARY_DIR}/Version.h"
VERBATIM
)
add_custom_target(generate_version_header ALL DEPENDS "${CMAKE_CURRENT_BINARY_DIR}/Version.h")
set(GENERATED_SOURCES "${CMAKE_CURRENT_BINARY_DIR}/Version.h")
generate_state_machine(../Userland/Libraries/LibVT/StateMachine.txt ../Userland/Libraries/LibVT/EscapeSequenceStateMachine.h)
set(VT_SOURCES
2021-01-12 11:17:30 +00:00
../Userland/Libraries/LibVT/Terminal.cpp
../Userland/Libraries/LibVT/Line.cpp
../Userland/Libraries/LibVT/EscapeSequenceParser.cpp
)
set(CRYPTO_SOURCES
2021-01-12 11:17:30 +00:00
../Userland/Libraries/LibCrypto/Cipher/AES.cpp
../Userland/Libraries/LibCrypto/Hash/SHA2.cpp
)
set(PARTITION_SOURCES
../Userland/Libraries/LibPartition/DiskPartitionMetadata.cpp
../Userland/Libraries/LibPartition/EBRPartitionTable.cpp
../Userland/Libraries/LibPartition/GUIDPartitionTable.cpp
../Userland/Libraries/LibPartition/MBRPartitionTable.cpp
../Userland/Libraries/LibPartition/PartitionTable.cpp
)
2021-10-15 13:57:42 +00:00
set(SOURCES
${AK_SOURCES}
)
if (NOT "${SERENITY_ARCH}" STREQUAL "aarch64")
set(SOURCES
${KERNEL_SOURCES}
${GENERATED_SOURCES}
${SOURCES}
${EDID_SOURCES}
${ELF_SOURCES}
${VT_SOURCES}
${CRYPTO_SOURCES}
${PARTITION_SOURCES}
)
else()
set(RPI_SOURCES
Arch/aarch64/RPi/DebugOutput.cpp
Arch/aarch64/RPi/Framebuffer.cpp
Arch/aarch64/RPi/GPIO.cpp
Arch/aarch64/RPi/InterruptController.cpp
Arch/aarch64/RPi/Mailbox.cpp
Arch/aarch64/RPi/MMIO.cpp
Arch/aarch64/RPi/Timer.cpp
Arch/aarch64/RPi/UART.cpp
)
set(SOURCES
2022-04-02 22:49:07 +00:00
${AK_SOURCES}
${RPI_SOURCES}
2022-04-02 22:49:07 +00:00
Arch/Processor.cpp
Arch/aarch64/boot.S
Arch/aarch64/BootPPMParser.cpp
Arch/aarch64/CrashHandler.cpp
Arch/aarch64/CurrentTime.cpp
Arch/aarch64/Dummy.cpp
Arch/aarch64/Exceptions.cpp
Arch/aarch64/init.cpp
Arch/aarch64/InterruptManagement.cpp
Arch/aarch64/Interrupts.cpp
Arch/aarch64/kprintf.cpp
Arch/aarch64/MainIdRegister.cpp
Arch/aarch64/MMU.cpp
Arch/aarch64/PageDirectory.cpp
Arch/aarch64/Panic.cpp
Arch/aarch64/Processor.cpp
Arch/aarch64/SafeMem.cpp
Arch/aarch64/ScopedCritical.cpp
Arch/aarch64/SmapDisabler.cpp
Arch/aarch64/vector_table.S
# Files from base Kernel
CommandLine.cpp
KString.cpp
KSyms.cpp
MiniStdLib.cpp
StdLib.cpp
UBSanitizer.cpp
UserOrKernelBuffer.cpp
2022-04-02 23:06:34 +00:00
Devices/DeviceManagement.cpp
Graphics/Console/BootFramebufferConsole.cpp
Graphics/Console/GenericFramebufferConsole.cpp
Locking/Spinlock.cpp
Memory/AddressSpace.cpp
Memory/AnonymousVMObject.cpp
Memory/InodeVMObject.cpp
Memory/MemoryManager.cpp
Memory/PageDirectory.cpp
Memory/PhysicalPage.cpp
Memory/PhysicalRegion.cpp
Memory/PhysicalZone.cpp
Memory/PrivateInodeVMObject.cpp
Memory/Region.cpp
Memory/RegionTree.cpp
Memory/RingBuffer.cpp
Memory/ScatterGatherList.cpp
Memory/SharedInodeVMObject.cpp
Memory/VirtualRange.cpp
Memory/VMObject.cpp
Interrupts/GenericInterruptHandler.cpp
Interrupts/IRQHandler.cpp
Interrupts/SharedIRQHandler.cpp
Interrupts/UnhandledInterruptHandler.cpp
)
# Otherwise linker errors e.g undefined reference to `__aarch64_cas8_acq_rel'
add_compile_options(-mno-outline-atomics -latomic)
# FIXME: Remove this once compiling MemoryManager.cpp doesn't give the nonnull error anymore.
add_compile_options(-Wno-nonnull)
endif()
add_compile_options(-fsigned-char)
add_compile_options(-Wno-unknown-warning-option -Wvla -Wnull-dereference)
add_compile_options(-fno-rtti -ffreestanding -fbuiltin)
if ("${SERENITY_ARCH}" STREQUAL "i686" OR "${SERENITY_ARCH}" STREQUAL "x86_64")
add_compile_options(-mno-80387 -mno-mmx -mno-sse -mno-sse2)
elseif("${SERENITY_ARCH}" STREQUAL "aarch64")
add_compile_options(-mgeneral-regs-only)
endif()
add_compile_options(-fno-asynchronous-unwind-tables)
add_compile_options(-fstack-protector-strong)
add_compile_options(-fno-exceptions)
add_compile_options(-nostdlib)
# Auto initialize trivial types on the stack, we use "pattern" as
# it's the only option portable across compilers going forward.
#
# This is designed to help avoid uninitialized variables bugs and
# information disclosures coming from the kernel stack.
#
# FIXME: It appears to conflict with something during the boot of the
# aarch64 kernel, we should investigate and remove this special case.
if (NOT "${SERENITY_ARCH}" STREQUAL "aarch64")
add_compile_options(-ftrivial-auto-var-init=pattern)
endif()
if (CMAKE_CXX_COMPILER_ID STREQUAL "GNU")
# Apply any flags that are only available on >= GCC 11.1
if (CMAKE_CXX_COMPILER_VERSION VERSION_GREATER_EQUAL "11.1")
# Zero any registers used within a function on return (to reduce data lifetime and ROP gadgets).
add_compile_options(-fzero-call-used-regs=used-gpr)
endif()
link_directories(${TOOLCHAIN_ROOT}/${SERENITY_ARCH}-pc-serenity/lib)
link_directories(${TOOLCHAIN_ROOT}/lib/gcc/${SERENITY_ARCH}-pc-serenity/${GCC_VERSION}/)
set(TARGET_STRING "")
# Prevent naively implemented string functions (like strlen) from being "optimized" into a call to themselves.
set_source_files_properties(MiniStdLib.cpp
PROPERTIES COMPILE_FLAGS "-fno-tree-loop-distribution -fno-tree-loop-distribute-patterns")
add_link_options(LINKER:-z,pack-relative-relocs)
else() # Assume Clang
add_compile_options(-Waddress-of-packed-member)
add_compile_options(-faligned-allocation)
# We need this in order to pick up the #define __serenity__, otherwise we end up including unistd.h into the linker script
set(TARGET_STRING "--target=${CMAKE_CXX_COMPILER_TARGET}")
add_link_options(LINKER:--build-id=none LINKER:--pack-dyn-relocs=relr)
endif()
macro (set_new_alignment alignment)
if (CMAKE_CXX_COMPILER_ID STREQUAL "GNU")
add_compile_options(-faligned-new=${alignment})
elseif (CMAKE_CXX_COMPILER_ID MATCHES "Clang$")
add_compile_options(-fnew-alignment=${alignment})
endif()
endmacro()
if ("${SERENITY_ARCH}" STREQUAL "x86_64")
add_compile_options(-mcmodel=large -mno-red-zone)
set_new_alignment(8)
elseif ("${SERENITY_ARCH}" STREQUAL "i686")
set_new_alignment(4)
endif()
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -static-pie")
2021-07-23 10:56:35 +00:00
# Kernel Coverage (KCOV) is an API to collect and expose program counters of
# kernel code that has been run to user space. It's rather slow and likely not
# secure to run in production builds. Useful for coverage guided fuzzing.
if (ENABLE_KERNEL_COVERAGE_COLLECTION)
add_definitions(-DENABLE_KERNEL_COVERAGE_COLLECTION)
add_compile_options(-fsanitize-coverage=trace-pc)
set(KCOV_EXCLUDED_SOURCES
# Make sure we don't instrument any code called from __sanitizer_cov_trace_pc
# otherwise we'll end up with recursive calls to that function.
../AK/Format.cpp
../AK/StringBuilder.cpp
../Kernel/Arch/x86/${KERNEL_ARCH}/Processor.cpp
../Kernel/Devices/KCOVDevice.cpp
../Kernel/Devices/KCOVInstance.cpp
../Kernel/FileSystem/File.cpp
../Kernel/FileSystem/OpenFileDescription.cpp
../Kernel/init.cpp
../Kernel/SanCov.cpp
# GCC assumes that the caller saves registers for functions according
# to the System V ABI and happily inserts coverage calls into the
# function prologue for all functions. This assumption is not true for
# interrupt handlers because their calling convention is not compatible
# with the System V ABI.
../Kernel/Arch/x86/common/Interrupts.cpp
../Kernel/Syscall.cpp
)
set_source_files_properties(${KCOV_EXCLUDED_SOURCES} PROPERTIES COMPILE_FLAGS "-fno-sanitize-coverage=trace-pc")
elseif (ENABLE_USERSPACE_COVERAGE_COLLECTION)
# Disable checking open() pledges and the veil for coverage data when building userspace with coverage
# so that binaries can write out coverage data even with pledges/veil
add_compile_definitions(SKIP_PATH_VALIDATION_FOR_COVERAGE_INSTRUMENTATION)
endif()
if (ENABLE_KERNEL_UNDEFINED_SANITIZER)
# Kernel Undefined Behavior Sanitizer (KUBSAN)
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -fsanitize=undefined")
endif()
Kernel: Initial integration of Kernel Address Sanitizer (KASAN) KASAN is a dynamic analysis tool that finds memory errors. It focuses mostly on finding use-after-free and out-of-bound read/writes bugs. KASAN works by allocating a "shadow memory" region which is used to store whether each byte of memory is safe to access. The compiler then instruments the kernel code and a check is inserted which validates the state of the shadow memory region on every memory access (load or store). To fully integrate KASAN into the SerenityOS kernel we need to: a) Implement the KASAN interface to intercept the injected loads/stores. void __asan_load*(address); void __asan_store(address); b) Setup KASAN region and determine the shadow memory offset + translation. This might be challenging since Serenity is only 32bit at this time. Ex: Linux implements kernel address -> shadow address translation like: static inline void *kasan_mem_to_shadow(const void *addr) { return ((unsigned long)addr >> KASAN_SHADOW_SCALE_SHIFT) + KASAN_SHADOW_OFFSET; } c) Integrating KASAN with Kernel allocators. The kernel allocators need to be taught how to record allocation state in the shadow memory region. This commit only implements the initial steps of this long process: - A new (default OFF) CMake build flag `ENABLE_KERNEL_ADDRESS_SANITIZER` - Stubs out enough of the KASAN interface to allow the Kernel to link clean. Currently the KASAN kernel crashes on boot (triple fault because of the crash in strlen other sanitizer are seeing) but the goal here is to just get started, and this should help others jump in and continue making progress on KASAN. References: * ASAN Paper: https://static.googleusercontent.com/media/research.google.com/en//pubs/archive/37752.pdf * KASAN Docs: https://github.com/google/kasan * NetBSD KASAN Blog: https://blog.netbsd.org/tnf/entry/kernel_address_sanitizer_part_3 * LWN KASAN Article: https://lwn.net/Articles/612153/ * Tracking Issue #5351
2021-02-14 20:47:10 +00:00
# Kernel Address Sanitize (KASAN) implementation is still a work in progress, this option
# is not currently meant to be used, besides when developing Kernel ASAN support.
#
if (ENABLE_KERNEL_ADDRESS_SANITIZER)
add_compile_options(-fsanitize=kernel-address)
add_link_options(-fsanitize=kernel-address)
Kernel: Initial integration of Kernel Address Sanitizer (KASAN) KASAN is a dynamic analysis tool that finds memory errors. It focuses mostly on finding use-after-free and out-of-bound read/writes bugs. KASAN works by allocating a "shadow memory" region which is used to store whether each byte of memory is safe to access. The compiler then instruments the kernel code and a check is inserted which validates the state of the shadow memory region on every memory access (load or store). To fully integrate KASAN into the SerenityOS kernel we need to: a) Implement the KASAN interface to intercept the injected loads/stores. void __asan_load*(address); void __asan_store(address); b) Setup KASAN region and determine the shadow memory offset + translation. This might be challenging since Serenity is only 32bit at this time. Ex: Linux implements kernel address -> shadow address translation like: static inline void *kasan_mem_to_shadow(const void *addr) { return ((unsigned long)addr >> KASAN_SHADOW_SCALE_SHIFT) + KASAN_SHADOW_OFFSET; } c) Integrating KASAN with Kernel allocators. The kernel allocators need to be taught how to record allocation state in the shadow memory region. This commit only implements the initial steps of this long process: - A new (default OFF) CMake build flag `ENABLE_KERNEL_ADDRESS_SANITIZER` - Stubs out enough of the KASAN interface to allow the Kernel to link clean. Currently the KASAN kernel crashes on boot (triple fault because of the crash in strlen other sanitizer are seeing) but the goal here is to just get started, and this should help others jump in and continue making progress on KASAN. References: * ASAN Paper: https://static.googleusercontent.com/media/research.google.com/en//pubs/archive/37752.pdf * KASAN Docs: https://github.com/google/kasan * NetBSD KASAN Blog: https://blog.netbsd.org/tnf/entry/kernel_address_sanitizer_part_3 * LWN KASAN Article: https://lwn.net/Articles/612153/ * Tracking Issue #5351
2021-02-14 20:47:10 +00:00
endif()
if ("${SERENITY_ARCH}" STREQUAL "aarch64")
add_compile_options(-fno-threadsafe-statics)
endif()
add_compile_definitions(KERNEL)
add_link_options(LINKER:-z,notext)
add_library(kernel_heap STATIC ${KERNEL_HEAP_SOURCES})
add_executable(Kernel ${SOURCES})
add_dependencies(Kernel generate_EscapeSequenceStateMachine.h)
if (NOT "${SERENITY_ARCH}" STREQUAL "aarch64")
add_custom_command(
OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/linker.ld
COMMAND "${CMAKE_CXX_COMPILER}" ${TARGET_STRING} -E -P -x c -I${CMAKE_CURRENT_SOURCE_DIR}/.. "${CMAKE_CURRENT_SOURCE_DIR}/Arch/x86/linker.ld" -o "${CMAKE_CURRENT_BINARY_DIR}/linker.ld"
MAIN_DEPENDENCY "Arch/x86/linker.ld"
COMMENT "Preprocessing linker.ld"
VERBATIM
)
add_custom_target(generate_kernel_linker_script DEPENDS ${CMAKE_CURRENT_BINARY_DIR}/linker.ld)
target_link_options(Kernel PRIVATE LINKER:-T ${CMAKE_CURRENT_BINARY_DIR}/linker.ld -nostdlib -nodefaultlibs)
set_target_properties(Kernel PROPERTIES LINK_DEPENDS "${CMAKE_CURRENT_BINARY_DIR}/linker.ld")
else()
target_link_options(Kernel PRIVATE LINKER:-T ${CMAKE_CURRENT_SOURCE_DIR}/Arch/aarch64/linker.ld -nostdlib LINKER:--no-pie)
set_target_properties(Kernel PROPERTIES LINK_DEPENDS ${CMAKE_CURRENT_SOURCE_DIR}/Arch/aarch64/linker.ld)
endif()
if (ENABLE_KERNEL_LTO)
include(CheckIPOSupported)
check_ipo_supported()
add_definitions(-DENABLE_KERNEL_LTO)
set_property(TARGET Kernel PROPERTY INTERPROCEDURAL_OPTIMIZATION TRUE)
if (NOT "${SERENITY_ARCH}" STREQUAL "aarch64")
set_property(TARGET kernel_heap PROPERTY INTERPROCEDURAL_OPTIMIZATION TRUE)
endif()
endif()
if (CMAKE_CXX_COMPILER_ID STREQUAL "GNU")
target_link_libraries(Kernel PRIVATE kernel_heap gcc)
elseif(CMAKE_CXX_COMPILER_ID MATCHES "Clang$")
target_link_libraries(Kernel PRIVATE kernel_heap clang_rt.builtins)
endif()
add_custom_command(
TARGET Kernel POST_BUILD
COMMAND "${CMAKE_COMMAND}" -E env NM=${CMAKE_NM} sh ${CMAKE_CURRENT_SOURCE_DIR}/mkmap.sh
COMMAND "${CMAKE_COMMAND}" -E env OBJCOPY=${CMAKE_OBJCOPY} sh ${CMAKE_CURRENT_SOURCE_DIR}/embedmap.sh
COMMAND ${CMAKE_OBJCOPY} --only-keep-debug Kernel Kernel.debug
COMMAND ${CMAKE_OBJCOPY} --strip-debug Kernel
COMMAND ${CMAKE_OBJCOPY} --add-gnu-debuglink=Kernel.debug Kernel
BYPRODUCTS ${CMAKE_CURRENT_BINARY_DIR}/kernel.map
)
install(FILES "${CMAKE_CURRENT_BINARY_DIR}/Kernel" DESTINATION boot)
install(FILES "${CMAKE_CURRENT_BINARY_DIR}/Kernel.debug" DESTINATION boot)
install(FILES "${CMAKE_CURRENT_BINARY_DIR}/kernel.map" DESTINATION res)
if ("${SERENITY_ARCH}" STREQUAL "aarch64")
embed_resource(Kernel serenity_boot_logo "Arch/aarch64/SerenityLogoRGB.ppm")
add_custom_command(
TARGET Kernel POST_BUILD
COMMAND ${CMAKE_OBJCOPY} -O binary Kernel kernel8.img
BYPRODUCTS ${CMAKE_CURRENT_BINARY_DIR}/kernel8.img
)
endif()
serenity_install_headers(Kernel)
serenity_install_sources(Kernel)
# aarch64 does not need a Prekernel
if (NOT "${SERENITY_ARCH}" STREQUAL "aarch64")
add_subdirectory(Prekernel)
endif()