#pmOS - microkernel OS for RISC-V, x86, and LoongArch
1 messages ยท Page 8 of 1
what's fishy?
PALEN-1:12?
I don't know if the address has to be shifted by 12, or be aligned to 4K
Like limine does this if I'm not missing something
probably the function happens to end up on a 4k boundary so that's why it works fine anyways?
either that or the hardware doesn't actually care about alignment
Did someone try it on physical hardware?
yeah
and it didn't care..?
you can send a PR fixing this
or send me a patch (made with git format-patch)
if you want attribution for fixing this
i'll just do it myself then
boo
๐
(it was absolutely useless...)
Fun, apparently it does have 5 level paging...
Ok, I'm not detecting the skill issue, but the paging is refusing to work
This is a bit strange...
loongarch?
Yeah
The kernel just pagefaults
Basically like RISC-V but more Chinese
lol
The documentation is a bit difficult to comprehend at times
And I don't even have printf...
But they have some interesting ideas I guess
which
Software refilled tlb/split paging/direct mapping regions for example
how does limine work if its software refilled
It has a special exception for TLB misses, where CPU drops into mode without paging and you refill it
But like they give you special instructions which do it for you basically
interesting, is it really cheaper for chips to do this instead of handling it internally
But you can configure how many bits is each level and so on
Idk, I guess
But like otherwise it's normal page tables
so u can implement hhdm in software technically?
cool
Wait a second
Bruh I crashed gdb
I don't get it
Page invalid exception for fetch operation: This exception is triggered when the virtual address of the
fetch operation finds a match in the TLB with V=0.
How am I messing up my page tables like that
It has to be something absolutely dumb...
I think my tlb configuration is off
lddir $t0, $t0, 2 is trolling me
wait, what the fuck, it's loading the page from 0x80001ff1
So I'm not supposed to be setting any bits in page directories?
Ok, this is really fucked
I don't get how it works, but I think I have paging...
This is interesting...
I think I've gotten paging to work...
Now I need to figure out the direct map thing...
So, DMW0 is choosing to troll me...
Good documentation
The hit is determined as follows: the highest 8 bits of the virtual address ([63:60] bits) are equal to the VSEG field in the configuration window register, and the current privilege level is available.
Someone is high
exception: 72 (Address error for Memory access)
(documentation doesn't mention anything about it, or I'm blind )
It was this...
ADdress error Exception (ADE): when the program has a functional error that causes the address of the instruction fetch or memory access instruction to appear illegal (such as the instruction fetch address
is not aligned on 4-byte boundaries, and the privileged address space is accessed), ADdress error Exception for Fetching instructions (ADEF) or ADdress error Exception for Memory access instructions 13 (ADEM) will be triggered.
Cool
Why does it get triggered though 
Like this address should be ok 90000000ebf8a000
I don't get it, why does it not work
For example, if PALEN is equal to 48 and DMWO is set to 0x9000000000000011, virtual address space
0x9000000000000000-0x9000FFFFFFFFFFFF will be directly mapped to physical address space 0x0-
0xFFFFFFFFFFFF at the PLV0 privilege level, the memory access type of which is consistent and
cacheable.
I do asm volatile("csrwr %0, %1" ::"r"(0x9000000000000011), "i"(CSR_DMW0)); and this faults
I think it time to read qemu source
Elixir Cross Referencer - source code of Qemu v9.2.2: target/loongarch/cpu_helper.c
QEMU bug?
@toxic torrent can you test an image?
sure
There are 3 possibilities, with the same probability of being right:
- Documentation is wrong
- QEMU is dumb
- I'm insane
always assume qemu is broken
though with loongarch this is sometimes actually the case
No, this is clearly a bug
Does Linux not use DMWs?
It's checking bits [63:48] to be canonical, which is like not what you're supposed to do according to manual
gimme a command
Wait, I can't read
Not a bug
Nevermind
?
I use this qemu-system-loongarch64 -m 2G -cdrom limine/pmOS.iso -smp 4 -serial stdio -bios ovmf-riscv64/RELEASELOONGARCH64_QEMU_EFI.fd -device ramfb -d int
I'm on a train with bad internet and discord is taking an eternity to upload files
I think this is the only line that could be throwing this exception
I have an idea
(well, not an idea, but a plan)

What the fuck
I think C++ is trolling me, except I've looked at assembly and it looked fine
So the top bit somehow does not get set??
ffffffff8000c0b8: 05 44 80 03 ori $a1, $zero, 17
ffffffff8000c0bc: a5 00 24 03 lu52i.d $a1, $a1, -1792
; asm volatile("csrwr %0, %1" ::"r"(0x9000000000000011), "i"(CSR_DMW0));
ffffffff8000c0c0: 25 00 06 04 csrwr $a1, 384
To me this is setting 0x180 to 0x9000000000000011
I am definetely setting it
The CSRWR instruction writes the old value of the general register rd to the specified CSR and updates the old value of the specified CSR to the general register rd
Oh, fun, very intuitive instruction name
bootlin elixir broken as usual
(I need to redo my exception handlers...)
Fun, almost missed my stop...
guh
during pmm init
I've tried to fix framebuffer and it only made it worse, so I think I'm gonna proceed to getting the rest working and pretend it isn't broken
This just pagefaults for no reason...
I think the kernel really doesn't want to be running on this arch...
(should have ported to ARM first)
I have a theory on why this is happening...
Yeah ```
loongarch_cpu_do_interrupt enter: pc ffffffff8000af2c ERA 000000000d4cca60 TLBRERA ffffffff8000af1d exception: 2 (Page invalid exception for store)
loongarch_cpu_do_interrupt: PC 00000000ebe18000 ERA ffffffff8000af2d cause 2(refill)
, ESTAT 0000000000000000 EXCFG 0000000000000800 BADVA ffff800000218820BADI 0000000029812085 SYS_NUM 12288 cpu 0 asid 00000000000a0000
helper_ertn: TLBRERA ffffffff8000af2c
loongarch_cpu_do_interrupt enter: pc ffffffff8000af1c ERA 000000000d4cca60 TLBRERA ffffffff8000af2c exception: 2 (Page invalid exception for store)
loongarch_cpu_do_interrupt: PC 0000000000000000 ERA ffffffff8000af1c cause 2
, ESTAT 0000000000020000 EXCFG 0000000000000800 BADVA ffff800000219020BADI 00000000298080c5 SYS_NUM 3215360 cpu 0 asid 00000000000a0000
(The key here is BADVA ffff800000218820 in first exception and BADVA ffff800000219020 in the second)
I think I'm being destroyed by loongarch caching invalid TLB entries
(and it's also why flanterm breaks if I fix it...)
I think I'll fix it tomorrow
So I've decided to add early exceptions...
I've kinda half fixed it
I fixed the framebuffer...
how do you store the per cpu data ptr on loomgarch?
im doing loongarch too but i havent had the time to read the manual yet :^)
is there a csr you can use to restore it when entering the kernel from user space?
$s0 (aka $r23 has garbage)
It has 1-16 saved CSRs
Linux uses 8 of them
ah, interesting
RISC-V only has one, so I did the same thing
csrwr swaps the csr with the given general register, so you can save the thread-local stuff there
So it's like kernel gs base in some sense
i thought thats what csrxchg was for
1 is mandatory
or something like that
lol real
I also though that initially, but it's like csrwr, but with a bitmask
thanks for explanation
not doing rd = csr, csr = rj
More like
temp = csr & rj;
csr &= ~rj | rd;
rd = temp;
idk
do you have experience with risc-v?
they have cpucfg which is like x86's CPUID which tells you a bunch of stuff about the CPU, including how many of saved CSRs you have
Also machine check and tlb refill exceptions have their own save CSRs
how do you access kernel data structures from within the tlb refill handler?
since it switches to physical address mode
and kernel data structures use virtual addresses, or they should at least
maybe im overthinking
you don't
(or through pc-relative instructions)
I guess
They give you a page table layout and instructions which refill the tub from page tables for you
So you basically have normal page tables (with bad names for their fields in the manual)
like you probably don't need to
This was destroying it
Very good documentation
what's wrong with those docs? seems perfectly fine to me
what is hint?
instruction category probably? it seems like the same kinda thing as the tables at the top of instruction docs in the x86 sdm, and its format is probably documented elsewhere in the manual
Maybe it's a me problem, but I didn't find it
Like for other instructions it's explained in their documentation
(Maybe I'm just spoiled by Intel docs)
oh hmm
I guess it's just an instruction encoding thing and only 0 is allowed
(since loongarch has 32 bit instructions a bit like risc-v)
(with fixed encoding formats)
I think I've reached userspace!
(after fixing some brainrot)
(can't even blame copilot for stupid code now
)
(astral negative influence)
It's actually userspace and timer interrupt I think?
writing la assembly is an experience
am i dumb or is the right way of moving data between two registers add.d $t0, $t1, $zero
risc architectures are so cruel :(
where's my mov $t0, $t1 
interesting that the assembler doesn't have a pseudoinstruction for that
im not sure if it does honestly, i just know that the manual does not specify one
also llvm-objdump says there's move but idk what it does
inb4 rep movsb
https://blog.xen0n.name/en/posts/tinkering/loongarch-faq/
The register move pseudo-instruction is called move, like MIPS. (Different from x86 or RISC-V; mov or mv are not recognized.)
hmm
might be exactly what im looking for
{ 0x00150000, 0xfffffc00, "move", "r0:5,r5:5", 0, 0, 0, INSN_DIS_ALIAS }, /* or rd, rj, zero */
from a binutils patch
+ { 0x00150000, 0xfffffc00, "move", "r0:5,r5:5", 0, 0, 0, INSN_DIS_ALIAS }, /* or rd, rj, zero */
oh lol
we had the same idea
anyway, nice! good to know
replaced my add.d with move, so much cleaner now that i dont have to explicitly use $zero lol
You have move
Ok, I've gotten to userspace doing syscalls

I think there are a bunch of other pseudo-instructions, like on RISC-V
But I didn't find a good list
(also, I'm pushing changes to dev branch all the time)
like qookie said, the binutils patch is a good source :^)
or not said but linked
and not a singular patch but rather the binutils source in general
the patch just tells you where to look
How did I miss that loongarch has a sane timer?
So, I need vector instructions...
By the look of things, the userspace is alive
(I think I'll figure that out tomorrow...)
So Linux does lazy saving of fp context? https://elixir.bootlin.com/linux/v6.13.6/source/arch/loongarch/kernel/traps.c#L507
Gotta love vscode...
https://elixir.bootlin.com/linux/v6.13.6/source/arch/loongarch/include/asm/asmmacro.h#L242 is it me, or is this broken?
Elixir Cross Referencer - source code of Linux v6.13.6: arch/loongarch/include/asm/asmmacro.h
What the fuck is this code
Ok, the kernel is trolling me
Something is corrupting memory...

So what's crashing is Rust...
I think I'm in a mood of adding support for interrupt controllers...
(I think my interrupt handling mess needs to go)
Wow, my ns16550 driver just half-worked without touching anything
(I'm missing the interrupt memes)
Picking stuff up from ACPI
(also, I don't know how to handle them yet)
Like there is no obvious way to "return to userspace with interrutps on"
(although I guess I can just mask them)
the interrupts are too
for me and are refusing to work...
PIC is just refusing to work
Time to figure out how to trace it I guess...
I don't get it; I think qemu doesn't bother to set up iocsr access to liointc?
Am I supposed to get this from AML?
(anyway, I think I'm just gonna support this for the time being...)
So QEMU wants BIO PIC...
loongarch has dual 8259 PIC confirmed?
no
jk
it has hpet though
lol really?
i haven't looked at it in depth, but the manual mentions hpet, and it seems to be very similar to x86
The ACPI is being weird
It says that BIO PIC GSI starts at 48...
I wonder if there's some sort of interrupt override thing
(Or I need to change the ACPI interrupt model)
nope, this is x86 only thing
So, through my rigorous investigation (a bunch of printfs), I have concluded that QEMU has EIO PIC, BIO PIC and MSI PIC
Now, I am completely clueless how I'm supposed to get it to work
Since Linux has decided to use different names for things https://docs.kernel.org/arch/loongarch/irq-chip-model.html
Like ugh what do I do with this 
(So EIO PIC is the Loongson 3A5000 controller, and BIO PIC is 7A1000 controller)
Did you figure it out
Which table is this?
MADT
But I don't get what I'm supposed to do with the node ID
it's probably the numa node id?
in your case you have only one
What I don't quite get is why it doesn't give me address
Base Address?
Yeah
I've tried to use the one provided in the manual and nothing hallpened
(But with legacy controller)
Maybe QEMU doesn't implement it at all?
git grep
This is EIO PIC
I mean except the cascade vector, this is what I expected
Time to add more pritnfs to qemu...
I'm trying to use iocsr instructions
Also, this is different from manual
there's already a trace_loongarch_extioi_readw
It's just quiet
I'm probably doing it wrong then
Idk, I want to get over with it, but I'm just feeling unwell and don't understand anything
(I think I'm getting close to a burnout, which is suboptimal)
I think it just wants me to use the extended mechanism
I'll just panic if I detect legacy only system
The kernel first identifies the extended interrupt mode support by CSR[0x8][3], and then enables the
extended interrupt mode by register CSR[0x420][48].
Ok, I am writing to the right place, at least

It's not showing byte-width accesses
Is it what's messing everything up?
I am dumb
The dumbness has been ratified
I still have no interrupts 
This is just trolling
Maybe it needs to be level-triggered...
Like this is the only thing which might be broken

(the addresses are relative to 0x1400, so I'm setting interrupt enable to 1, and CPU mask to 0x01, which should be correct...)
and it's impossible to debug because of pagefaults
Is it because your access width was wrong?
I've changed it to use 32 and 64 bit reads and writes
So linux is doing some weirdness with its interrupts
Am I supposed to be using both of the controllers? https://docs.kernel.org/arch/loongarch/irq-chip-model.html
Like UART is still conected to lioint
In newer generation Loongson CPUs, Extend I/O Programmable Interrupt Controller (EIO PIC) replaces the combination
of HT PIC and part of LIO PIC, and routes interrupts from BIO PIC and MSI PIC to CORE PIC directly. The
format of the EIO PIC structure is shown in the following table.
"part of LIO PIC"

It was not 0
I think this SPCR is invalid?
I'm gonna add #ifdef to it
Nope, still no interrupts...
Desperate times call for desperate measures (I've added more printfs to QEMU)
This looks wrong
Yeah, it should 66 and not 112
This is broken
(except it's not)
I don't get it, this seems to be broken https://elixir.bootlin.com/qemu/v9.2.2/source/hw/intc/loongarch_extioi.c#L128
Nevermind, I can't read
I think I'm starting to see the parallels
The EIO PIC is like LAPIC, and GIO PIC is like IOAPIC
Lol, they literally call it IO-APIC
I think the time has come to finally move interrupt allocation to the kernel
This sounds like lapic
In addition to being compatible with the legacy I/O interrupt method, the 3A5000 supports extended I/O
interrupts, which are used to distribute 256-bit interrupts on the HT bus directly to each processor core
instead of forwarding them through the HT interrupt line, increasing the flexibility of I/O interrupt usage.
Through breaking interrupts, I now have serial console...
The manual says that the kernel should write to BIO PIC to ack interrupts...
(Time to add a new syscall)
What the fuck
where is it not tbh
Ok RISC-V you can just
and use PLIC and don't think about it
I think I'm liking the new interrupts interface...
ah, well you don't seem to use it though 
(my kernel always returns int64_t result and uint64_t value)
yeah
It should be the same as vector
you can also docpp if (auto res = ...; !res) { // ... }
you can emulate that
somewhat easily
if (({ int res = ...; res != 0; })) {
// ...
}```
you can probably macro it away
but that's gcc extension
So I've programmed the second controller, but interrupts still refuse to work 
The writes don't get to the controller
I'm going to sleep
(qemu trace doesn't show writes to the registers)
sounds like you aren't writing the registers
What am I doing wrong 
Is there a way to see where qemu places this in memory? https://elixir.bootlin.com/linux/v6.14-rc6/source/drivers/irqchip/irq-loongson-pch-pic.c
Elixir Cross Referencer - source code of Linux v6.14-rc6: drivers/irqchip/irq-loongson-pch-pic.c
(wrong source)
well the address is definitely fetched from madt https://elixir.bootlin.com/linux/v6.14-rc6/source/drivers/irqchip/irq-loongson-eiointc.c#L376
Elixir Cross Referencer - source code of Linux v6.14-rc6: drivers/irqchip/irq-loongson-eiointc.c
I had been bitten by ACPI tables being broken in QEMU
On RISC-V
I don't know why it doesn't work
tbh i have no idea where qemu assigns memory to these regions
I don't have memory clobbers on inline assembly...
The assembly looks different
nope, still broken
Wtf
I forgot an ~
This looks better
But still no interrupts 
(except that the enable bit is not what it should be)
(why am I failing so badly at this?)
I can't believe it...
So this is basically PLIC with extra complications...
So it works, but I'm getting an interrupt storm
now do the ged thing
I want to fix interrupts 
I wonder if they want me to disable the interrupt flag
I am too dumb for this...
Either I don't understand something (very likely) or QEMU dgaf about interrupt masking
The spec says that you do have to mask them if you don't use HT
Like this implies that the interrupts are edge triggered?
Why is it spamming the interrupts then?
Ok, it works with the terrible thing...
I'm sticking with it
What the fuck is this assembly
; la $t0, on_failure
ffffffff80003098: 8c 09 00 1a pcalau12i $t0, 76
ffffffff8000309c: 8c c1 d0 28 ld.d $t0, $t0, 1072
; st.d $t0, $tp, 48 # CPU_Info::jumpto_func
ffffffff800030a0: 4c c0 c0 29 st.d $t0, $tp, 48
It's probably broken because I'm setting level triggered interrupt as edge triggered
But SPCR does tell me the interrupt level
Which is fun
Though it shouldn't matter
(reference to myself https://reviews.llvm.org/D138021)
Also, doesn't limine do GOT relocations?
Omg, I think I know why fork is broken on RISC-V
(this was making the loongarch build hang)
ahh yes. pcalau12i $t0, 76.
I have no idea how x86 builds weren't crashing...
(I think I need a reschedule defer mechanism...)
For context: since I don't switch contexts, the rescheduling could be a race condition since the task could appear on the other CPU, so on these syscalls, I set the result to success before the copy to user is completed, which overwrites the arguments on loongarch, risc-v and i686...
(which switches the task inside it)
But I think the loongarch build kinda fully works now
I just need to fix the other builds and also change the interrupt registering stuff
Does it have an _S5 btw
Take your time to chill
And I have exams next week
I think I'll finish/fix the other ports parts so it's presentable enough to be in the main branch and doesn't linger on me, and take a break for a couple of weeks
By kinda fully working I mean basically complete, except the (platform independent) interrupt API changes induced stuff which I need to fix
I think I'll fix RISC-V memes...
(note to myself: qemu-system-loongarch64 -m 2G -cdrom limine/pmOS.iso -smp 4 -serial stdio -bios ovmf-riscv64/RELEASELOONGARCH64_QEMU_EFI.fd -device ramfb)
Uncool
It's trolling me
I'm not returning nullptr there...
Cool, my brain is fried from the loongarch assembly
I can't write RISC-V one anymore
(so I almost have fast syscalls on risc-v)
fast syscalls?
Basiccally doing memcpy on user memory and catching pagefaults
Instead of walking the page tables every time I copy from user
thats not safe at all
But it worked
It's proper, just very slow
I do
i mean yeah i guess, but it's kinda badddd
thats literally more lines of code than just catching a fault
It was a design skill issue
I'm trying to catch them now
Besides, it works on x86 and loongarch already
if loongarch is so good, wheres loongerarch
MIPS? 
I was setting on all interrupts, so the kernel couldn't preempt itself properly
So like it was not 
btw u should support smap/smep etc
The kernel is choosing violence
I think everything is calling exit again 
No?
The screen and ns16550 drivers are just refuse to work...
actual brainrot
(this should be a0-a2)
so by the looks of things, the RISC-V port is also fully working now...
So the plan is to
- Fix x86 port, and by that I mean moving IOAPIC code to kernel
- Change the drivers to use that
Nice code
How did not know that this was in C? https://en.cppreference.com/w/c/language/generic
Cool, using auto in C feels magical...
the kernel is trolling me
It's tripple faulting
I think I need to take a break
It is trolling me hard
It's casually faulting with error 0 with instruction ... cmpq %rdi, 0x10

Fun, the kernel ooms and dies if I enable LAPICs 
This makes absolutely no sense
What the fuck
It has to be something extremely dumb
So somehow this is just broken...
I think I've caught it
There is no such thing as too many asserts
I was missing a ~ again
fun, the 32 bit x86 port is dead for some reason...
it's not dead but interrupts are broken 
(Even though it shares the interrupt code with x86_64)
RISC-V and LoongArch are fully working
I think I'll fix the ia32 port (after taking a nap) and then push loongarch stuff to main
And maybe I'll write the GED driver after that
uACPI server hangs?
(probably a skill issue)
Or like doesn't hang, but it doesn't ack the interrupt for some reason
Maybe I broke something
It doesn't

EC stopped working??
i think the kernel is panicking...
Anyway, I merged the changes to main
Unfun...
Ok, I fixed it
But my Lenovo laptop still seems to be unable to recieve EC interrupts...
I have a suspicion my com driver is misconfiguring the baud rate...
interrupts are very broken
i have no idea why
and have very little motivation to fix them
(or do anything)

(maybe it's kernel panic)
Maybe I should announce my OS on Reddit 
๐๐๐
The kernel is hardcore trolling me
I've put a printfs around it, and there are no interrupts, at all
on physical hardware
like not even apic timer interrupt
Cool, the ns16550 driver has started working on my PC
In i686 build...
I have no clue of what's going on...
Still no SCI
But this does use interrupts...
Why the hell is hpet under root
Probably for the same reason that firmware remaps LAPICs
I think I've fixed SCIs...
So, I think I have kinda completed what I wanted (LoongArch port) and it would be best for me to take a break from osdev
The only thing missing from it compared to other platforms (x86, RISC-V) is SMP (since it's not supported by Limine), and I also wanted to write an ACPI GED driver for it, but I feel like I'm too burnt out to do it now
The next plan would be to write the proper init server, which would include listening to pmbus events and starting drivers, as they are discovered by ACPI/PCI/other buses, then finish the ext4 driver (in Rust) and try to get bash working
But I want to do GED...
I've decided to write an init server
this one's really nice
Maybe I should move processes to the kernel after all? 
you've just discovered the idea of a monolithic kernel!
no
process as a collection of threads
Idk what to do 
I'm in a design limbo
Like the issue is that I want to track processes in my init server, but I need process server for that, which can't then be tracked by init
Maybe I should merge them into one server 
this would solve all of my problems 
The only issue is that my init server is in C, and my processes server is in C++
And I don't like C
Since I also want that to eventually be able to catch failing servers and restart them
systemd 
Can it listen to (p)mbus?
I'm planning my init server to do it
on managarm, once devices show up on mbus, posix creates the sysfs stuff for them, and they show up on udev
from where on out we use udev rules for starting servers
for systemd, we have a service that awaits for a keyboard, mouse and DRM card to be available before continuing to launch weston/kmscon
depends on how you define "integration" ig
Thats pretty smart
Technically thatโs a binary that waits for it and we execute it as ExecStartPre
I think I'll merge the init and POSIX servers into one...
What if I want to port to ARM?
And for that I think I'll implement IPC handles/capabilities
VMM now works properly 
no it doesnt
you think it does
but it doesnt
never belive the vmm
it only knows how to lie to you
I've put a bunch of printfs and it did seem correct
Small update: I've decided to move the port resolution by name into bootstrap server as well, and I think I can hook it into init server as well, which is pretty interesting I guess...
pmOS - microkernel OS for RISC-V, x86, and LoongArch
my libc and kernel supports loongarch without soonโข๏ธ
@carmine nacelle did you have to do anything special to port gcc to loongarch?
it's giving me this bullshit
my honest reaction
It's in my gitlab
kk
I think binutils also had just worked
(at least it compiled and GCC worked with "no issues" (except ocasional segafults))
I don't support it
ah
okay yay it's building with the weird ass hack
yeah, it's just a bunch of C++ which takes care of everything
fyi i had to do this shit
in gcc?
isn't it what you're supposed to do?
(I mean I don't use mlibc so that's what I was doing as well)
only loongarch has this garbage hack
don't bother
i think my llvm toolchain works as well so far, except it doesn't have a dynamic linker for some reason
like no interp
that all seems pretty standard, i imagine the only reason you didn't have to do it for anything else would be if mlibc support for those targets was upstreamed into gcc
hm
it's weird they hardcoded this though
like, ever other target doesn't have this switch
Wait, when did that happen?
i don't know if it is, i just don't know any other reason why that wouldn't be required for other targets
or well, the top hunk seems standard, the triplet_os=... thing is weird
ah ok
Small update: after a week being unmotivated and debugging it with no printf, I've managed to move "named ports" stuff to bootstrap daemon, and will be removing it from kernel shortly
after which the plan is to finally add handles/capabilities/whatever the name is to the IPC
I don't know how to name it so it's not too confusing
Right now I have ports, and I want to be giving out send "capabilities"/whatever I decide to call it
Mach calls it rights?
I've looked at Mach docs and it talks about port rights namespace, which gave me an idea...
I have task groups, so I thought about associating port rights to them, but didn't want to do that because I would have to look up the task group, verify that the task is part of it, and then look up to port/right inside the tak group...
What I think I'll do instead is I'll have add a way to set the default task group for ports, which will just be a pointer, which kinda solves all the problems
So the libc will probably just set it to be the task group of the process, but you're free to redefine it if you want to...
But first I have to replace this atrocity (shared pointers for task groups) with RCU
(too many things to do
)
wouldnt be that atrocious if it were an rwlock
the lock isn't the problem, I can easily replace it
My shared pointers impl is kinda bad and I'm trying to get rid of it
my ports already used RCU...
(which is convenient I guess)
I think I know how I would implement the rights thing
Mach has a refcount, but I don't like it, I'll just have one right per task (group)
This is why it's not an rwlock (I've been using splay trees
)
awesome highlighting
average vscode experience
Nice types
So I've converted this to RCU, but I now have a feeling that it's use after free/double free minefield...
what's an RCU
Read copy update
an algorithm to manage lifetimes in concurrent programs
say, if you have a lock free linked list and you delete an element. you can only truly release the memory when no other thread can still have a pointer to it
and that's what RCU ensures
I think I more or less have the idea of how I'm going to implement the rights thing...
and the interface should also be relatively nice, I'm going to add a (atomic) syscall, which allows to set the task group for the rights namespace by the thread, and I'm going to limit it to the caller thread and the task group it is in, so there will not be a need to use locks, or check permissions...
And for the kernel stuff, I'm going to create a task group, which would have the idle (and if I add them, general kernel) threads
Which could also be used for other stuff, like for example, at the moment I use the task groups to track threads in processes, and detect when a thread exits unexpectedly
I think I know how I'm gonna handle notifications about rights being closed (on the other side)
Don't know it it's the best solution, but I'll insert all the rights into a tree in the parent port (with my intrusive BST class), keyed by some internal ID, and I'll allow duplicate nodes there and do count() on their deletion
I like this better than keeping some common data structure (if that makes sense)
The send once rights (which I anticipate to be the most common/created and deleted the most I guess) will not have to do this
(also, I think this will solve the IPC balancing in multithreaded processes
)
What the fuck
did you include the .cc on accident?
no

I think one is in global namespace, and the other is in kernel::sched
(I've just decided to add namesapces to kernel)
lol
Nice formatting again
lmao
but why you use light mode???????
are you ok?
I've gotten bored of dark mode
you hate life
Small (not) update: I think I've burnt myself out, so there has been very little progress, and probably won't be for a few weeks
I've kinda started implementing this, and in my head it should all work out quite well
But on an unrelated note, I've ordered an ARM board, which should have UEFI support, so I think I will do an ARM port once I get myself together...
The issue is that clang doesn't support some architecture I'm considering targeting
which
sh4
never heard
Dreamcast
when ppc
I've looked at it and it gave me MIPS vibes
When someone writes a bootloader for it
uboot
(someone could be me, but I can't be bothered)
aarch64
But that uses Linux protocol?
so?
average C++
lol what is that XD
C++
why do you even need a ref to a pointer?
yes
that's cursed
why
never saw a lambda like that
(tbh I could just return iterator here)
wdym
it makes it a pointer
classic iterator to pointer conversion
(I basically have my own intrusive tree type)
wtf is -><error type> and that auto kernel::proc:... thing
thats not valid C++
ah the coloring is confusing
That's a little odd arch, XD registers is by far the best part of it
Cool, my rights thing is becoming a concurrency nightmare
I think I'll be having to hold up to 6 locks at the same time 
(in one function)
?
I want to allow sending up to 4 rights + reply right with each meesage
And the only feasable way to do it that I've come up with is by protecting each right with a lock
(Since I want them to do a bunch of stuff)
I'm not very clear where I could use bitmap in there
You can just lock the table though
No?
yeah
So they are not in a global namespace
I also thought about limiting it to these initially, but it also had some issue with concurrency
(I don't remember which)
And since I'm having to take locks on both of them anyway (to pass ownership from right to a message), I might as well expand it to four
Since it would also be useful for drivers, where I can have a reply right, "service right" (e.g. so that the server can communicate with the driver), and some sort of public facing right, so that stuff can communicate with server directly
Idk
Maybe it's not needed 
But at least two should be nice
Anyway, I think it's going to be a neat system
I'm planning to have send once and send many rights, with ability to explicitly revoke them, some sort of notification to the sender if the right disappears, and notification to the reciever if sender closes it as well
So it should solve the permission issues and the issue of servers dying unexpectedly and not replying to messages
I remembered, I need to check the right I use to send (to avoid sending message twice on a send once right) + the right I am sending (to check for the similar problem), besides the newly created right, so it's still 3 locks
This in theory should not be a big issue, since it's 'just' 6 rbtree removals inside the lock
(at most)
(maybe I have too many locks in the kernel)
New fun problem/design decision, I can send rights, but how do I accept them? 
Somehow my rights stuff is working??
I guess now I just need to rewrite everything to use it...
Cool
yes
so debian had installed itself, but had broken repos, and ubuntu installer is just refusing to boot?
ok, my os is completely destroyed after the IPC rewrite...
what are you changing?
I'm adding IPC writes
IPC writes?
Autocorrect 
rights*
I think my libc is really falling apart...
time to merge your libc into mlibc :^)
Yeah
I've been looking at mlibc recently
(though I have exams soon and don't have time to do this now)
But how does it handle os-specific libraries and stuff?
Briefly
Like since my kernel API is weird and a lot of my stuff goes through IPC
So does managarm
not sure what you mean by "os-specific libraries" but you can just do whatever you need to/want to in your sysdep's meson.build file
and sysdeps are of course a way for mlibc to call into your kernel to allocate memory, open files or whatever
Yeah, I've seen it, but it has a bunch of stuff in managarm namespace, and I didn't find it
they map pretty closely to libc functions
(but didn't really search much)
To open files and stuff, I need a lot of library code + I have a bunch of functions in my library which is not in libc
idk how to explain it
well, as long as you can link against it from c++ code you should be just fine
you're gonna have to make it available to meson somehow
a simple meson.build to build them as a static library should do
so you can pull it in through a subproject and have it work with meson of course
again, managarm itself is a good example of how to do it since they rely on libraries from the managarm repo in mlibc
So like it's better to make it a separate library?
well, that's what i assumed it was already
alternatively, if you don't plan on using it outside (m)libc, and you want to replace your libc with mlibc, you can just copy the code into your sysdep directory and use it like that
i see include/pmos/ has the headers you probably need but i don't know where to find the actual sources lol
lib/libc
well, that's libc
that's not what i was looking for
but i don't think i need to look at it anyway
I don't have a separate library for it, but I should probably make it be so
you can put that into your sysdeps
mlibc can install custom headers as part of the headers_only build target
Maybe I want to have it as a separate library
if I want to have 2 c libraries for some reason...
then just dylink against it in the build script idk
though that probably won't work in upstream
It's also probably worth checking if it makes sense to integrate parts of your libc into mlibc
There may be areas where your libc is more complete
The issue is that my libc is in pure C
doesn't matter
Though yeah, this benefits everyone
code can be copied
I'll take a look
aren't there some things that aren't valid c++ that are valid c?
i was mainly talking about that
i said usually
and yeah very minor edge cases
yeah i know, that's why i said it's not a big deal to adjust it
not really
especially if you compile with -fno-exceptions
which mlibc probably does?
iirc it does, yeah
yes
Fun, I'm trying to write nothrow C++ wrappers for my IPC stuff, and it's really obnoxious with stl
I wonder if I should roll my own vector (again)
I think most of the OS compiles with the new IPC functions?
I just need to fix Rust 
Somehow this is promising
By the look of things, this is a blatent nullptr deref?
Somehow it's not in the order that I expected it to be?
this is ub lol
the order of evaluation is undefined here
I though that functions were evaluated from right to left?
Almost 0 operators (including function calls) in C/C++ define their evaluation order
With && and || being the obvious exceptions
operator, :^)
ok, both the kernel and userspace are trolling me now
Now I actually have no words
me when i write too much python
there's a c++ header that adds a macro for not
for users that dont have ! on their keyboard
its not an official keyword
dont use it
ik and and or do not require any header
really? thats cool
I think it is official C++ https://en.cppreference.com/w/cpp/language/operator_alternative
Ok, the rights thing is a bit of a hell to debug now 
(actually, maybe I take my words back)
I'm starting to suspect that it might be a deadlock
(I need a watchdog timer...)
I'm losing my mind
It looks like the userspace is at fault...
(pointer infestation)
(I've no idea what's going on)
The userspace has gone insane
and the assembly looks sane
(I think I kinda know what's going on)

Insanity
(instead of loader_port_name, it should be create_result.right)
After a lot of printfs, I think I have userspace back...
Now I just actually need coroutine abstractions around my IPC 
I think that excluding the printf weirdness, my IPC rights thing is fully working?
this feels like it's readin from heap or something
(I think I know what's up)
That were non null terminated strings
maybe I want to get 32 bit risc-v userspace working?
brain damage
Ok, the loongarch port is not as dead as I expected
I think it's a skill issue of my libc...
Yeah
"But Rust is memory safe"
Cool, it jumps to 0 in panic
And I really don't feel like debugging that right now
I think my printf is not returning the right size
(that's my suspicion)
Maybe I should check ia32 build first
So, I'm done with studying
Which means it's time to fix Rust
And then add more stuff
I think the top priority would be the init server
Cool, Rust is just trolling me
when is it not xd
