#OBOS (not vibecoded)

1 messages Β· Page 6 of 1

flint idol
#

I'd just set it to some arbitrary value

real pecan
#

because what u do is cpu mmu emulation

#

its not productive

flint idol
#

After fighting with KASAN to not crash or be slow af

#

I finally get a violation

#
ASAN Violation at ffffffff8001a276 while trying to read 8 bytes from 0x0000000000000000.```
#

While initializing the scheduler

#

But of course that's in the VMM

flint idol
#

I've been checking if the address that's trying to be accessed was allocated by the kernel allocator

#

then if it was

#

it would check if the address falls into the shadow space after the node

#

It could've easily been a memcmp to check if the address is poisoned (all n bytes are set to 0xA5)

#

Upon doing that

#

I triple fault

#

Bug with memcmp?

#

As you can see my kernel is very stable

#

oops:

mov al, dil
mov rcx, rdx
repe scasb
sete al```
#

spot the mistake?

#

for reference this is the signature:

#

bool memcmp(void*, uint8_t against, size_t count)

sharp pike
#

that's not the right signature

#

fix that

flint idol
#

No

#

That's my own special memcmp

#

I have another for comparing memory blocks

sharp pike
#

if the symbol is called memcmp then you should make it work like the standard memcmp

#

because the compiler expects that

flint idol
#

The symbol is mangled

sharp pike
#

ah

#

then nvm

flint idol
#

I should probably fix that though

#

I only have mangled versions of memcmp, memcpy, and memset

flint idol
#

Well some vmm node is getting zeroed or is never getting initialized

#

Because it is zeroed I can't even find out what address it's supposed to point to

#

That is because the VMM is reallocating pages again

#

Whoopsie...

#

It was because of the interdependency between the allocator and VMM

#

The VMM was requesting a page node

#

But the allocator needed more room

#

and the conditions were just right in this case for the VMM to choose the same base address

#

for the allocator

#

The fix to this is

#

idk

#

I can only think of temporarily adding the node passed to AppendPageNode

#

So it doesn't get reallocated

#

and then removing it once the node on the heap is added

#

which is pretty hacky imo

#

The problem is deeper

#

It occurs before the node can be appended in the vmm's allocate function

#

ie. in it's initialization

#

I described how my VMM finds addresses somewhere in #1230349543623757845

#

So the only solution is to rather change that

#

or remove the interdependency

flint idol
#

So that this becomes impossible to happen

#

I'll just reserve a shit ton of memory for the allocator

#

and commit parts of it whenever the allocator needs to grow

#

Anyway sounds like a problem for tomorrow

flint idol
#

I thought of another idea to fix the bug. That is to remove the interdependency entirely. One way I thought of doing that is using the hhdm along with pages from the PMM. Although since continuous physical pages are inefficient to get, this will only be done for the vmm's allocator.

#

The normal kernel allocator should be able to keep using the vmm to allocate new regions

flint idol
#

That'd be a fun bug to track down

flint idol
#

I just found a very dumb memory corruption bug

#

Well not very dumb

#

More like an oversight

#

I was initially using the regular new/delete operator pair for allocating/freeing page nodes and page descriptors

#

When I gave the VMM its own allocator, I just overloaded the new operator for page_node and page_descriptor

#

But I didn't overload the delete operator

#

Causing all VMM frees to go through the general kernel allocator (not good)

#

Sometimes I'm genuinely surprised how bugs like this go untriggered for so long

#

Ok it works now

#

ie. boots with no problem

#

Just a "bit" slower

#

I should fix my UB that UBSan detects

#

Then I can fulfill [this](#1217009725711847465 message)

flint idol
#

I don't see how it's the language's fault

#

In this case

vernal chasm
#

You wouldn't use new/delete

flint idol
#

Then I would use kmalloc/kfree

#

Literally the same thing except I pass the size

vernal chasm
flint idol
#

No it wouldn't if I went with the same design that my kernel uses

#

actually nvm

lean glen
#

You can literally pass an allocator to new

#

If you want

flint idol
#

I enabled KASAN in uACPI's static library and there is coincidentally a table which contains KASAN's value that it uses for poisoning

#

Reporting a KASAN violation

#

Seems like I need to use a more random value

flint idol
#

the value 0xA5 seems to come up in ACPI Tables quite often

#

I just found a USB stick with a very, very early revision of my first kernel

#

In it's protected mode, vga text mode glory

#

Time to see what it does

#

"Hello, world!"
Triple fault

#

I also found another

#

That used some crappy acpi shutdown function on the osdev wiki

vernal chasm
flint idol
#

I just found a usb stick with my 2nd kernel

#

Time to see what it does

#

"Entering rescue mode"
"grub rescue> "

flint idol
#

KASAN+my kernel on my laptop = slow af

#

Until it finally reaches the test driver

#

where it finishes

#

and asan reports an asan violation

#

the stack trace is pretty goofy

#

the first stack trace entry is asan_report

#

then panicVariadic

#

then reportKASANViolation

#

Letting the kernel panic through the debugger

#

Reports stack corruption and not kasan violation

#

I think I should poison the stack through KASAN

#

That might catch uninitialized variable access

#

Instead it:

Attempt to call LowerIRQL() with the irql 15, which is greater than the current IRQL, 0.```
#

That doesn't happen second reboot

#

or after fixing a bug with a use of uninitialized variable

flint idol
#

I have found a scheduler bug

#

Where if the kernel main thread exits

#

ie. it gets terminated

#

The scheduler will find a way to switch to the part of KernelArchInit that checks for the watchdog timer

#

Of course, because why not, the code gets run as the BSP's idle task

flint idol
#
Attempt to call LowerIRQL() with the irql 15, which is greater than the current IRQL, 15.```
flint idol
#

Solution: Remove stack poisoning

#

Anyway I may or may not have 22 outgoing commits

#

But this time I tried to only keep a couple changes per commit

#

Instead of one fat commit for changes to everywhere

#

Between current commit and master:

54 files changed, 1252 insertions(+), 341 deletions(-)```
flint idol
#

I've merged that branch

#

and also merged the vfs branch

#

then I made it again

#

so it can have the bug fixes

#

and other changes

#

Anyway, what was I doing before this

#

Ah yes VFS

#

I guess I'll have some struct

#

that stores an opened file's context

#

ie. the offset

#

how it was opened

#

etc.

#

Then I'll have some member functions

#

that initialize it (open a file)

#

read from the file

#

write to it

#

close it

#

whatever else a file descriptor does

flint idol
#

I have found a scheduler bug

#

I just don't know why it happens

#

Nor do I want to look into why it happens

#

But it doesn't happen all the time

#

Time to use UBSan I guess

ashen goblet
#

what does it do

flint idol
#

what the bug?

#

causes a GPF

ashen goblet
#

interesting

flint idol
#

(of course as I turn on UBSan the bug disappears)

#

I'm sure it'll come back

#

it just happened

#

with no UBSan violations...

#

Time to turn on KASAN

#

With KASAN, I get stack corruption

#

i.e., it causes the stack corruption

#

It reports the stack corruption in scheduler::yield

#

All I wanted was an implementation of KASAN, is that so hard to ask for?

#

Why does it have to do all this

flint idol
#

Very goofy stack trace:

Stack trace:
        0xffffffff800344eb: _ZN4obos6logger9panicImplEPvbPKcP13__va_list_tag+378
        0xffffffff8003430b: _ZN4obos6logger20reportKASANViolationEPKcz+0
        0xffffffff800342d9: _ZN4obos6logger13panicVariadicEPvPKcP13__va_list_tag+0
        0xffffffff80050b14: _ZN4obos3vfs11string_viewC1EPKc+0
        0xffffffff8004f296: _ZN4obos9scheduler5yieldEv+370```
#

let's see what it becomes on a reboot

#

it becomes nothing

#

These bugs are making me want to rewrite my kernel, although I must resist

flint idol
#

The stack seems to be getting fucked by my scheduler

#

Somehow

#

Time for more debugging on how

#

Specifically, the yield() function

limber wave
flint idol
#

My kernel should be used as a test case for GDB

#

That'd probably not even be that bad of a way of testing it

#

Considering how much bugs I produce

real pecan
#

Lol

flint idol
#

maybe adding a cli in the YieldThread function (which saves thread context and calls the scheduler) will help

#

Well that certainly does something

#

Whether that thing is a good thing or not, idk

#

I'll wait to see if KASAN reports anything or if anything shits itself

#

Well

#

nothing shat itself

#

but that's probably a lucky run

#

hmmm

#

another reboot worked

#

I'll try again...

#

three reboots and not one fails with magical memory corruption

#

I'll rebuild

#

then run qemu

#

and see what happens

#

It works

#

Time to consider this bug fixed until not fixed

#

KASAN significantly slows down the kernel

real pecan
#

Do u even understand why that was a bug

flint idol
#

So I'll disable that until I need it

#

Nope

real pecan
#

Perhaps u just made the bug more unlikely to trigger

flint idol
#

Well if a cli made it not get triggered over 4 reboots

#

that probably means YieldThread got preempted by an interrupt

#

(similar behaviour also happens when I try to get my IRQs preemptible)

#

I do use ISTs for some interrupts in my kernel

#

Which uses the CPU temp stack

#

oh dear

#

so does the scheduler

#

maybe that was my previous kernel and I'm misremembering

#

it was my previous kernel that did that

#

oops

#

double faults use ist 2

#

but that's never initialized

#

No IRQ uses IST stacks

#

only certain exceptions

#

I'm going to remove the cli

#

and disable ISTs

#

for all interrupts

#

and I'll see what happens

#

triple fault

#

oh yeah

#

I remember now

#

I need to map all stacks as no demand page

#

after fixing that, everything goes to shit

#

ISTs aren't the root cause

#

Maybe ISRs somehow leave the stack in a goofy state

#

Doubt it though

#

Well I would've noticed that a long time ago

#

I don't know why this bug happens

#

all I know is disabling interrupts in YieldThread "fixes" it

real pecan
#

Shouldn't matter

flint idol
#

Maybe it has something to do with KASAN being disabled in only some functions the scheduler depends on

#

idk how that would affect anything though

flint idol
#

I got the VFS's look for index node function working

#

I just need to vigorlessly test it

#

(with three available nodes for it to test)

#

I'll also do goofy stuff with the path to test if parsing the path works

#

like putting many slashes beside each other for no reason

#

Parsing the path seems to work

#

I'll try paths relative to the root passed to LookForIndexNode

#

see what that does

#

doesn't work

#

It's a problem with parsing the path

#

Fixed it

#

I'll also try adding ../ to the path and see if that gets messed up

#

oops

#

infinite recursion

#

I fixed it

#

I'll try adding ./ to see if that works

#

page fault

flint idol
#

ok I fixed it

#

I'll try to look off of a node

#

that works

flint idol
#

I saw a gdb option for instrumenting functions, and I thought it would be nice if I could implement it.

#

To see what functions take the longest

#

which get called the most

#

etc.

#

It's only two functions I need to implement

#

and they can technically be pretty simple

flint idol
#

The downside is that everything related to the VMM and allocator now needs to be marked as no_instrument_function or everything will go to shit because of recursion (the function for recording function calls may or may not depend on the allocator)

#

Which means not the allocator nor the VMM can be instrumented (at least not in kernel mode)

#

Although anything else can be

flint idol
#

Even so much as an exception handler

#

or the IRQL functions

#

or spin lock (although tbf that shouldn't be instrumented anyway)

#

I feel bad for anyone who wanted to port OBOS (me in the future)

#

There will be so much forgotten quirks

#

Like this

#

That will pop out of no where

#

Even one liner functions in the VMM have to be marked

#

as no instrument

#

because there is the slight off-chance that infinite recursion happens

#

Now luckily for me the VMM nor the allocator really depend on anything else in the kernel

#

Ok I'm done a very barebones implementation

#

Time to see whether it shits itself (it will)

#

You know what this is too unstable

flint idol
#

I might rewrite the kernel (again)

#

note how "might" is emphasized

#

The reasons, well, look above this message

#

Mainly kernel instability

#

But that can always be fixed, my previous kernel at one point had similar problems

#

Except none of which were with the allocator

#

Mainly scheduler instability

flint idol
#

The allocator would be ported if I rewrite

unkempt pawn
#

Oh man how many rewrites have been done already lol

flint idol
#

This is the 4th revision

#

So the next would be the 5th

flint idol
#

Me programming OBOS

devout niche
# flint idol

what is it that you're worried you've miscoded/misarchitected?

flint idol
#

Well for one I messed up IRQs a bit

#

I wanted them to be preemptible

#

It's not really too late for that

#

It's just a lot of debugging because when I tried the kernel shat itself

#

The kernel, at least in the early stages of boot, is really fragile

flint idol
#

I shall rewrite the kernel (starting in a couple hours)

#

I'll merge VFS with master then rename master to some old_code

#

This time, I'll rewrite in C

limber wave
#

C? What language werr you using before?

flint idol
#

C++

limber wave
#

I think you probably were not using C++ features anyways, but if that's the case the rewrite will be much easier anyways

ashen goblet
#

Can I place a bet on how many rewrites until you stop doing osdev

limber wave
#

would not it be better to take your time and slowly build up working code instead of slowly building up bugs? That's what you say, but also what you should really do

#

you will just waste your time otherwise

flint idol
#

Yeah that's what I'll do this time

#

I'm going to try and get KASAN and UBSAN asap

#

to prevent those bugs

limber wave
flint idol
#

I'll test everything

#

vigorously

#

This rewrite might take longer to get to around the same state as this kernel

#

But at least it won't be buggy af

ashen goblet
#

first uncursed version of obos incoming?

flint idol
#

the third kernel wasn't cursed

limber wave
limber wave
#

nothing to worry about (I was not even here)

flint idol
#

No it was fine and relatively stable

#

It was able to get to a point where I could port a libc

#

until someone (hyenasky) saw my VMM and made me want to rewrite

#

I also decided some parts were designed poorly

#

He was banned in this server

limber wave
#

you could use the best of all the rewrites

flint idol
#

But you can find him elsewhere

limber wave
#

do you usually test your code in a controlled environment?

flint idol
#

Nope

limber wave
#

why?

flint idol
#

Too tempting to just go on and use the feature

limber wave
flint idol
#

nope

limber wave
#

which feature?

flint idol
#

most

#

scheduler was completely untested when I was done with it

limber wave
#

and that is the root of all your problems

flint idol
#

VMM was very lightly tested

#

which is why the allocator bug came up

#

It was a bug in vmm::Free which could've been fixed if I tested

limber wave
#

in contrast

flint idol
#

If anyone needs to test their debugger, you can use the fourth kernel

limber wave
#

but you couls have continued from there, or you can roll back now

#

to a certain degree

flint idol
#

btw I still haven't started the rewrite

#

I'm at school

#

I can't just start a rewrite in the middle of class

limber wave
#

that means you can still think on what is the best way of doing it before heading in

limber wave
flint idol
#

oh btw for this rewrite I'm using the hyper bootloader

limber wave
#

(never heard of it)

flint idol
#

nah

#

I just want to

#

Hyper is @real pecan's bootloader

real pecan
#

Good luck with the rewrite

flint idol
#

ty

limber wave
#

yes, good luck!

devout niche
#

yes

#

best wishes

thick jolt
#

hey guys

thick jolt
thick jolt
#

😎

#

C is key!

#

actually will probs be easier cause no oop!

#

😎 😎

#

man i love C

ashen goblet
thick jolt
ashen goblet
#

C++ is more than c with classes

thick jolt
#

yea and i dont like classes

weary hound
#

then don't use them?

thick jolt
weary hound
#

waiting for you to reinvent a vtable with a struct of function pointers

#

:^)

thick jolt
#

my brain just went πŸ’₯

empty kernel
flint idol
#

Yes.

#

hopefully this one

#

but that's what I've said for each other kernel, so idk

#

I've almost been doing osdev for a year

#

which is le cool I guess

#

Definitely felt a lot less than a year

empty kernel
#

Only a year? I've been doing osdev for almost 2 years, and I'm still on the same kernel.

flint idol
#

My kernels' timeline:

#

First kernel may 2023-august 2023

#

second august 2023-october 2023

#

third october 2023-february 2024

#

fourth february 2024-(basically may) april 2024

flint idol
#

I think this rewrite will keep some parts of the previous build system

#

Like dependency management

#

I'll spend a bit of time on that, then move onto the gdt (copying and pasting the previous kernel's gdt)

#

First though I got to make a new branch for the rewrite

empty kernel
#

Theres no point rewriting things like the GDT, which are working well.

flint idol
#

I know I use git branch -c to make a new branch based on another branch

#

but what do I use to make a new branch

#

ie. one with no commit history

#

I'll just search

#

git checkout --orphan

#

The github repo will be a bit goofy for a bit

#

whoops

#

I accidentally put in the old kernel's readme

#

ok the github repo is good

#

except there is nothing except for the branch for the old code

#

and master that only has markdown files and the license

empty kernel
flint idol
#

MIT

#

best license

empty kernel
#

I used that until I came across GPLv3

flint idol
#

boo

empty kernel
#

I like GPLv3 because you have to state changes

flint idol
#

hmmm should I use C23 for obos

#

gcc has support for most of it

chilly osprey
#

use c++23

flint idol
#

bruh

#

I'm using C

#

oh wait

#

Well C23 is quite new

#

obvious solution is use ANSI C

#

I'll use C17

#

It's not so new that modern compilers don't have some features

#

but not that old either

limber wave
#

C23 has constexpr so it’s obviously based

flint idol
#

yeah but compiler support for it is unstable

limber wave
flint idol
#

yeah I know

ashen goblet
weary hound
#

constexpr in c solves the problem of const int x = 5; int foo[x]; making a VLA

#

because now you can mark it constexpr instead of just const

ashen goblet
#

Yeah that makes sense

flint idol
#

I got the kernel to boot into while(1);

#

This time the kernel is using c 😎

real pecan
#

At least it's stable

flint idol
#

lol

#

time to copy+paste the gdt

real pecan
#

Most stable oberrow kernel

flint idol
#

good thing I coded my gdt in asm

empty kernel
#

For how long will it stay stable?

flint idol
#

for the previous kernel

flint idol
real pecan
flint idol
#

when I port my GDT

empty kernel
#

What order are you planning on making things in?

flint idol
#

gdt

#

idt

#

IRQs and IRQL

#

scheduler

#

VMM

#

also with vmm comes page cache

#

GDT is working

empty kernel
#

Wouldnt it make more sense to do vmm before scheduler? Also, you forgot the PMM

flint idol
#

oh yeah

flint idol
#

scheduler must have no dependencies

flint idol
flint idol
#

A wise man once told me that the timer IRQ shouldn't be linked to the scheduler

#

so it makes sense to just make it so early

#

that it can't depend on anything

empty kernel
#

What about the kernel heap?

flint idol
#

in-between PMM and VMM

#

btw VMM != page table manager

#

a wise man told me that aswell

#

actually he told that to @vernal chasm

flint idol
#

time for a lot of porting (I'm not writing this again)

#

Ok this is how symbols will be named:

Arch_* arch specific code
OBOS_* General kernel code
Mm_* VMM code
Vfs_* VFS Code
Io_* Io manager
Core_* Scheduler, IRQ code, other code in the kernel that are essential to the kernel working.
Kdbg_* Kernel debugger-related functions.
Drv_* Driver interface/loader functions.
'S' suffix to a namespace name means the symbol is declared by the arch-independent part of the kernel, but the architecture must define the symbol itself.
'H' suffix to namespace name means the symbol is a helper function.
TODO: Add more```
empty kernel
#

What about things that are exclusive to x86_64?

flint idol
#

Arch_

#

arch specific code

#

The others will be solely for arch-independant code

#

note that list is only for global exposed symbols

#

statically-linked ones aren't counted

#

structs will be named in snake_case

#

functions will be named in PascalCase

#

because why not

#

Finally my stack traces won't be wider than they are deep

vernal chasm
flint idol
#

A wise man told you that a VMM is not a page table manager

#

#560042023638269955 message

#

Hyper is a bit too fast for my own good

#

I can't tell a triple fault from goofy control flow

real pecan
#

lol

#

it was 5 times faster than limine for the limine barebones kernel example last time I tested

flint idol
#

ok the int3 instruction doesn't triple fault

#

just the question is, does it work?

#

it indeed does

#

I think I'll leave the IRQ interface for after I port the allocator

#

Ok now IRQL

#

Pretty straightforward

flint idol
#

Because these commits are so straightforward I'm just directly pushing to master

#

They're not really tied to a feature

#

I think I might put all functions in a certain "namespace" (whatever the prefix to the function is) in their own directory

#

Actually no

#

only for some

#

IRQL functions are going under the OBOS "namespace"

real pecan
#

u might want to make the namespace prefix simpler like NT

#

so its easier to type out

flint idol
#

I'll see what NT does

real pecan
#

Ke Rtl etc

#

or Nt

flint idol
#

From what I see from a wikipedia page, Nt is for syscalls

real pecan
#

no idea

flint idol
#

Wait NT calls SSDT the "system service descriptor table"

real pecan
#

does it tho

flint idol
#

Nt or Zw are system calls declared in ntdll.dll and ntoskrnl.exe. When called from ntdll.dll in user mode, these groups are almost exactly the same; they execute an interrupt into kernel mode and call the equivalent function in ntoskrnl.exe via the SSDT. When calling the functions directly in ntoskrnl.exe (only possible in kernel mode), the Zw variants ensure kernel mode, whereas the Nt variants do not. The Zw prefix does not stand for anything
From here

#

Well I guess calls it was misleading

vernal chasm
#

I still don't really know what Rtl or Zw means kekw

real pecan
#

oh thats unrelated to acpi lol

#

its some nt thing

vernal chasm
#

Ik

real pecan
#

i was talking to oberrow

vernal chasm
#

ah xD

flint idol
#

I think a reason the old kernel was so fragile was because everything depended on everything

#

it was a big clusterfuck of dependencies

#

so changing one thing that is seemlingly unrelated to something else can cause the kernel to πŸ’©

#

Before I get to the rest of the kernel I need a way to log

#

stuff

#

and panic

vernal chasm
real pecan
#

instead of c++ logging

vernal chasm
#

Imagine changing how system time is computed and the pmm dies

flint idol
#

probably could've happened lol

flint idol
#

I hate cout logging

#

It's so annoying

real pecan
#

but u did something else and not printf iirc

flint idol
#

It was indirectly calling printf

#

It was first printing what kind of log message it was

#

Whether it was a debug log, info/general log, warning, or error

#

then it printed the message

#

also I kind of forgot about error handling in the previous kernel

#

Something failed and you wanted to know why? Too bad, you're not going to

#

error codes were "false"

#

success was "true"

real pecan
#

Lmao

flint idol
#

isn't it three am where you are

#

probably a good idea to sleep

real pecan
#

Indeed

flint idol
#

It'd be funny if I implement a USB driver first thing after IRQL so I can send logs

#

and make a gdb stub for the kernel

real pecan
#

That would be big

flint idol
#

If I don't implement printing stuff on the framebuffer I'll be stuck with testing with qemu only

#

But I don't want to implement printing stuff on the framebuffer

#

because that's boring

#

I'll get to it eventually.

real pecan
#

You could use flanterm

#

Or qr code generator

flint idol
#

how would I use a qr code generator

#

for logs

real pecan
#

Store logs in a buffer

#

On key press generate a qr code from that buffer

#

Display it

#

Done

flint idol
#

pretty sure that's more work than just printing shit on the framebuffer

real pecan
#

Yes and no

#

Framebuffer can only fit so much

#

And u cant ctrl+c from a framebuffer

flint idol
#

Another problem with my previous kernel is that nothing was documented

#

There was no documentation, not even so much as comments explaining what the function does

#

None.

vernal chasm
flint idol
#

well I did make a kernel debugger for my previous kernel

#

that'd be the next step

#

obviously I should make a kernel debugger then add dwarf parsing so I can get line numbers

vernal chasm
#

Sounds like pain

flint idol
#

I think it is

vernal chasm
#

Probably less pain than dealing with timer sync

flint idol
#

for the dwarf part

#

A basic kernel debugger is pretty simple

#

Took me a day to do it

flint idol
#

Kernel logger is complete (port 0xE9 only for now)

#

The new kernel is no longer stable

#

It panics on every boot

#

Now where was I

#

ah yes IRQL

#

I got the IRQL system working

#

I just need to test it

#

It's so simple I can't think of ways to test it immediately

#

after testing that I'll make a spinlock

#

Not many ways to test that either

#

It (probably) won't break

#

Spinlocks will be a part of the Core namespace

#

IRQL is a part of that namespace aswell

#

Things in the core namespace cannot depend on anything (except basic kernel routines and other Core namespace members)

#

If they do the kernel can, and most definitely will at one point, go to shit

#

For example the scheduler code cannot depend on the logging code

#

nor can it depend on, for example the VMM code

#

Maybe the scheduler was a bad choice but you the point still stands

#

of course that code can depend on Core namespace code

#

that's kind of the entire point

flint idol
#

Spin locks work I guess

#

So simple I cannot mess up

#

I "tested" them by locking the logging functions (as I should)

#

There was a bug in Core_SpinlockRelease

#

It was with irql.

#

I think the fact that I'm writing it in C has caused me to think more about namespaces and dependencies

#

I just pushed the code for the kernel logger, IRQL, and spinlocks.

#

Tomorrow I shall work on the scheduler

#

Then the PMM

#

Then I shall port the old kernel's allocator

#

Then VMM and page cache shit

#

Then drivers

vernal chasm
#

write gpu driver O_O

flint idol
#

Eventually

vernal chasm
#

Oh god

#

Gl at that point

flint idol
#

I told @livid oracle I would here #349857717445459968 message

vernal chasm
#

True true

#

But still good luck tho

#

O_O

flint idol
#

But that's in a long time

#

I barely understand what graphics is

#

like what the hell does a geometry shader do?

#

make shapes?

vernal chasm
#

The fewest input primitives are singular points

#

And the fewest output primitives are singular points

flint idol
#

I know what I should do

#

Port the windows driver interface

vernal chasm
#

But you can produce any number of points from that singular point.
Or any number of lines or triangles

flint idol
#

1:1, they won't notice a thing

#

then use windows graphics drivers

vernal chasm
#

However it's technically limited up to some max number which you pre specify in the shader

#

But I'm not entirely sure if the driver has to conform to that limit

flint idol
#

I'll port the WDF and have my own driver interface aswell

#

then I get graphics for free

#

and other drivers for dumb devices

#

anyway enough osdev for today

livid oracle
vernal chasm
#

Wait why you in here O_O

livid oracle
#

I am everywhere

vernal chasm
#

Spooky

#

Wait so are you in #614652561965711370?

#

Probably not

#

Only like 4 people there so xD

#

Two of which are me...

livid oracle
#

that you know of evil

vernal chasm
#

Now I'm scared

livid oracle
#

anyhoo it's time for me to disappear

devout niche
devout niche
#

WDF is large

flint idol
flint idol
#

I'm writing all code related to thread context in assembly

#

Why you might ask? Because I can't be bothered to write a setup context in C then translate the C struct for context into assembly for the context switch function.

flint idol
#

I've implemented those functions

#

Time to test them

#

I also have a thread structure

#

Lets see will I finally make stable kernel

#

Bro

#

I'm triple faulting randomly

#

WHYYYYYYY

#

oh of course it triple faults calling a function

#

We just love OSDev

#

The instruction that page faults, causing the triple fault is push rbp

#

then cr2 is 0x80

#

rsp is a good value

#

so is rbp

#

not that that would matter

#

no register is 0x80

#

there is no possible way for this to fail unless some dumb code overwrote the instruction

#

it's triple faulting on return?

#

The hell

#

Why is RIP the start of getIntIST then?

#

Why is this randomly triple faulting

#

the red zone is disabled

#

Qemu is cursed

#

I have more assembly in my kernel than C

#

unless header files count

#

I think it might be a bug with spinlocks somehow

#
const bool expected = true;
irql newIrql = Core_GetIrql() < minIrql ? Core_RaiseIrql(minIrql) : IRQL_INVALID;
while (atomic_compare_exchange_strong(lock, &expected, false))
    spinlock_hint();```
#

whoops

#

Nope

#

It isn't

#

It can't be a problem with some timer IRQ coming in

#

cr8 is 0xf

#

which blocks all IRQs

#

oh and of course when I add -no-shutdown -no-reboot to the qemu command line it doesn't triple fault

#

wtf is happening

#

In a debugger it triple faults

#

outside a debugger it doesn't

#

it hangs I think?

#

It's stuck in an infinite gpf loop because there is no handler

#

which spit a 593 MiB qemu log

real pecan
flint idol
#

It can't even be my fault

#

There is no code

#

It's page faulting on

#

address 0x80

#

THERE IS NOTHING THAT CAN ACCESS 0x80 at the faulting RIP

#

It's a push rbp with an intact stack pointer

real pecan
#

Single step with gdb

flint idol
#

That's what I'm trying

#

but it triple faults at random points

#

(of course only in a debugger)

#

nvm

#

Still triple faults at random points

#

I'm calling TCG bug

#

There is no other way

#

I'll use whpx as my accelerator

#

lo and behold it doesn't triple fault

#

My thread context switching code doesn't work

real pecan
flint idol
#

I ran with whpx

#

It worked as expected

real pecan
#

Timing issue

#

TCG doesn't have bugs

#

Or I doubt u can trigger them with such simple code

flint idol
#

The instruction at RIP is push rbp

#

The part where it triple faulted is at the end

real pecan
#

Send the report to qemu mailing list

weary hound
#

tip: -M smm=off

real pecan
#

But 99.9999999% sure its a you issue

flint idol
#

I'd test on real hardware right now

#

But I have no way to print logs

#

on real hardware

#

rn

real pecan
#

See if it triple faults or not

#

But like I said it can just be a timing issue

#

Which it probably is

flint idol
#

btw it doesn't triple fault

real pecan
#

Print out the contents of rsp

#

In the fault handler

real pecan
flint idol
#

on real hardware

real pecan
#

Anyway

flint idol
#

btw this triple fault is happening before initialization of the gdt

#

and idt

#

so no fault handlers for me

#

it's happening while logging initialization of the GDT

real pecan
#

You think basic code like that causes a TCG bug?

flint idol
#

probably not

#

but you never know

#

I'll test on wsl's qemu

real pecan
#

Try it

flint idol
#

btw this only happens while a debugger is connected to qemu

#

maybe that has something to do with it

weary hound
#

what is your gdt?

flint idol
#

null segment 0x00

#

kernel code 0x08

#

kernel data 0x10

#

tss 0x18

real pecan
#

I thought your gdt worked

#

How is it dying now

weary hound
#

are you still using limine gdt at the point of the crash?

flint idol
#

Well I'm using hyper's

weary hound
#

judging by cs=0x28

flint idol
#

but yes

weary hound
#

is 0x10 a 64-bit data segment?

#

i have a feeling it's like 16-bit or 32-bit

#

or did you not touch the segment selectors yet

flint idol
#

I hadn't touched them at the time of triple fault

weary hound
#

hm what if you do x/i 0xffffffff800044b1 in the qemu monitor when it crashes

#

as opposed to objdumping or addr2line-ing the binary

real pecan
#

TCG has no gdt validation basically

#

So even if u put garbage there it doesn't matter

weary hound
#

well it's apparently before the gdt init

#

so it's still the bootloaders gdt

real pecan
#

Yeah should be fine

flint idol
#

What the hell, it stopped triple faulting

#

I add some code back it triple faults

real pecan
flint idol
#

why doesn't your gdt have a 64-bit code segment?

#

*data

real pecan
#

Thats not a thing I think? (or at least it doesn't matter)

flint idol
#

It is a thing

#

and I'm pretty sure it matters

weary hound
#

you can just set all the other segment selectors to 0 for the kernel

#

but you need a valid segment for ss in user mode

real pecan
flint idol
#

maybe not though

#

idk

#

all I know about gdt is "make once, never think back"

real pecan
#

Yeah at ring 0 u can just set them to 0

weary hound
#

such a weak mindset, you wouldn't last a minute in protected mode on the 286

real pecan
#

CS is still used for privilege checks I think

flint idol
real pecan
#

And 64-bit data segment is not a thing right? @weary hound

weary hound
#

it is a thing, as i said you need a valid segment for ss in ring 3 in long mode

real pecan
#

That bit is valid only for the code segment

#

So I dont think so

weary hound
#

or wait hold on

#
    common::x86::makeGdtFlatData32UserSegment(gdt, kGdtIndexClientUserData);
real pecan
#

Yup

weary hound
#

my bad, the data segment is the same for 32-bit and 64-bit

flint idol
#

that leaves me wondering why [this](#curated-resources message) says 64-bit user data segment

#

and 64-bit data segment

#

probably because it's less confusing for beginners

real pecan
#

Saga skill issue

weary hound
#

compare the values though

#

they are the sam

#

e

flint idol
#

well it was pitust's message

real pecan
#

Look carefully

weary hound
#

oh i see

flint idol
#

but using x/i at the address in qemu

#

gives me push rbp

lean glen
#

yea your stack is wrong

flint idol
#

it isn't though

#

The stack is fine

real pecan
#

The first unstable kernel pre gdt init

flint idol
#

The cr2 value is fucked

lean glen
flint idol
#

rsp=0xffff80001ffb0ed8

#

cr2=0x0000000000000080

real pecan
#

Bruh

weary hound
# real pecan Nope

okay no what's posted in curated resources is correct, the 32-bit segment has flags.DB=1 set and flags.L=0, and the 64-bit segment has flags.DB=0 and flags.L=1, which is what you are supposed to do apparently

#

quoth the osdev wiki gdt page

L: Long-mode code flag. If set (1), the descriptor defines a 64-bit code segment. When set, DB should always be clear. For any other type of segment (other code types or any data segment), it should be clear (0).

#

oh wait no

#

that's specifically for code

real pecan
#

Literally incorrect

#

Yeah

weary hound
#

reading comprehension: 0

#

on my part

real pecan
#

Lol

#

Pitust fell off

weary hound
#

for a moment i thought managarm was doing something wrong :^)

real pecan
#

Nah thats impossiblehalfmemeright

weary hound
#

yeah how could i ever doubt it

#

anyway

flint idol
#

The triple fault changes locations every crash

weary hound
#

did you enable interrupts by accident? :^)

real pecan
#

You sure interrupts are disabled

flint idol
#

cr8=0xf

#

eflags.IF=1

weary hound
#

are you sure the legacy pic is masked?

#

also IF=1 means they are on

real pecan
flint idol
#

oh yeah PIC doesn't go through APIC

#

silly me

#

and it isn't subject to cr8

#

amazing

#

it works

#

ie. doesn't triple fault

#

now I got a context switch function to debug

real pecan
#

Big

weary hound
#

very cool tcg bug halfmemeleft

real pecan
#

Lmao

flint idol
#

does hyper by any chance remap the PIC

real pecan
#

It doesn't touch any hardware

flint idol
#

well why cr2=0x80 is forever unknown

weary hound
#

limine explicitly masks the pic

flint idol
#

I'll call Arch_disablePIC before anything

ashen goblet
#

I see obos v5 is released?

#

Problems with teiple faults i see?

real pecan
#

TCG bugs halfmemeright

flint idol
#

but why was cr2=0x80

weary hound
flint idol
#

but what vector

#

was it addressing

real pecan
#

0

weary hound
#

0x80 / 16 = 8

#

vector 8

flint idol
#

oh yeah idt entry is 16 bytes

real pecan
#

Or that

weary hound
#

aka where the master pic is mapped by default

#

on bios

#

so irq 0 on master pic

#

aka pit

real pecan
flint idol
#

I remember getting this bug on my first kernel

#

when I stied

#

Because I had no IDT

#

I had no idea why it happened

weary hound
# real pecan Oh interesting

yeah ibm didn't listen to intel saying that the first 32 vectors are reserved and now you end up with the pic in the middle of cpu exceptions on legacy bios

real pecan
#

IBM big retard

weary hound
#

although originally there was nothing there and no one could've predicted the pc would come out on top as the dominant platform so

ashen goblet
flint idol
#

which is why we should make a time machine

#

go back in time

#

with the limine mafia

#

and threaten ibm to listen to intel

ashen goblet
#

And force every os to use limine

real pecan
#

I would just buy Bitcoin

weary hound
#

go back in time
tell ibm to map pic to vector 0x20
go back to the present
you are using a m68k computer now

real pecan
#

Lol

flint idol
#

lol

real pecan
#

With keyronex as your daily driver

flint idol
#

but why didn't it triple fault on my laptop

#

It should've because no hardware was touched

#

and it emulates the PIT

real pecan
#

Pit not enabled by default

weary hound
#

uefi machine?

flint idol
#

indeed

#

oh yeah

#

I forgot that I would boot from legacy bios emulation (I forgor what it's called) on my laptop for my 2nd kernel

#

which is why I could use PIT

#

I should probably sleep even though it's pretty early

real pecan
#

Same

flint idol
#

if I'm forgetting stuff like this' this bad

flint idol
real pecan
#

Yes

ashen goblet
#

Dont give up now

flint idol
#

I obviously should've started rewrite six when I got the triple fault

real pecan
#

Obos rewrite 6, remastered gdt init

ashen goblet
#

😭

#

This time in Rust so you are safe from memory leaks triple faults scheduler bugs and allocator/vmm problems

flint idol
#

I remember when my kernel wasn't cursed

#

t'was a long time ago

real pecan
#

You will get there

flint idol
#

eventually

real pecan
#

Yes

ashen goblet
#

Good luck

flint idol
#

ty

#

for future reference, the align directive in nasm does nothing for struc alignment

#

only code alignment

#

and data

#

ok

#

after some debugging

#

I can switch to an "arbitrary" """thread""" context

#
static void test_function(uintptr_t userdata)
{
    OBOS_Debug("In %s, userdata: %lu.\n", __func__, userdata);
    while (1);
}```
#

is basically is getting called in a fancy way:

thread_ctx ctx;
memzero(&ctx, sizeof(ctx));
CoreS_SetupThreadContext(&ctx, test_function, 0x45, false, thr_stack, 0x4000);
CoreS_SwitchToThreadContext(&ctx);```
ashen goblet
#

Hows memzero different / better than memset

flint idol
#

it's not

#

I just like saying memzero

#

instead of memset

ashen goblet
#

Thats a valid reason

flint idol
#

I mean technically it's faster by a couple cycles

low lodge
#

but why memzero and not OBOS_CoreS_MemorySetZero?

flint idol
#

because

#

I don't wanna type all that

low lodge
#

also valid

flint idol
#

and the prefixes have a meaning

#

anything without the prefixes is rather statically linked or is something like memzero

#

or memset

#

or it's a type

#

types don't follow that rule

ashen goblet
flint idol
#

No

low lodge
#

wdym by statically linked? surely everything in the kernel is linked into the kernel

#

unless you have modules already

flint idol
#

I meant static linkage

#

like the static keyword

low lodge
#

ah, internal

flint idol
#

It's just xor rax,rax takes fewer cycles than mov al, sil

#

so using memzero is faster

#

by a couple clock cycles

ashen goblet
#

What if the data youre zeroing isnt in a register

flint idol
#

rax is used for rep stosb

#

for the value to fill the memory in

ashen goblet
#

oh yeah i remember

#

al in the case of stosb tho right

flint idol
#

I'm not sure if I'm lagging or discord is

flint idol
flint idol
#

I open discord

#

and there is no message

#

until I reopen discord

ashen goblet
#

Common discord L

weary hound
flint idol
#

good idea I should do that

low lodge
#

The real question is whether you have memzero call memset or if its handmade - the compilers specially optimize specifically memset, so if you're handrolling something you're likely leaving perf on the table

flint idol
#

I got memset implemented

#

using rep stosb

#

I optimized memzero

#

to be one byte shorter

low lodge
#

https://godbolt.org/z/Yeco3zPha as an example, memset doesn't even exist in this TU but the compiler still magically optimizes it to rep stosq

sharp pike
#

not with -ffreestanding

low lodge
#

oh really?

sharp pike
#

because it implies -fno-builtin

low lodge
#

I thought that magic was always magic

sharp pike
#

nope

#

try it

low lodge
#

you're right indeed

#

though -ffreestanding -fbuiltin brings the behavior back, idk if that has other bad side effects for a kernel though

sharp pike
#

i mean yeah because you're re-enabling it

flint idol
#

btw what happened to banter

sharp pike
#

it means that you have to implement standard behaviour for function calls, and that you also have to be careful when implementing stuff because for example the compiler could optimise a memset() impl to a memset call

#

as you showed there

#

which is not very good

flint idol
#

which is why you should ditch compilers

#

and code everything in asm

sharp pike
#

in general you can reenable -fbuiltin but it requires you to be extra careful about stuff like that

flint idol
#

not just x86_64 asm

#

8086 asm

sharp pike
#

no

flint idol
#

I have more asm in my kernel than C code