From 1b4bd4df5f5cc15c688a13a169a76a8af69d0700 Mon Sep 17 00:00:00 2001 From: Amlal El Mahrouss Date: Fri, 2 Feb 2024 11:58:14 +0100 Subject: Bootloader: Getting it done now. Signed-off-by: Amlal El Mahrouss --- Private/EFIKit/Api.hxx | 6 ++-- Private/EFIKit/EFI.hxx | 17 +++++++++++ Private/FSKit/NewFS.hxx | 27 +++++++++-------- Private/NewBoot/BootKit/Arch/ATA.hxx | 4 ++- Private/NewBoot/BootKit/BootKit.hxx | 5 ++-- Private/NewBoot/Source/HEL/AMD64/ATA.cxx | 22 +++++--------- Private/NewBoot/Source/HEL/AMD64/BootKit.cxx | 40 ++++++++++++++++++++----- Private/NewBoot/Source/HEL/AMD64/Entrypoint.cxx | 3 ++ Private/NewBoot/Source/makefile | 1 + 9 files changed, 84 insertions(+), 41 deletions(-) diff --git a/Private/EFIKit/Api.hxx b/Private/EFIKit/Api.hxx index b08c2866..dea09425 100644 --- a/Private/EFIKit/Api.hxx +++ b/Private/EFIKit/Api.hxx @@ -7,8 +7,8 @@ * ======================================================== */ -#ifndef __EFI_LIB__ -#define __EFI_LIB__ +#ifndef __EFI_API__ +#define __EFI_API__ #include @@ -72,4 +72,4 @@ enum { #include #endif // IF TARGET=BOOTLOADER -#endif /* ifndef __EFI_LIB__ */ +#endif /* ifndef __EFI_API__ */ diff --git a/Private/EFIKit/EFI.hxx b/Private/EFIKit/EFI.hxx index 529efe65..6ea95b0d 100644 --- a/Private/EFIKit/EFI.hxx +++ b/Private/EFIKit/EFI.hxx @@ -268,6 +268,13 @@ typedef struct EfiDevicePathProtocol { UInt8 LengthData[2]; } EfiDevicePathProtocol; +typedef struct EfiFileDevicePathProtocol { + UInt8 Type; + UInt8 SubType; + UInt8 LengthData[2]; + WideChar Path[kPathLen]; +} EfiFileDevicePathProtocol; + typedef UInt64 EfiPhysicalAddress; typedef UIntPtr EfiVirtualAddress; @@ -424,4 +431,14 @@ typedef struct EfiIPV6 { #define __EFI_x86_64__ 1 #endif // __x86_64 +enum { + kEFIHwDevicePath = 0x1, + kEFIAcpiDevicePath, + kEFIMessaingDevicePath, + kEFIMediaDevicePath, + kEFIBiosBootPath, + kEFIEndOfPath, + kEFICount, +}; + #endif // __EFI__ diff --git a/Private/FSKit/NewFS.hxx b/Private/FSKit/NewFS.hxx index 75f4e554..bfb6f7c5 100644 --- a/Private/FSKit/NewFS.hxx +++ b/Private/FSKit/NewFS.hxx @@ -21,18 +21,19 @@ #define kIdent "NewFS" #define kPadLen 16 -#define kFilesystemVersion 1 +#define kNewFSVersion 1 enum { - kHardDrive = 0xC0, // Hard Drive - kOpticalDrive = 0x0C, // Blu-Ray/DVD - kMassStorageDevice = 0xCC, // USB - kUnknowmn = 0xFF, // unknown device or unsupported (floppy) + kNewFSHardDrive = 0xC0, // Hard Drive + kNewFSOpticalDrive = 0x0C, // Blu-Ray/DVD + kNewFSMassStorageDevice = 0xCC, // USB + kNewFSUnknowmn = 0xFF, // unknown device or unsupported (floppy) + kNewFSDriveCount = 4, }; struct PACKED NewBootBlock final { - HCore::Char Ident[kIdentLen]; - HCore::Char Shell[kNameLen]; + HCore::WideChar Ident[kIdentLen]; + HCore::WideChar Shell[kNameLen]; HCore::Int64 NumParts; HCore::Int64 FreeSectors; @@ -45,7 +46,7 @@ struct PACKED NewBootBlock final { HCore::Lba FirstPartBlock; HCore::Lba LastPartBlock; - HCore::Char Pad[kPadLen]; + HCore::WideChar Pad[kPadLen]; }; #define kFlagDeleted 0xF0 @@ -55,9 +56,10 @@ struct PACKED NewBootBlock final { #define kKindCatalog 1 #define kKindDirectory 2 #define kKindSymlink 3 +#define kKindPartition 4 struct PACKED NewCatalog final { - HCore::Char Name[kNameLen]; + HCore::WideChar Name[kNameLen]; HCore::Int32 Flags; HCore::Int32 Kind; @@ -91,8 +93,8 @@ struct PACKED NewFork final { #define kPartLen 32 struct PACKED NewPartitionBlock final { - HCore::Char PartitionName[kPartLen]; - HCore::Char JsonPath[kConfigLen]; + HCore::WideChar Ident[kIdentLen]; + HCore::WideChar PartitionName[kPartLen]; HCore::Int32 Flags; HCore::Int32 Kind; @@ -184,8 +186,7 @@ class MeFilesystemHelper final { }; } // namespace HCore -#define kNewFSAddressAsLba 5 -#define kNewFSAddressAsCHS 6 +#define kNewFSAddressAsLba 1024 // FSControl() syscall // FSOpen, FSClose, FSWhereAt, FSSetCursor, FSNodeSize, FSWrite, FSRead syscalls diff --git a/Private/NewBoot/BootKit/Arch/ATA.hxx b/Private/NewBoot/BootKit/Arch/ATA.hxx index 5c42237a..8b25a125 100644 --- a/Private/NewBoot/BootKit/Arch/ATA.hxx +++ b/Private/NewBoot/BootKit/Arch/ATA.hxx @@ -133,7 +133,7 @@ class BATADevice final { struct ATATraits final { SizeT mBase{1024}; UInt16 mBus{kPrimary}; - Boolean mMaster{false}; + Boolean mMaster{true}; }; operator bool() { return ATAIsDetected(); } @@ -154,3 +154,5 @@ enum { kATADeviceSATA_PI, kATADeviceCount, }; + +#define kATASectorSz 512 diff --git a/Private/NewBoot/BootKit/BootKit.hxx b/Private/NewBoot/BootKit/BootKit.hxx index 70519aba..b0dbccd5 100644 --- a/Private/NewBoot/BootKit/BootKit.hxx +++ b/Private/NewBoot/BootKit/BootKit.hxx @@ -48,6 +48,8 @@ class BTextWriter final { BTextWriter(const BTextWriter &) = default; }; +HCore::SizeT BCopyMem(CharacterType *dest, CharacterType *src, + const HCore::SizeT len); HCore::SizeT BStrLen(const CharacterType *ptr); HCore::SizeT BSetMem(CharacterType *src, const CharacterType byte, const HCore::SizeT len); @@ -80,8 +82,7 @@ class BFileReader final { private: Int32 mErrorCode{kOperationOkay}; - CharacterType mPath[255]; - BATADevice mDevice; + CharacterType mPath[kPathLen]; }; /***********************************************************************************/ diff --git a/Private/NewBoot/Source/HEL/AMD64/ATA.cxx b/Private/NewBoot/Source/HEL/AMD64/ATA.cxx index 4f1b3171..c289bcf5 100644 --- a/Private/NewBoot/Source/HEL/AMD64/ATA.cxx +++ b/Private/NewBoot/Source/HEL/AMD64/ATA.cxx @@ -114,9 +114,7 @@ Void ATAReadLba(UInt32 Lba, UInt8 Bus, Boolean Master, CharacterType* Buf, ATAPoll(IO); - for (SizeT index = 0UL; index < 256; ++index) { - Buf[index + Offset] = In16(IO + ATA_REG_DATA); - } + Buf[Offset] = In16(IO + ATA_REG_DATA); ATAWait(IO); } @@ -140,13 +138,13 @@ Void ATAWriteLba(UInt32 Lba, UInt8 Bus, Boolean Master, wchar_t* Buf, ATAPoll(IO); - for (SizeT index = 0UL; index < 256; ++index) { - Out16(IO + ATA_REG_DATA, Buf[index + Offset]); - } + Out16(IO + ATA_REG_DATA, Buf[Offset]); ATAWait(IO); } +Boolean ATAIsDetected(Void) { return kATADetected; } + /*** * * @@ -155,10 +153,8 @@ Void ATAWriteLba(UInt32 Lba, UInt8 Bus, Boolean Master, wchar_t* Buf, * */ -Boolean ATAIsDetected(Void) { return kATADetected; } - /** - * @brief Init ATA driver. + * @brief ATA Device constructor. * @param void none. */ BATADevice::BATADevice() noexcept { @@ -189,13 +185,9 @@ BATADevice& BATADevice::Read(CharacterType* Buf, const SizeT& Sz) { if (!Buf || Sz < 1) return *this; - SizeT Off = 0; - for (SizeT i = 0UL; i < Sz; ++i) { ATAReadLba(this->Leak().mBase + i, this->Leak().mBus, this->Leak().mMaster, - Buf, Off); - - Off += 512; + Buf, i); } return *this; @@ -217,7 +209,7 @@ BATADevice& BATADevice::Write(CharacterType* Buf, const SizeT& Sz) { ATAWriteLba(this->Leak().mBase + i, this->Leak().mBus, this->Leak().mMaster, Buf, Off); - Off += 512; + Off += kATASectorSz; } return *this; diff --git a/Private/NewBoot/Source/HEL/AMD64/BootKit.cxx b/Private/NewBoot/Source/HEL/AMD64/BootKit.cxx index 99f8d41b..600a8fcc 100644 --- a/Private/NewBoot/Source/HEL/AMD64/BootKit.cxx +++ b/Private/NewBoot/Source/HEL/AMD64/BootKit.cxx @@ -9,10 +9,27 @@ #include #include +#include /// bugs 0 +///////////////////////////////////////////////////////////////////////////////////////////////////////// + +HCore::SizeT BCopyMem(CharacterType *dest, CharacterType *src, + const HCore::SizeT len) { + if (!dest || !src) return 0; + + SizeT index = 0UL; + for (; index < len; ++index) { + dest[index] = src[index]; + } + + return index; +} + HCore::SizeT BStrLen(const CharacterType *ptr) { + if (!ptr) return 0; + HCore::SizeT cnt = 0; while (*ptr != (CharacterType)0) { @@ -23,12 +40,10 @@ HCore::SizeT BStrLen(const CharacterType *ptr) { return cnt; } -/** - @biref set memory -*/ - HCore::SizeT BSetMem(CharacterType *src, const CharacterType byte, const HCore::SizeT len) { + if (!src) return 0; + HCore::SizeT cnt = 0UL; while (*src != 0) { @@ -43,9 +58,8 @@ HCore::SizeT BSetMem(CharacterType *src, const CharacterType byte, return cnt; } -/** -@brief puts wrapper over VGA. -*/ +///////////////////////////////////////////////////////////////////////////////////////////////////////// + BTextWriter &BTextWriter::WriteString(const CharacterType *str) { if (*str == 0 || !str) return *this; @@ -66,6 +80,9 @@ BTextWriter &BTextWriter::WriteCharacter(CharacterType c) { return *this; } +///////////////////////////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////////////////////////// + /*** @brief File Reader constructor. */ @@ -89,5 +106,14 @@ HCore::VoidPtr BFileReader::ReadAll() { .WriteString(mPath) .WriteString(L" *** \r\n"); + EfiFileDevicePathProtocol loadFile{0}; + loadFile.LengthData[0] = 0xFF; + loadFile.LengthData[1] = 0; + + loadFile.Type = kEFIMediaDevicePath; + loadFile.SubType = 0; // from all drives. + + BCopyMem(loadFile.Path, mPath, kPathLen); + return nullptr; } diff --git a/Private/NewBoot/Source/HEL/AMD64/Entrypoint.cxx b/Private/NewBoot/Source/HEL/AMD64/Entrypoint.cxx index 69f235c4..8dfd7a71 100644 --- a/Private/NewBoot/Source/HEL/AMD64/Entrypoint.cxx +++ b/Private/NewBoot/Source/HEL/AMD64/Entrypoint.cxx @@ -7,6 +7,7 @@ * ======================================================== */ +#include "NewKit/Defines.hpp" #define __BOOTLOADER__ 1 #include @@ -33,6 +34,8 @@ EFI_EXTERN_C int EfiMain(EfiHandlePtr ImageHandle, KeRuntimeStop(L"HCoreLdr_NoSuchKernel", L"Couldn't find HCoreKrnl.exe! Aborting..."); + writer.WriteString(L"HCoreLdr: Running HCoreKrnl.exe...\r\n"); + EFI::ExitBootServices(SystemTable, mapKey, ImageHandle); EFI::Stop(); diff --git a/Private/NewBoot/Source/makefile b/Private/NewBoot/Source/makefile index 063fa42a..0f679772 100644 --- a/Private/NewBoot/Source/makefile +++ b/Private/NewBoot/Source/makefile @@ -17,6 +17,7 @@ bootloader-amd64: $(CC_GNU) $(FLAG_GNU) HEL/AMD64/*.cxx $(LD_GNU) *.o -e efi_main -filealign:16 -shared --subsystem=10 -ffreestanding -o HCoreLdr.exe cp HCoreLdr.exe CDROM/EFI/BOOT/BOOTX64.EFI + cp ../../HCoreKrnl.exe CDROM/EFI/BOOT/HCoreKrnl.exe .PHONY: run-efi-debug run-efi-debug: -- cgit v1.2.3 From 167ef193e25aa58e962620558b8e2685cbded476 Mon Sep 17 00:00:00 2001 From: Amlal El Mahrouss Date: Fri, 2 Feb 2024 12:37:36 +0100 Subject: NewBoot/Kernel: Finishing Bootloader and protocol. Signed-off-by: Amlal El Mahrouss --- Private/EFIKit/BootProtocol.hxx | 80 ++++++++ Private/EFIKit/EPM.hxx | 6 +- Private/NewBoot/BootKit/Arch/ATA.hxx | 1 + Private/NewBoot/BootKit/EPM.hxx | 2 +- Private/NewBoot/BootKit/Protocol.hxx | 58 +----- Private/NewBoot/Source/HEL/AMD64/AMD64-ATA.cxx | 222 +++++++++++++++++++++ Private/NewBoot/Source/HEL/AMD64/AMD64-BootKit.cxx | 119 +++++++++++ Private/NewBoot/Source/HEL/AMD64/AMD64-Main.cxx | 42 ++++ .../NewBoot/Source/HEL/AMD64/AMD64-Platform.cxx | 32 +++ Private/NewBoot/Source/HEL/AMD64/ATA.cxx | 222 --------------------- Private/NewBoot/Source/HEL/AMD64/BootKit.cxx | 119 ----------- Private/NewBoot/Source/HEL/AMD64/Entrypoint.cxx | 43 ---- Private/NewBoot/Source/HEL/AMD64/Platform.cxx | 30 --- Private/Source/RuntimeMain.cxx | 8 +- 14 files changed, 506 insertions(+), 478 deletions(-) create mode 100644 Private/EFIKit/BootProtocol.hxx create mode 100644 Private/NewBoot/Source/HEL/AMD64/AMD64-ATA.cxx create mode 100644 Private/NewBoot/Source/HEL/AMD64/AMD64-BootKit.cxx create mode 100644 Private/NewBoot/Source/HEL/AMD64/AMD64-Main.cxx create mode 100644 Private/NewBoot/Source/HEL/AMD64/AMD64-Platform.cxx delete mode 100644 Private/NewBoot/Source/HEL/AMD64/ATA.cxx delete mode 100644 Private/NewBoot/Source/HEL/AMD64/BootKit.cxx delete mode 100644 Private/NewBoot/Source/HEL/AMD64/Entrypoint.cxx delete mode 100644 Private/NewBoot/Source/HEL/AMD64/Platform.cxx diff --git a/Private/EFIKit/BootProtocol.hxx b/Private/EFIKit/BootProtocol.hxx new file mode 100644 index 00000000..2978cfed --- /dev/null +++ b/Private/EFIKit/BootProtocol.hxx @@ -0,0 +1,80 @@ +/* + * ======================================================== + * + * NewBoot + * Copyright Mahrouss Logic, all rights reserved. + * + * ======================================================== + */ + +/** + * @file BootProtocol.hxx + * @author Amlal El Mahrouss (amlalelmahrouss@icloud.com) + * @brief Handover protocol. + * @version 0.1 + * @date 2024-02-02 + * + * @copyright Copyright (c) 2024, Mahrouss Logic + * + */ + +#pragma once + +#include + +/* useful macros */ + +#define kHandoverMagic 0xBAD55 + +#define kBaseHandoverStruct 0x80000000 +#define kHandoverStructSz sizeof(HEL::HandoverHeader) + +namespace HCore::HEL { +/** + @brief the kind of executable we're loading. +*/ +enum { + kTypeKernel = 100, + kTypeKernelDriver = 101, + kTypeRsrc = 102, + kTypeCount = 3, +}; + +/** + @brief The executable architecture. +*/ + +enum { + kArchAmd64 = 122, + kArchCount = 2, +}; + +/** +@brief The first struct that we read when inspecting The executable +it tells us more about it and IS format independent. +*/ +struct __attribute__((packed)) HandoverHeader final { + Int32 f_TargetMagic; + Int32 f_TargetType; + Int32 f_TargetArch; + UIntPtr f_TargetStartAddress; +}; + +struct HandoverInformationHeader { + HandoverHeader* f_Header; + voidPtr f_VirtualStart; + SizeT f_VirtualSize; + voidPtr f_PhysicalStart; + SizeT f_PhysicalSize; + Char f_FirmwareVendorName[32]; + SizeT f_FirmwareVendorLen; + voidPtr f_RsdPtr; + voidPtr f_SmBIOS; + voidPtr f_RTC; +}; + +/** + @brief Handover Jump Proc +*/ +typedef UInt64 (*HandoverProc)(HandoverInformationHeader* pHandover); +} // namespace HCore::HEL diff --git a/Private/EFIKit/EPM.hxx b/Private/EFIKit/EPM.hxx index f1cb84ba..8c74d533 100644 --- a/Private/EFIKit/EPM.hxx +++ b/Private/EFIKit/EPM.hxx @@ -16,9 +16,9 @@ #ifndef __PARTITION_MAP__ #define __PARTITION_MAP__ -inline consteval int kUUIDLen = 37; -inline consteval int kNameLen = 32; -inline consteval int kMagicLen = 4; +#define kUUIDLen 37 +#define kNameLen 32 +#define kMagicLen 4 /* the first 512 > x > 1024 bytes of a disk contains this headers. */ diff --git a/Private/NewBoot/BootKit/Arch/ATA.hxx b/Private/NewBoot/BootKit/Arch/ATA.hxx index 8b25a125..4042aaa9 100644 --- a/Private/NewBoot/BootKit/Arch/ATA.hxx +++ b/Private/NewBoot/BootKit/Arch/ATA.hxx @@ -127,6 +127,7 @@ class BATADevice final { }; explicit BATADevice() noexcept; + ~BATADevice() = default; HCORE_COPY_DEFAULT(BATADevice); diff --git a/Private/NewBoot/BootKit/EPM.hxx b/Private/NewBoot/BootKit/EPM.hxx index 803d500c..359eed1b 100644 --- a/Private/NewBoot/BootKit/EPM.hxx +++ b/Private/NewBoot/BootKit/EPM.hxx @@ -9,4 +9,4 @@ #pragma once -#include +#include diff --git a/Private/NewBoot/BootKit/Protocol.hxx b/Private/NewBoot/BootKit/Protocol.hxx index 2f84d0a8..b2725794 100644 --- a/Private/NewBoot/BootKit/Protocol.hxx +++ b/Private/NewBoot/BootKit/Protocol.hxx @@ -9,61 +9,5 @@ #pragma once +#include #include - -/* useful macros */ - -#define kHandoverMagic 0xBAD55 - -#define kBaseHandoverStruct 0x80000000 -#define kHandoverStructSz sizeof(HEL::HandoverHeader) - -namespace HCore::HEL { -/** - @brief the kind of executable we're loading. -*/ -enum { - kTypeKernel = 100, - kTypeKernelDriver = 101, - kTypeRsrc = 102, - kTypeCount = 3, -}; - -/** - @brief The executable architecture. -*/ - -enum { - kArchAmd64 = 122, - kArchCount = 2, -}; - -/** -@brief The first struct that we read when inspecting The executable -it tells us more about it and IS format independent. -*/ -struct __attribute__((packed)) HandoverHeader final { - Int32 f_TargetMagic; - Int32 f_TargetType; - Int32 f_TargetArch; - UIntPtr f_TargetStartAddress; -}; - -struct HandoverInformationHeader { - HandoverHeader* f_Header; - voidPtr f_VirtualStart; - SizeT f_VirtualSize; - voidPtr f_PhysicalStart; - SizeT f_PhysicalSize; - Char f_FirmwareVendorName[32]; - SizeT f_FirmwareVendorLen; - voidPtr f_RsdPtr; - voidPtr f_SmBIOS; - voidPtr f_RTC; -}; - -/** - @brief Handover Jump Proc -*/ -typedef UInt64 (*HandoverProc)(HandoverInformationHeader* pHandover); -} // namespace HCore::HEL diff --git a/Private/NewBoot/Source/HEL/AMD64/AMD64-ATA.cxx b/Private/NewBoot/Source/HEL/AMD64/AMD64-ATA.cxx new file mode 100644 index 00000000..c289bcf5 --- /dev/null +++ b/Private/NewBoot/Source/HEL/AMD64/AMD64-ATA.cxx @@ -0,0 +1,222 @@ +/* + * ======================================================== + * + * NewBoot + * Copyright Mahrouss Logic, all rights reserved. + * + * ======================================================== + */ + +/** + * @file ATA.cxx + * @author Amlal El Mahrouss (amlalelmahrouss@icloud.com) + * @brief ATA driver. + * @version 0.1 + * @date 2024-02-02 + * + * @copyright Copyright (c) 2024 + * + */ + +#include +#include + +/// bugs: 0 + +static Boolean kATADetected = false; +static Int32 kATADeviceType = kATADeviceCount; + +void ATASelect(UInt8 Bus, Boolean isMaster) { + if (Bus == ATA_PRIMARY) + Out8(ATA_PRIMARY_IO + ATA_REG_HDDEVSEL, + isMaster ? ATA_PRIMARY_SEL : ATA_SECONDARY_SEL); + else + Out8(ATA_SECONDARY_IO + ATA_REG_HDDEVSEL, + isMaster ? ATA_PRIMARY_SEL : ATA_SECONDARY_SEL); +} + +Boolean ATAInitDriver(UInt8 Bus, UInt8 Drive, UInt16& OutBus, + Boolean& OutMaster) { + BTextWriter writer; + + UInt16 IO = (Bus == ATA_PRIMARY) ? ATA_PRIMARY_IO : ATA_SECONDARY_IO; + + ATASelect(Bus, Drive); + + Out8(IO + ATA_REG_SEC_COUNT0, 0); + Out8(IO + ATA_REG_LBA0, 0); + Out8(IO + ATA_REG_LBA1, 0); + Out8(IO + ATA_REG_LBA2, 0); + + Out8(IO + ATA_REG_COMMAND, ATA_CMD_IDENTIFY); + + UInt8 status = In8(IO + ATA_REG_STATUS); + + if (status & ATA_SR_ERR) { +#ifdef __DEBUG__ + writer.WriteString(L"HCoreLdr: Init ATA: Bad Drive!\r\n"); +#endif // ifdef __DEBUG__ + return false; + } + + OutBus = (Bus == ATA_PRIMARY) ? BATADevice::kPrimary : BATADevice::kSecondary; + OutMaster = (Bus == ATA_PRIMARY); + + unsigned cl = In16(Bus + ATA_CYL_LOW); /* get the "signature bytes" */ + unsigned ch = In16(Bus + ATA_CYL_HIGH); + + /* differentiate ATA, ATAPI, SATA and SATAPI */ + if (cl == 0x14 && ch == 0xEB) { + writer.WriteString(L"HCoreLdr: PATAPI drive detected.\r\n"); + kATADeviceType = kATADevicePATA_PI; + } + if (cl == 0x69 && ch == 0x96) { + writer.WriteString(L"HCoreLdr: SATAPI drive detected.\r\n"); + kATADeviceType = kATADeviceSATA_PI; + } + if (cl == 0 && ch == 0) { + writer.WriteString(L"HCoreLdr: PATA drive detected.\r\n"); + kATADeviceType = kATADevicePATA; + } + if (cl == 0x3c && ch == 0xc3) { + writer.WriteString(L"HCoreLdr: SATA drive detected.\r\n"); + kATADeviceType = kATADeviceSATA; + } + + return true; +} + +/*** @brief + * This polls the ATA drive. + */ +void ATAWait(UInt16 IO) { + for (int i = 0; i < 4000; i++) In8(IO + ATA_REG_ALT_STATUS); +} + +void ATAPoll(UInt16 IO) { ATAWait(IO); } + +Void ATAReadLba(UInt32 Lba, UInt8 Bus, Boolean Master, CharacterType* Buf, + SizeT Offset) { + UInt16 IO = Bus; + + ATASelect(IO + ATA_REG_HDDEVSEL, + (Master ? ATA_MASTER : ATA_SLAVE) | Lba >> 24 & 0xF); + + ATASelect(IO + 1, 0); + + Out8(IO + ATA_REG_SEC_COUNT0, 1); + + Out8(IO + ATA_REG_LBA0, (UInt8)Lba); + Out8(IO + ATA_REG_LBA1, (UInt8)(Lba >> 8)); + Out8(IO + ATA_REG_LBA2, (UInt8)(Lba >> 16)); + + Out8(IO + ATA_REG_COMMAND, ATA_CMD_READ_PIO); + + ATAPoll(IO); + + Buf[Offset] = In16(IO + ATA_REG_DATA); + + ATAWait(IO); +} + +Void ATAWriteLba(UInt32 Lba, UInt8 Bus, Boolean Master, wchar_t* Buf, + SizeT Offset) { + UInt16 IO = Bus; + + ATASelect(IO + ATA_REG_HDDEVSEL, + (Master ? ATA_MASTER : ATA_SLAVE) | Lba >> 24 & 0xF); + + ATASelect(IO + 1, 0); + + Out8(IO + ATA_REG_SEC_COUNT0, 1); + + Out8(IO + ATA_REG_LBA0, (UInt8)Lba); + Out8(IO + ATA_REG_LBA1, (UInt8)(Lba >> 8)); + Out8(IO + ATA_REG_LBA2, (UInt8)(Lba >> 16)); + + Out8(IO + ATA_REG_COMMAND, ATA_CMD_WRITE_PIO); + + ATAPoll(IO); + + Out16(IO + ATA_REG_DATA, Buf[Offset]); + + ATAWait(IO); +} + +Boolean ATAIsDetected(Void) { return kATADetected; } + +/*** + * + * + * ATA Device class. + * + * + */ + +/** + * @brief ATA Device constructor. + * @param void none. + */ +BATADevice::BATADevice() noexcept { + if (ATAIsDetected()) return; + + if (ATAInitDriver(ATA_PRIMARY, true, this->Leak().mBus, + this->Leak().mMaster) || + ATAInitDriver(ATA_PRIMARY, false, this->Leak().mBus, + this->Leak().mMaster) || + ATAInitDriver(ATA_SECONDARY, true, this->Leak().mBus, + this->Leak().mMaster) || + ATAInitDriver(ATA_SECONDARY, false, this->Leak().mBus, + this->Leak().mMaster)) { + kATADetected = true; + + BTextWriter writer; + writer.WriteString(L"BATADevice::BATADevice: OnLine\r\n"); + } +} + +/** + @brief Read Buf from disk + @param Sz Sector size + @param Buf buffer +*/ +BATADevice& BATADevice::Read(CharacterType* Buf, const SizeT& Sz) { + if (!ATAIsDetected()) return *this; + + if (!Buf || Sz < 1) return *this; + + for (SizeT i = 0UL; i < Sz; ++i) { + ATAReadLba(this->Leak().mBase + i, this->Leak().mBus, this->Leak().mMaster, + Buf, i); + } + + return *this; +} + +/** + @brief Write Buf into disk + @param Sz Sector size + @param Buf buffer +*/ +BATADevice& BATADevice::Write(CharacterType* Buf, const SizeT& Sz) { + if (!ATAIsDetected()) return *this; + + if (!Buf || Sz < 1) return *this; + + SizeT Off = 0UL; + + for (SizeT i = 0UL; i < Sz; ++i) { + ATAWriteLba(this->Leak().mBase + i, this->Leak().mBus, this->Leak().mMaster, + Buf, Off); + + Off += kATASectorSz; + } + + return *this; +} + +/** + * @brief ATA Config getter. + * @return BATADevice::ATATraits& the drive config. + */ +BATADevice::ATATraits& BATADevice::Leak() { return mTraits; } diff --git a/Private/NewBoot/Source/HEL/AMD64/AMD64-BootKit.cxx b/Private/NewBoot/Source/HEL/AMD64/AMD64-BootKit.cxx new file mode 100644 index 00000000..600a8fcc --- /dev/null +++ b/Private/NewBoot/Source/HEL/AMD64/AMD64-BootKit.cxx @@ -0,0 +1,119 @@ +/* + * ======================================================== + * + * NewBoot + * Copyright Mahrouss Logic, all rights reserved. + * + * ======================================================== + */ + +#include +#include +#include + +/// bugs 0 + +///////////////////////////////////////////////////////////////////////////////////////////////////////// + +HCore::SizeT BCopyMem(CharacterType *dest, CharacterType *src, + const HCore::SizeT len) { + if (!dest || !src) return 0; + + SizeT index = 0UL; + for (; index < len; ++index) { + dest[index] = src[index]; + } + + return index; +} + +HCore::SizeT BStrLen(const CharacterType *ptr) { + if (!ptr) return 0; + + HCore::SizeT cnt = 0; + + while (*ptr != (CharacterType)0) { + ++ptr; + ++cnt; + } + + return cnt; +} + +HCore::SizeT BSetMem(CharacterType *src, const CharacterType byte, + const HCore::SizeT len) { + if (!src) return 0; + + HCore::SizeT cnt = 0UL; + + while (*src != 0) { + if (cnt > len) break; + + *src = byte; + ++src; + + ++cnt; + } + + return cnt; +} + +///////////////////////////////////////////////////////////////////////////////////////////////////////// + +BTextWriter &BTextWriter::WriteString(const CharacterType *str) { + if (*str == 0 || !str) return *this; + + ST->ConOut->OutputString(ST->ConOut, str); + + return *this; +} + +/** +@brief putc wrapper over VGA. +*/ +BTextWriter &BTextWriter::WriteCharacter(CharacterType c) { + EfiCharType str[2]; + str[0] = c; + str[1] = 0; + ST->ConOut->OutputString(ST->ConOut, str); + + return *this; +} + +///////////////////////////////////////////////////////////////////////////////////////////////////////// +///////////////////////////////////////////////////////////////////////////////////////////////////////// + +/*** + @brief File Reader constructor. +*/ +BFileReader::BFileReader(const CharacterType *path) { + if (path != nullptr) { + SizeT index = 0UL; + for (; path[index] != L'0'; ++index) { + mPath[index] = path[index]; + } + + mPath[index] = 0; + } +} + +/** +@brief this reads all of the buffer. +*/ +HCore::VoidPtr BFileReader::ReadAll() { + BTextWriter writer; + writer.WriteString(L"*** BFileReader::ReadAll: Reading ") + .WriteString(mPath) + .WriteString(L" *** \r\n"); + + EfiFileDevicePathProtocol loadFile{0}; + loadFile.LengthData[0] = 0xFF; + loadFile.LengthData[1] = 0; + + loadFile.Type = kEFIMediaDevicePath; + loadFile.SubType = 0; // from all drives. + + BCopyMem(loadFile.Path, mPath, kPathLen); + + return nullptr; +} diff --git a/Private/NewBoot/Source/HEL/AMD64/AMD64-Main.cxx b/Private/NewBoot/Source/HEL/AMD64/AMD64-Main.cxx new file mode 100644 index 00000000..256c7feb --- /dev/null +++ b/Private/NewBoot/Source/HEL/AMD64/AMD64-Main.cxx @@ -0,0 +1,42 @@ +/* + * ======================================================== + * + * NewBoot + * Copyright Mahrouss Logic, all rights reserved. + * + * ======================================================== + */ + +#define __BOOTLOADER__ 1 + +#include +#include + +// don't remove EfiGUID, it will call initializer_list! + +EFI_EXTERN_C int EfiMain(EfiHandlePtr ImageHandle, + EfiSystemTable* SystemTable) { + KeInitEFI(SystemTable); + + BTextWriter writer; + + writer.WriteString(L"HCoreLdr: Firmware: ") + .WriteString(SystemTable->FirmwareVendor) + .WriteString(L"\r\n"); + + UInt64 mapKey = 0; + + BFileReader reader(L"\\Root\\System\\HCoreKrnl.exe\0"); + auto blob = reader.ReadAll(); + + if (!blob) + KeRuntimeStop(L"HCoreLdr_NoSuchKernel", + L"Couldn't find HCoreKrnl.exe! Aborting..."); + + writer.WriteString(L"HCoreLdr: Running HCoreKrnl.exe...\r\n"); + + EFI::ExitBootServices(SystemTable, mapKey, ImageHandle); + EFI::Stop(); + + return kEfiOk; +} diff --git a/Private/NewBoot/Source/HEL/AMD64/AMD64-Platform.cxx b/Private/NewBoot/Source/HEL/AMD64/AMD64-Platform.cxx new file mode 100644 index 00000000..663d4bcb --- /dev/null +++ b/Private/NewBoot/Source/HEL/AMD64/AMD64-Platform.cxx @@ -0,0 +1,32 @@ +/* + * ======================================================== + * + * NewBoot + * Copyright Mahrouss Logic, all rights reserved. + * + * ======================================================== + */ + +/* + * + * @file Platform.cxx + * @brief Platform Specific Functions. + * + */ + +#include +#include + +extern "C" void rt_halt() { asm volatile("hlt"); } + +extern "C" void rt_cli() { asm volatile("cli"); } + +extern "C" void rt_sti() { asm volatile("sti"); } + +extern "C" void rt_cld() { asm volatile("cld"); } + +extern "C" void rt_std() { asm volatile("std"); } + +/// @brief Stack check + +extern "C" void ___chkstk_ms(void) {} diff --git a/Private/NewBoot/Source/HEL/AMD64/ATA.cxx b/Private/NewBoot/Source/HEL/AMD64/ATA.cxx deleted file mode 100644 index c289bcf5..00000000 --- a/Private/NewBoot/Source/HEL/AMD64/ATA.cxx +++ /dev/null @@ -1,222 +0,0 @@ -/* - * ======================================================== - * - * NewBoot - * Copyright Mahrouss Logic, all rights reserved. - * - * ======================================================== - */ - -/** - * @file ATA.cxx - * @author Amlal El Mahrouss (amlalelmahrouss@icloud.com) - * @brief ATA driver. - * @version 0.1 - * @date 2024-02-02 - * - * @copyright Copyright (c) 2024 - * - */ - -#include -#include - -/// bugs: 0 - -static Boolean kATADetected = false; -static Int32 kATADeviceType = kATADeviceCount; - -void ATASelect(UInt8 Bus, Boolean isMaster) { - if (Bus == ATA_PRIMARY) - Out8(ATA_PRIMARY_IO + ATA_REG_HDDEVSEL, - isMaster ? ATA_PRIMARY_SEL : ATA_SECONDARY_SEL); - else - Out8(ATA_SECONDARY_IO + ATA_REG_HDDEVSEL, - isMaster ? ATA_PRIMARY_SEL : ATA_SECONDARY_SEL); -} - -Boolean ATAInitDriver(UInt8 Bus, UInt8 Drive, UInt16& OutBus, - Boolean& OutMaster) { - BTextWriter writer; - - UInt16 IO = (Bus == ATA_PRIMARY) ? ATA_PRIMARY_IO : ATA_SECONDARY_IO; - - ATASelect(Bus, Drive); - - Out8(IO + ATA_REG_SEC_COUNT0, 0); - Out8(IO + ATA_REG_LBA0, 0); - Out8(IO + ATA_REG_LBA1, 0); - Out8(IO + ATA_REG_LBA2, 0); - - Out8(IO + ATA_REG_COMMAND, ATA_CMD_IDENTIFY); - - UInt8 status = In8(IO + ATA_REG_STATUS); - - if (status & ATA_SR_ERR) { -#ifdef __DEBUG__ - writer.WriteString(L"HCoreLdr: Init ATA: Bad Drive!\r\n"); -#endif // ifdef __DEBUG__ - return false; - } - - OutBus = (Bus == ATA_PRIMARY) ? BATADevice::kPrimary : BATADevice::kSecondary; - OutMaster = (Bus == ATA_PRIMARY); - - unsigned cl = In16(Bus + ATA_CYL_LOW); /* get the "signature bytes" */ - unsigned ch = In16(Bus + ATA_CYL_HIGH); - - /* differentiate ATA, ATAPI, SATA and SATAPI */ - if (cl == 0x14 && ch == 0xEB) { - writer.WriteString(L"HCoreLdr: PATAPI drive detected.\r\n"); - kATADeviceType = kATADevicePATA_PI; - } - if (cl == 0x69 && ch == 0x96) { - writer.WriteString(L"HCoreLdr: SATAPI drive detected.\r\n"); - kATADeviceType = kATADeviceSATA_PI; - } - if (cl == 0 && ch == 0) { - writer.WriteString(L"HCoreLdr: PATA drive detected.\r\n"); - kATADeviceType = kATADevicePATA; - } - if (cl == 0x3c && ch == 0xc3) { - writer.WriteString(L"HCoreLdr: SATA drive detected.\r\n"); - kATADeviceType = kATADeviceSATA; - } - - return true; -} - -/*** @brief - * This polls the ATA drive. - */ -void ATAWait(UInt16 IO) { - for (int i = 0; i < 4000; i++) In8(IO + ATA_REG_ALT_STATUS); -} - -void ATAPoll(UInt16 IO) { ATAWait(IO); } - -Void ATAReadLba(UInt32 Lba, UInt8 Bus, Boolean Master, CharacterType* Buf, - SizeT Offset) { - UInt16 IO = Bus; - - ATASelect(IO + ATA_REG_HDDEVSEL, - (Master ? ATA_MASTER : ATA_SLAVE) | Lba >> 24 & 0xF); - - ATASelect(IO + 1, 0); - - Out8(IO + ATA_REG_SEC_COUNT0, 1); - - Out8(IO + ATA_REG_LBA0, (UInt8)Lba); - Out8(IO + ATA_REG_LBA1, (UInt8)(Lba >> 8)); - Out8(IO + ATA_REG_LBA2, (UInt8)(Lba >> 16)); - - Out8(IO + ATA_REG_COMMAND, ATA_CMD_READ_PIO); - - ATAPoll(IO); - - Buf[Offset] = In16(IO + ATA_REG_DATA); - - ATAWait(IO); -} - -Void ATAWriteLba(UInt32 Lba, UInt8 Bus, Boolean Master, wchar_t* Buf, - SizeT Offset) { - UInt16 IO = Bus; - - ATASelect(IO + ATA_REG_HDDEVSEL, - (Master ? ATA_MASTER : ATA_SLAVE) | Lba >> 24 & 0xF); - - ATASelect(IO + 1, 0); - - Out8(IO + ATA_REG_SEC_COUNT0, 1); - - Out8(IO + ATA_REG_LBA0, (UInt8)Lba); - Out8(IO + ATA_REG_LBA1, (UInt8)(Lba >> 8)); - Out8(IO + ATA_REG_LBA2, (UInt8)(Lba >> 16)); - - Out8(IO + ATA_REG_COMMAND, ATA_CMD_WRITE_PIO); - - ATAPoll(IO); - - Out16(IO + ATA_REG_DATA, Buf[Offset]); - - ATAWait(IO); -} - -Boolean ATAIsDetected(Void) { return kATADetected; } - -/*** - * - * - * ATA Device class. - * - * - */ - -/** - * @brief ATA Device constructor. - * @param void none. - */ -BATADevice::BATADevice() noexcept { - if (ATAIsDetected()) return; - - if (ATAInitDriver(ATA_PRIMARY, true, this->Leak().mBus, - this->Leak().mMaster) || - ATAInitDriver(ATA_PRIMARY, false, this->Leak().mBus, - this->Leak().mMaster) || - ATAInitDriver(ATA_SECONDARY, true, this->Leak().mBus, - this->Leak().mMaster) || - ATAInitDriver(ATA_SECONDARY, false, this->Leak().mBus, - this->Leak().mMaster)) { - kATADetected = true; - - BTextWriter writer; - writer.WriteString(L"BATADevice::BATADevice: OnLine\r\n"); - } -} - -/** - @brief Read Buf from disk - @param Sz Sector size - @param Buf buffer -*/ -BATADevice& BATADevice::Read(CharacterType* Buf, const SizeT& Sz) { - if (!ATAIsDetected()) return *this; - - if (!Buf || Sz < 1) return *this; - - for (SizeT i = 0UL; i < Sz; ++i) { - ATAReadLba(this->Leak().mBase + i, this->Leak().mBus, this->Leak().mMaster, - Buf, i); - } - - return *this; -} - -/** - @brief Write Buf into disk - @param Sz Sector size - @param Buf buffer -*/ -BATADevice& BATADevice::Write(CharacterType* Buf, const SizeT& Sz) { - if (!ATAIsDetected()) return *this; - - if (!Buf || Sz < 1) return *this; - - SizeT Off = 0UL; - - for (SizeT i = 0UL; i < Sz; ++i) { - ATAWriteLba(this->Leak().mBase + i, this->Leak().mBus, this->Leak().mMaster, - Buf, Off); - - Off += kATASectorSz; - } - - return *this; -} - -/** - * @brief ATA Config getter. - * @return BATADevice::ATATraits& the drive config. - */ -BATADevice::ATATraits& BATADevice::Leak() { return mTraits; } diff --git a/Private/NewBoot/Source/HEL/AMD64/BootKit.cxx b/Private/NewBoot/Source/HEL/AMD64/BootKit.cxx deleted file mode 100644 index 600a8fcc..00000000 --- a/Private/NewBoot/Source/HEL/AMD64/BootKit.cxx +++ /dev/null @@ -1,119 +0,0 @@ -/* - * ======================================================== - * - * NewBoot - * Copyright Mahrouss Logic, all rights reserved. - * - * ======================================================== - */ - -#include -#include -#include - -/// bugs 0 - -///////////////////////////////////////////////////////////////////////////////////////////////////////// - -HCore::SizeT BCopyMem(CharacterType *dest, CharacterType *src, - const HCore::SizeT len) { - if (!dest || !src) return 0; - - SizeT index = 0UL; - for (; index < len; ++index) { - dest[index] = src[index]; - } - - return index; -} - -HCore::SizeT BStrLen(const CharacterType *ptr) { - if (!ptr) return 0; - - HCore::SizeT cnt = 0; - - while (*ptr != (CharacterType)0) { - ++ptr; - ++cnt; - } - - return cnt; -} - -HCore::SizeT BSetMem(CharacterType *src, const CharacterType byte, - const HCore::SizeT len) { - if (!src) return 0; - - HCore::SizeT cnt = 0UL; - - while (*src != 0) { - if (cnt > len) break; - - *src = byte; - ++src; - - ++cnt; - } - - return cnt; -} - -///////////////////////////////////////////////////////////////////////////////////////////////////////// - -BTextWriter &BTextWriter::WriteString(const CharacterType *str) { - if (*str == 0 || !str) return *this; - - ST->ConOut->OutputString(ST->ConOut, str); - - return *this; -} - -/** -@brief putc wrapper over VGA. -*/ -BTextWriter &BTextWriter::WriteCharacter(CharacterType c) { - EfiCharType str[2]; - str[0] = c; - str[1] = 0; - ST->ConOut->OutputString(ST->ConOut, str); - - return *this; -} - -///////////////////////////////////////////////////////////////////////////////////////////////////////// -///////////////////////////////////////////////////////////////////////////////////////////////////////// - -/*** - @brief File Reader constructor. -*/ -BFileReader::BFileReader(const CharacterType *path) { - if (path != nullptr) { - SizeT index = 0UL; - for (; path[index] != L'0'; ++index) { - mPath[index] = path[index]; - } - - mPath[index] = 0; - } -} - -/** -@brief this reads all of the buffer. -*/ -HCore::VoidPtr BFileReader::ReadAll() { - BTextWriter writer; - writer.WriteString(L"*** BFileReader::ReadAll: Reading ") - .WriteString(mPath) - .WriteString(L" *** \r\n"); - - EfiFileDevicePathProtocol loadFile{0}; - loadFile.LengthData[0] = 0xFF; - loadFile.LengthData[1] = 0; - - loadFile.Type = kEFIMediaDevicePath; - loadFile.SubType = 0; // from all drives. - - BCopyMem(loadFile.Path, mPath, kPathLen); - - return nullptr; -} diff --git a/Private/NewBoot/Source/HEL/AMD64/Entrypoint.cxx b/Private/NewBoot/Source/HEL/AMD64/Entrypoint.cxx deleted file mode 100644 index 8dfd7a71..00000000 --- a/Private/NewBoot/Source/HEL/AMD64/Entrypoint.cxx +++ /dev/null @@ -1,43 +0,0 @@ -/* - * ======================================================== - * - * NewBoot - * Copyright Mahrouss Logic, all rights reserved. - * - * ======================================================== - */ - -#include "NewKit/Defines.hpp" -#define __BOOTLOADER__ 1 - -#include -#include - -// don't remove EfiGUID, it will call initializer_list! - -EFI_EXTERN_C int EfiMain(EfiHandlePtr ImageHandle, - EfiSystemTable* SystemTable) { - KeInitEFI(SystemTable); - - BTextWriter writer; - - writer.WriteString(L"HCoreLdr: Firmware: ") - .WriteString(SystemTable->FirmwareVendor) - .WriteString(L"\r\n"); - - UInt64 mapKey = 0; - - BFileReader reader(L"\\Root\\System\\HCoreKrnl.exe\0"); - auto blob = reader.ReadAll(); - - if (!blob) - KeRuntimeStop(L"HCoreLdr_NoSuchKernel", - L"Couldn't find HCoreKrnl.exe! Aborting..."); - - writer.WriteString(L"HCoreLdr: Running HCoreKrnl.exe...\r\n"); - - EFI::ExitBootServices(SystemTable, mapKey, ImageHandle); - EFI::Stop(); - - return kEfiOk; -} diff --git a/Private/NewBoot/Source/HEL/AMD64/Platform.cxx b/Private/NewBoot/Source/HEL/AMD64/Platform.cxx deleted file mode 100644 index f92de33b..00000000 --- a/Private/NewBoot/Source/HEL/AMD64/Platform.cxx +++ /dev/null @@ -1,30 +0,0 @@ -/* - * ======================================================== - * - * NewBoot - * Copyright Mahrouss Logic, all rights reserved. - * - * ======================================================== - */ - -/* - * - * @file Platform.cxx - * @brief Platform Specific Functions. - * - */ - -#include -#include - -extern "C" void rt_halt() { asm volatile("hlt"); } - -extern "C" void rt_cli() { asm volatile("cli"); } - -extern "C" void rt_sti() { asm volatile("sti"); } - -extern "C" void rt_cld() { asm volatile("cld"); } - -extern "C" void rt_std() { asm volatile("std"); } - -extern "C" void ___chkstk_ms(void) { EFI::Stop(); } diff --git a/Private/Source/RuntimeMain.cxx b/Private/Source/RuntimeMain.cxx index 02a7ce09..f103e98c 100644 --- a/Private/Source/RuntimeMain.cxx +++ b/Private/Source/RuntimeMain.cxx @@ -8,8 +8,9 @@ */ #include -#include +#include #include +#include #include #include #include @@ -18,7 +19,8 @@ extern "C" void (*__SYSTEM_FINI)(); extern "C" void (**__SYSTEM_INIT)(); -extern "C" void RuntimeMain() { +extern "C" void RuntimeMain( + HCore::HEL::HandoverInformationHeader* HandoverHeader) { /// Init C++ globals for (HCore::SizeT index_init = 0UL; __SYSTEM_INIT[index_init] != __SYSTEM_FINI; ++index_init) { @@ -31,7 +33,7 @@ extern "C" void RuntimeMain() { MUST_PASS(HCore::ke_init_hal()); HCore::IFilesystemManager::Mount(new HCore::NewFilesystemManager()); - HCore::PEFLoader img("/System/Shell.exe"); + HCore::PEFLoader img("/System/HCoreShell.exe"); if (!HCore::Utils::execute_from_image(img)) { HCore::ke_stop(RUNTIME_CHECK_BOOTSTRAP); -- cgit v1.2.3