#pmOS - microkernel OS for RISC-V, x86, and LoongArch
1 messages Β· Page 10 of 1
CPUs can be software-disabled for many reasons
yes
In MADT
ofc
but I mean two x2apic entries with the same id
yes

u have to be able to deduplicate them
fun
(if lapic entries also exist)
you get less cpu cores 
CPU usable is flags & ACPI_PIC_ENABLED or flags & ACPI_PIC_ONLINE_CAPABLE, right?
static bool cpu_usable(u32 flags)
{
if (flags & ACPI_PIC_ENABLED)
return true;
if (!s_online_capable_bit_usable)
return false;
return flags & ACPI_PIC_ONLINE_CAPABLE;
}
oh no
nah its simple
static void setup_online_capable_bit(void)
{
struct acpi_fadt *fadt;
uacpi_status st;
st = uacpi_table_fadt(&fadt);
BUG_ON(st != UACPI_STATUS_OK);
/*
* Online capable bit was introduced in ACPI 6.3, prior revisions might set
* it erroneously so don't look at it for those versions.
*/
s_online_capable_bit_usable =
(fadt->hdr.revision > 6) ||
(fadt->hdr.revision == 6 && fadt->fadt_minor_verison >= 3);
}
How many helpers are there in uACPI? 
lol
So fadt only gets unreferenced once I do the unitialization thing, right?
(I forgot what was the function)
uacpi_table_fadt returns an internal version that doesnt need ref/unref
So uacpi just stores it in its buffer
yeah, since the raw copy requires a lot of sanitization
So I guess this basically is as correct as it gets (except the smp_wake_everyone_else_up function
) https://gitlab.com/mishakov/pmos/-/blob/dev/kernel/arch/x86/cpus/cpus.cc?ref_type=heads#L261
And not checking if I'm on bsp
looks good
is there no acpi 6.4?
Wdym?
wdym
The current version is 6.6 I think
I have 6.5 in my osdev folder
It came out in like December
Small update: I've started publishing PCI devices to pmbus as well, but it's currently broken because of broken puts() or whatever Rust is using 
Maybe I should just finally switch to mlibc? 
Though I wanted to implement futex first 
I think I'm going insane, why is my todo list so large 
This is cool
I think this can all fall nicely into place
I don't have energy to do it right now, but I think I can add handles to the interrupts in kernel (which can use iommu as well), which can act as a permission system
Then also do this, with a different handle
(anyway, now I can match AHCI devices in a better form, I think I'm going to make my ahci driver use this, then do the disk thing, then hopefully I can have disk?)
I think the kernel OOMed
Ok, this looks extremely promising (it's failing because I haven't implemented that syscall yet), and it found a mouse and a keyboard, and tried to start the service twice (even though i8042 should have only started once), so I can probably make it restart servers as well with very little work
I can probably even forgo dependencies for servers for now, and make it start servers as the things get published in pmbus
Because the idea is to have devicesd launch and publish pci devices -> this will start ahci server which will publish the disk -> this will start the disks server, which will parse the partition tables (iirc I had code for that already) -> which will start the filesystem drivers, which can finally start the vfs or whatever
(I need to decide how to handle the mountpoints)
And all of this is just passing capabilities between everything
Idk, I have so many ideas for this
(I really have to study though, so I don't have time for this now)
(famous last words)
This is fully working now
(aparently, I had everything already in the kernel, just needed to make it a syscall...)
lol
It's working, but I'm exhausted
Though I'm planning to make 64 bit port bootable with Hyper as well
After this
what's the yaml for?
Init server
(I've used libyaml, but I think I'm doing it wrong, since the code I'm writing is horrible)
yaml is famously complicated
cool
And this is my limine file, which can hopefully make Hyper work as well
yeah thats the thing about yaml, if u actually use advanced features its ridiculously complicated
dont see why not
My i686 port might be broken
I haven't tested it in like a year
And I've changed a bunch of x86 stuff recently
(I mean I unified more of x86_64 and i686)
yeah that definitely looks better than shoving everything into name
does the init server do device matching to launch the servers?
yes
with the pmbus
yeah i figured that much
and then it just starts them and gives them a handle to the device
Btw what if I have multiple ps2 keyboards
It launches i8042 just once
Then that is supposed to publish two ps2 port object (which I haven't implemented yet)
IMO ALWAYS_ONCE should be implied by the lack of a match specifier
Then that launches the PS/2 server
I guess, but other servers run without match
Wdym
I also though about it, and the stuff like POSIX server can interact with the bootstrapd directly
Like devicesd and pmbus itself just always run
(I also wanted to add a mechanism to restart them, and so on)
Right
Also, I need to "urgently" fix my build system 
(recompiling everything for a different arch is a mess)
How do u not recompile everything if its a different arch
I mean I do
But I have to recompile libc, then reinstall llvm's libs, and then recompile the rest
But like it's not automatic
Cool, the i686 kernel doesn't compile

π
and missing using namespace 
What even is this error? π
Cool, it gets to userspace, and crashes after that...
(In i686 port)
(I mean the userspace crashes)
I think I'll fix it tomorrow
Which probably implies the kernel fully works
Yeah, ofc
Cool
Just qemu-system-i386 -hdd pmos-hyper.img -serial stdio
Thats like 128 megs of ram
1 am is rookie time
16 is syscall_create_right
which shouldn't be too hard to fix, whatever it is
And -ESRCH means that it can't find the task group?
I hope 15 is create_left 
SYSCALL_SET_INTERRUPT 
Nooo
the liberalism
Though iirc I'm not reclaiming bootloader reclaimable memory with hyper
Which might be suboptimal
(I mean I removed it from limine as well, because of SMP considerations, but since I do it myself, the other cores shouldn't be touching it anyway, so there shouldn't be race conditions with it)
Yeah, the fact it's doing this makes no sense...
I'll do it tomorrow
Doing what?
Failing to create a right
It's failing because the rights namespace (a.k.a. the current task group) doesn't exist, which makes no sense
At least from my recollection of code that I wrote like a year ago
Interesting
What actually pagefaulted was syscall_return???
And the stack was unmapped for some reason
I've no idea what's going on
Or rather, how did 64 bit port work?
Huh?
I think I just "forgot" to set it on pthread entry
Because for some reason I did it in assembly??
This looks more promissing...
Ugh
Since when are uint64_t s are 8 bytes aligned on x86??
Or wait
Wait, it's not it
bruh
Also, since when is movq valid on ia32???
Cool, the stack is off...
I think the kernel is ignoring the fixed flag
thats because by default clang assumes a higher baseline
so it uses sse unconditionally even for 32 bit
It's not the problem with sse, but that my stack is not where it's supposed to be 
yeah im just saying movq and sse is because of that
Ofc it's available with i686 target
I think movq should be fine with misaligned uint64_t though
yes
I think I'm getting somewhere
This was exploding because of a dumb error in the auxvec serialization logic
Which I've changed for 64 bit pointers, but forgot for 32 bit ones
All of the errors are in Rust...
Though why didn't it print the rest of the stuff?
Now it just decided to break for no reason...
It must be something stupid
The log server isn't starting
I found the error 
Ok, i686 is kinda working
(what's broken is syscall return...)
I think I want to port x86_64 to hyper as well
I will add a cmdline field to modules soon but I guess u don't need it anymore
Yeah...
I mean a config is better anyway
I give up
Lol why
lol
I'm tired and want to fix i8042 driver first
How did you break it
I've looked at my hyper code, and there were too many uint32_ts in there
I've changed everything around it, and it was kinda left abandoned
Like the logic probably works, but I want it to use pmbus, etc.
Ah
I need to unify my memory initialization logic
Because it's 2 1k loc files, that are different for 2 protocols I support...
Also, maybe I should finally implement futex??
i8042 is trolling me (in QEMU!)
This is concerning...
wtf
Or maybe it's actually fine
But my CPU cooler is like at 100% for some reason
Which tells me it's not 

I'm dumb
I think my rbtree impl is trolling me 
Not anymore 
Now I kinda want to properly do interrupts stuff, like it's done on managarm in kdb server, but I kinda don't have energy for it
Talking of which, I have decided that I will make my rights also be messages in the kernel, so that they can be pushed onto the ports
(since then it lets the kernel send messages without having to allocate memory for them)
I know this is basically just a bunch of userspace stuff, but why is it so cool to see it do this? (devicesd -> i8042 -> ps2d, all launching new drivers instances through pmbus)
(the ordering here is from async IPC and the fact that I think I don't have SMP enabled in qemu...)
What's concerning now is that my ns16550 driver breaks half the times, for some reason
(Which I think is because of broken interrupts)
Cool, the keyboard is fixed
(totally not overengineered)
Time to figure out evdev?
how do I represent keyboard and mouse data then?
thats up to you to design
Like I though it was just some standard structs + char devices at /dev/input
standard for linux yes
Since Managarm and freebsd have it, why not do it as well
managarm has it because its aiming for linux compatibility
although at api not abi level
and freebsd literally has linuxlator so yeah
I don't want to deal with input tbh
All I wanted was drivers
Also, I have no idea how human input and terminals and GUIs work
I see Wikipedia mentions STREAMS when talking about line discipline 
I have decided, I'll do my tty server in C++ 
I like coroutines, and people have said that the Rust's ones are too complicated
yeah, no, itβs fine
probably easier and better integrated than c++ coroutines
tho that comes with a few drawbacks, mainly lifetimes that are wack
yeah, if you just compare the mechanism, C++ coroutines are probably a bit easier than rust async/await
but with rust you can use a lot of existing libraries
tbh i have never even taken a look at c++ coroutines, so that's why i think rust futures are easier :^)
Another detail is that I already have stuff which uses C++ coroutines, I just haven't bothered yet to make them handle rights (I mean this kinda also was the reason to implement them in the first place)
what the fuck
Ok, this was actually not a C++ bug
This is very promissing (timers are broken again
)
Yeah, it's actually kinda mostly working...
Oof
My AHCI is hardcore trolling me
It's just calling exit() somewhere, with no error messages
Also, I'm fed up with my timers
It just breaks half of the time
I'm done
It was a very dumb double free
why does limine not load with 128mb of ram?
Does hyper work
it was last time I checked
Big
large kernel modules?
this is still smaller than a rust hello world 
pmbus is in rust 
damn
I think the time has come to fix the timers...
The only issue is that I haven't decided what interface I want to use
I hope I don't get AI psychosis 
But I've talked to a clanker, and I think I have a very good solution 
This is insightful
I need to think about what it said
But I think I'll add timer capabilities, which send messages as programmed (so I can just tread them as recieve rights for messages on the other side), and it's like what I have already, but better. And I was worried about the concurrency, but it suggested me that I can just IPI other cores to invalidate the timers on them (since my timers are per-CPU, but multiple threads have access to capabilities).
(It also said to look at QNX, Mach and L4, which is like reasonable...)

After some (passive) thinking, I think it just repeated what I said to it
So this doesn't count
Why do I even bother with asking AI
I think I'm in the mood for fixing timers...
Though I won't redo the timers interface for now...
Just make it absolute, and universal
Though while I'm at it, what's stopping me from making the kernel fully preemptible? 
I just won't reschedule if I'm preempted...
I mean could be worse, iirc lemonOS uses (and only has support for) the PIT.

I think the ACPI PM time source is working now...
The only issue is that it seems that it's a bit faster than it should be in QEMU (but not by too much...)
how did u hook it up into the kernel
Like 60 seconds passes there, while it's 56 in reality, and I don't think it can be broken code since its frequency is fixed
It's just used as a time base, and then I use lapic in one shot mode to get to deadlines
try on real hw
dont u have display output

like fbcon
It's in a different branch 
since 2022
its crazy that u have so many features yet a black screen lmao
No, I can just rebase on it
It should probably work
no, the driver is in userspace
it's not black, it's just that if the kernel doesn't boot, there is no screen
I think it should shough
(I was actually planning on implementing tty soon, and bash or something, to the screen)
yeah u should
I didn't boot on my test machine 
But I would imagine it just doesn't have acpi pm
i dont think ive seen an x86 box without a pm timer
It's a mac
anyway its easy to check via acpidump
Idr if I ever sent you its dump...
My kernel is trolling me
I'm building the kernel-fb branch...
Can you get the dump from OS X?
if not, I can just boot ubuntu on it, or something
tbh I should make a flantem in kernel a define instead of a separate branch
Or like just have it at all time, since it useful for panics
Since now I just print it to com

Yeah, it's a broadcast IPI dip skill issue
I can already see it's very accurate
(the timer)
I mean, why wouldn't it be
And shutdown still works
The keyboard had a skill issue though, for some reason
Though knowing it's a mac, it probably has a usb or i2c keyboard, or some weirdness like that
AHCI is busted though
Ok, too large of a todo list
I'll do HPET, then TSC (deadline), then the KVM thing probably
yeah see it also reports garbage ioapic id
its a common theme
because back in the day ids had to be unique
but it doesnt actually program that id in
btw are those found cpu lapic logs only for APs?
Yeah
But it prints it when it finds them in madt
why isnt there a print for BSP
IIt prints it when it initializes data for an AP in prepare_cpu function. And it doesn't get called for the BSP
https://gitlab.com/mishakov/pmos/-/blob/dev/kernel/arch/x86/cpus/cpus.cc?ref_type=heads#L286
(Need to fix the typo)
It's all very simple 
Yeah, because you said that there was for_each after I did that loop, and I didn't bother with rewriting it
lol
I mean it works
do I want to bother with hpet interrupts?
(No)
HPET is refusing to cooperate 
Which I think is a skill issue with units 
Yeah, HPET in qemu also runs a little bit faster than it should
(though I'm using qemu in wsl2, so it's double virt, so it's kinda not out of the question=
Also, my keyboard and AHCI drivers now work consistently (with either of them)
I want to do TSC...
Why is APIC timer code on oasdev wiki in assembly??
i doubt that it does
how much faster?
Like the same as ACPI timer
they should all run at the proper frequency
My phone counts about 56-58 seconds while it counts 60
And I can see it's a bit faster
And it was seemengly very accurate on the phys hardware
would you rather it be in c? 
(I haven't tested HPET, but ACPI PM was)
that's almost certainly an issue on your side
Yeah, I think it's an issue with WSL2
56/60 deviation is huge
Because ACPI PM's frequency is fixed, and my kernel uses deadlines based on it, I don't think the code can be bad
I want to implement kvm clock and see if it improves
Like I take PMTMR/HPET as a reference, and lapic oneshot deadlines, and I've set it up to print something in kernel every second (after the previous deadline), so it should have been precisely at 1 Hz (even if I don't get an interrupt on time)
(so even if my lapic calibration is bad, it shouldn't matter)
Cool, it's tripple faulting if I use tsc deadline on wrmsr 
Wtf
Wtf
I think I'll just trust that it's working and not test it 
it found a ps/2 keyboard -> timers are not fucked
wait, the pvclock is like really nice actually?
it gives me the tsc frequency and time in nanoseconds, and just have to lapic dedline it and that's it??
No calibration or weirdness needed
that's kind of the whole point
What did you expect lol
idk, the typical x86 jank
nevermind
loongarch is like tsc + lapic (without tsl deadline), but it's like architectural, with a fixed frequency that's given to you in cpuid
Apparently the timers weren't working there because I never actually called the initialization function 
coild the limine smp init code for risc-v be broken?
RISC-V is trolling me 
why are you switching between some many different tasks all the time lol
I'm just fixing the broken stuff
since I switched away from using limine mp request (on x86), I had to reimplement it on risc-v
and I kinda wanted to have smp
(I mean maybe I'll implement smp loongarch as well)
cool, it's working
the only broken thing now is acpi power button interrupt, for some reason
(also, smp trampoline on risc-v is like super easy)
I think I'll add clock source, calibration source and interrupt source to kernel as an abstraction on x86
This way I can support hpet and kvm clock elegantly...
(as an interrupt source, with the kvm clock handling, etc.)
I think I either won't support PIT in the kernel, or make it a cmdline flag
Fuck me
Cool, I think my HPET calibration produces more or less the same frequency as ACPI PM
(anyway, my timer infra is proper now, and I don't use PIT anymore at all)
It's ACPI PM, HPET and CPUID 0x15 TSC
(or like the first two for calibration)
I think I can live without KVM timer for now...
(I'll maybe do it this weekend)
But I'm happy and this feels complete
I need to look at how people do POSIX servers. because what I have feels weird
should I seek contributors?
idk
but like now all of the code is mine
(except the libraries and stuff like that)
idk how to say what I want to say
I can't keep doing it alone forever
I would love to contribute when I get to a point of not being utterly incompetent at C/C++ 
I mean I have Rust in userspace as well 
oh right
on that note, how do you build your std?
my problem is that I don't know what functions i need to add to the libc crate that aren't needed for the unix group
actually
where tf IS your rust std
nvm
hm
did you just add random headers to the libc crate until it worked?
Kinda, yeah
I think I've just defined my os as unix, then added headers by looking at other operating systems, then implemented everything that was needed for it to link
k
I've tried to implement smap and smep, but qemu is trolling me
This doesn't detect it for some reason

the kernel works, but my userspace breaks with smap ππ
how
do you fault on something?
My mmap syscall fails π
(or like not the actual mmap, but mapping memory objects)
so basically your code is broken?
where does it fail
see this is why i put tracing probes all over my kernel so you can enable them to get debug prints all over the place π
(and yes they are not terribly fast, but they are very cool)
I though it was a copy from user thing, which didn't have smap, but apparently it's not?
anyway, I have an exam in a few hours and I'm just procrastinating
I though it would be a quick thing since I already had it on risc-v?
I think that my copy_from_user catches the pagefault incorrectly or something?
and the overhead isnt even that crazy if they are inactive
Yeah, I am pretty sure it's the copy_from_user stuff, because why would it fail otherwise
Cool, I have smap and smep on amd64
it was some assembly skill issue
in my copy to user...
wtf
Do I go with xbstrap or jinx 
totally unbiased answer: jinx
So I can't eventually self-host it? 
unless you want to implement linux features, no
Xbstrap also talks about containers...
i have requested this before
I don't remember the outcome of the discussion
being able to self host the distro is something I'd like to do at some point
xbstrap can run without containers although I wouldn't recommend that
though I think I'm still quite far from self hosting
what the fuck
Cool, it's compiling clang
hm?
cursed
What am I supposed to do?
sudo !!
no
it's a host recipe
I did this
#!/bin/sh
name=clang
revision=1
from_source=clang-src
# hostdeps="cmake"
configure() {
cmake -S ${source_dir}/llvm -DCMAKE_BUILD_TYPE=Release -DLLVM_ENABLE_PROJECTS="clang;lld;lldb" -DLLVM_TARGETS_TO_BUILD="X86;RISCV;LoongArch" -DCMAKE_INSTALL_PREFIX=${prefix} -DLLVM_TARGET_TRIPLE=x86_64-pmos -DCLANG_DEFAULT_CXX_STDLIB=libc++ -DCLANG_DEFAULT_LINKER=lld
}
build() {
make -j ${parallelism}
}
package() {
make install
}
Cool, I think it worked
didn't know llvm also took DESTDIR
yeah i use it to make it install into a subfolder in it's project XD
for some reason, it's not finding the directory?
Why
#!/bin/sh
name=libc
version=0.0.1
revision=1
source_dir=lib/libc
deps="libc-headers"
hostdeps="clang"
configure() {
cmake -S ${source_dir} -DSYSROOT=${sysroot_dir} -DTARGET_ARCH=${JINX_ARCH} -DINSTALL_DIR="${dest_dir}/usr/lib"
}
build() {
make -j ${parallelism}
}
package() {
INSTALL_DIR="${dest_dir}/usr/lib" make install
}
This is my CMake
cmake_minimum_required(VERSION 3.22)
set(CMAKE_C_STANDARD 17)
set(TOOLCHAIN_PREFIX "${TARGET_ARCH}-pmos")
set(CMAKE_C_COMPILER "clang")
set(CMAKE_ASM_COMPILER "clang")
set(CMAKE_AR "llvm-ar")
SET(CMAKE_C_COMPILER_TARGET ${TOOLCHAIN_PREFIX})
SET(CMAKE_ASM_COMPILER_TARGET ${TOOLCHAIN_PREFIX})
set(CMAKE_TRY_COMPILE_TARGET_TYPE "STATIC_LIBRARY")
set(CMAKE_ASM_OUTPUT_EXTENSION_REPLACE 1)
set(CMAKE_C_OUTPUT_EXTENSION_REPLACE 1)
set(CMAKE_C_FLAGS "-Wall -Wextra -O3 -g -nostdlib -fPIC --sysroot=${SYSROOT} -fno-omit-frame-pointer -mno-omit-leaf-frame-pointer -flto -ffat-lto-objects")
if (${TARGET_ARCH} STREQUAL "riscv64")
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -march=rva20u64 -mabi=lp64d")
endif()
set(CMAKE_ASM_FLAGS ${CMAKE_C_FLAGS})
project(libc VERSION 0.1 LANGUAGES C ASM)
set(SRC_FOLDER "src")
file(GLOB_RECURSE GENERIC_SRC "${SRC_FOLDER}/generic/*.c" "${SRC_FOLDER}/generic/*.S")
file(GLOB_RECURSE ARCH_SRC "${SRC_FOLDER}/arch/${TARGET_ARCH}/*.c" "${SRC_FOLDER}/arch/${TARGET_ARCH}/*.S")
list(FILTER ARCH_SRC EXCLUDE REGEX ".*/crti\.S$")
list(FILTER ARCH_SRC EXCLUDE REGEX ".*/crtn\.S$")
list(FILTER ARCH_SRC EXCLUDE REGEX ".*/crt0\.S$")
set(SRC ${GENERIC_SRC} ${ARCH_SRC})
# GCC shenanigans
# https://gcc.gnu.org/bugzilla/show_bug.cgi?id=67618
# https://github.com/zephyrproject-rtos/zephyr/issues/64941
# https://github.com/zephyrproject-rtos/zephyr/pull/65082
# https://gcc.gnu.org/onlinedocs/gcc/Other-Builtins.html
#
# Apply -fno-inline-malloc so GCC doesn't optimize calloc to itself, creating infinite recursion
set_source_files_properties(${SRC_FOLDER}/generic/malloc/malloc.c PROPERTIES COMPILE_FLAGS "-fno-builtin-malloc -fno-builtin-free -fno-builtin-calloc -fno-builtin-realloc")
set_source_files_properties(${SRC_FOLDER}/generic/string.c PROPERTIES COMPILE_FLAGS "-fno-builtin")
add_library(csrc OBJECT ${SRC})
add_library(c STATIC $<TARGET_OBJECTS:csrc>)
# add_library(c_static SHARED $<TARGET_OBJECTS:csrc>)
# set_target_properties(c_static PROPERTIES OUTPUT_NAME c)
# crti and crtn
add_library(crtstuff OBJECT ${SRC_FOLDER}/arch/${TARGET_ARCH}/crti.S ${SRC_FOLDER}/arch/${TARGET_ARCH}/crtn.S ${SRC_FOLDER}/arch/${TARGET_ARCH}/crt0.S)
# set(INSTALL_DIR "${CMAKE_CURRENT_SOURCE_DIR}/../../sysroot/usr/lib" CACHE PATH "Installation directory")
install(TARGETS c ARCHIVE DESTINATION ${INSTALL_DIR})
# install(TARGETS c_static DESTINATION ${INSTALL_DIR})
install(FILES $<TARGET_OBJECTS:crtstuff> DESTINATION ${INSTALL_DIR})
I don't get it
It worked the second time...
i'm pretty sure cmake just handles DESTDIR for you out of the box
no need for all that INSTALL_DIR stuff
Or not
I had to do this??
#!/bin/sh
name=libc
version=0.0.1
revision=1
source_dir=lib/libc
deps="libc-headers"
hostdeps="clang"
configure() {
cmake -S ${source_dir} -DSYSROOT=${sysroot_dir} -DTARGET_ARCH=${JINX_ARCH} -DDESTDIR="${dest_dir}/usr/lib"
}
build() {
make -j ${parallelism}
}
package() {
DESTDIR="${dest_dir}" make install
}
Ok, I've made it work...
you don't need DESTDIR when configuting
yeah
Jinx's trolling me again 
#!/bin/sh
name=kernel
version=0.0.1
revision=1
source_dir=kernel
deps="libc-headers libcxx"
hostdeps="clang"
configure() {
cmake -S ${source_dir} -DTARGET_ARCH=${JINX_ARCH} -DSYSROOT=${sysroot_dir}
}
build() {
make -j ${parallelism}
}
If I add it it still does it
#!/bin/sh
name=kernel
version=0.0.1
revision=1
source_dir=kernel
deps="libc-headers libcxx"
hostdeps="clang"
configure() {
cmake -S ${source_dir} -DTARGET_ARCH=${JINX_ARCH} -DSYSROOT=${sysroot_dir}
}
build() {
make -j ${parallelism}
}
package() {
DESTDIR="${dest_dir}" make install
}
well i didn't know what the error was
clearly it has nothing to do with the step missing
try to rebuild libcxx
idk i dont have the brain capcity to even think of a possible solution
maybe it's the rc in the name
who knows
rindex is failing for some reason
it was added libcxx to the pool
#!/bin/sh
name=libcxx
revision=1
from_source=clang-src
deps="libc-headers libc"
hostdeps="clang"
triplet="${JINX_ARCH}-pmos"
configure() {
cmake -S ${source_dir}/runtimes \
-DLLVM_ENABLE_RUNTIMES="libcxx;libcxxabi;libunwind;compiler-rt" \
-DCMAKE_BUILD_TYPE=Release \
-DCMAKE_INSTALL_PREFIX=/usr/ \
-DLLVM_TARGET_TRIPLE=loongarch64-pmos \
-DCMAKE_CXX_COMPILER_TARGET="${triplet}" \
-DCMAKE_C_COMPILER="clang" \
-DCMAKE_CXX_COMPILER="clang++" \
-DCMAKE_C_COMPILER_TARGET="${triplet}" \
-DCMAKE_ASM_COMPILER_TARGET="${triplet}" \
-DCOMPILER_RT_BUILD_BUILTINS=ON \
-DCMAKE_C_FLAGS="--sysroot=${sysroot_dir} -nostartfiles" \
-DCMAKE_CXX_FLAGS="--sysroot=${sysroot_dir} -nostdlib" \
-DLIBCXXABI_USE_LLVM_UNWINDER=true \
-DLIBCXX_ENABLE_SHARED=OFF \
-DLIBUNWIND_ENABLE_SHARED=OFF \
-DLIBCXXABI_ENABLE_SHARED=OFF \
-DCOMPILER_RT_BUILD_BUILTINS=ON \
-DCOMPILER_RT_BUILD_ORC=OFF \
-DCOMPILER_RT_BUILD_SANITIZERS=OFF \
-DCOMPILER_RT_BUILD_MEMPROF=OFF \
-DCOMPILER_RT_BUILD_XRAY=OFF \
-DCOMPILER_RT_BUILD_LIBFUZZER=OFF \
-DCOMPILER_RT_BUILD_PROFILE=OFF \
-DCOMPILER_RT_INSTALL_LIBRARY_DIR="/usr/lib" \
-DCOMPILER_RT_BUILD_CTX_PROFILE=OFF
}
build() {
make -j ${parallelism}
}
package() {
DESTDIR="${dest_dir}" make install
}
should be good
Idk
I've added version and revision to libcxx and rebuilt it
If I remove libcxx, it starts to build it (but obviously can't because of the missing headers)
And like idk, there shouldn't be anything wrong
And like also it had built clang fine from the same source
yeah, I gues it really doesn't like the -
I've changed clang to 19.1.0_rc3 and got this
Ok, the kernel is compiling...
I guess the userspace shoudn't be too difficult
I just need to figure out how to package it into a disk file, and generate bootloader configs
Is there something to do conditional building?
I think I'll make a clanker generate a script 
I think that it inherits the version, but not revision, from the source recipe?
Time to figure out how to compile rust
But tbh it's much nicer than my make insanity so far
(Also, I've switched everything to CMake
)
I'm too flat brained to figure out out of tree gnumake compilation

I'm too dumb for this 
(does anyone know how to fix it?)
This is interesting...
https://github.com/Andy-Python-Programmer/aero/blob/master/host-recipes/rust
I think it still doesn't fix my issue 
it would be nice if you shared the recipe
but iirc you need to do this https://github.com/48cf/jinix/blob/82e89b58dfa5faa4508f9d4d7e83dae91ecaa955/source-recipes/rust#L9-L11
I removed the builds directory and didn't work
I've changed the recipe to just rust and now it seems to be compiling?
Though my another complaint is that it fails easily on a flaky wifi connection
well that doesnβt sound like a jinx issue?
Everything else retries
anyway
running: /build_dir/host-builds/rust/build/x86_64-unknown-linux-gnu/stage0/bin/cargo build --jobs=default --manifest-path /base_dir/sources/rust/src/bootstrap/Cargo.toml -Zroot-dir=/base_dir/sources/rust -Zwarnings
warning: unused config key `build.docs` in `/build_dir/.cargo/config.toml`
error: failed to run `rustc` to learn about target-specific information
Caused by:
process didn't exit successfully: `/build_dir/host-builds/rust/build/x86_64-unknown-linux-gnu/stage0/bin/rustc - --crate-name ___ --print=file-names -Zallow-features= -Wrust_2018_idioms -Wunused_lifetimes --target x86_64-unknown-pmos --crate-type bin --crate-type rlib --crate-type dylib --crate-type cdylib --crate-type staticlib --crate-type proc-macro --print=sysroot --print=split-debuginfo --print=crate-name --print=cfg -Wwarnings` (exit status: 1)
--- stderr
error: error loading target specification: could not find specification for target "x86_64-unknown-pmos"
|
= help: run `rustc --print target-list` for a list of built-in targets
Traceback (most recent call last):
File "/base_dir/sources/rust/x.py", line 53, in <module>
bootstrap.main()
~~~~~~~~~~~~~~^^
File "/base_dir/sources/rust/src/bootstrap/bootstrap.py", line 1413, in main
bootstrap(args)
~~~~~~~~~^^^^^^
File "/base_dir/sources/rust/src/bootstrap/bootstrap.py", line 1363, in bootstrap
build.build_bootstrap()
~~~~~~~~~~~~~~~~~~~~~^^
File "/base_dir/sources/rust/src/bootstrap/bootstrap.py", line 1030, in build_bootstrap
run(args, env=env, verbose=self.verbose, cwd=self.rust_root)
~~~^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
File "/base_dir/sources/rust/src/bootstrap/bootstrap.py", line 237, in run
raise RuntimeError(err)
RuntimeError: failed to run: /build_dir/host-builds/rust/build/x86_64-unknown-linux-gnu/stage0/bin/cargo build --jobs=default --manifest-path /base_dir/sources/rust/src/bootstrap/Cargo.toml -Zroot-dir=/base_dir/sources/rust -Zwarnings

I've deleted rust and now it's this??
#!/bin/sh
name=rust
revision=1
from_source=rust
allow_network=yes
configure() {
cat > config.toml <<EOL
[llvm]
download-ci-llvm = false
targets = "X86"
[build]
target = ["x86_64-unknown-pmos", "x86_64-unknown-linux-gnu"]
build-dir = "${base_dir}/host-builds/rust"
docs = false
[install]
prefix = "${prefix}"
sysconfdir = "${prefix}/etc"
EOL
}
build() {
CARGO_HOME="${build_dir}/.cargo" ${source_dir}/x.py build --stage 2 -j${parallelism} --verbose
}
package() {
CARGO_HOME="${build_dir}/.cargo" DESTDIR="${dest_dir}" ${source_dir}/x.py install -j${parallelism}
find ${dest_dir} -name "*.old" -delete
strip_command=strip
post_package_strip
}
#!/bin/sh
name=rust
version=1.0.0
revision=1
git_url=https://gitlab.com/mishakov/rust-pmos.git
commit="39dedc845fe6715741cf9a7d425cd389f9e26f0f"
early_prepare() {
git submodule update --init --recursive --depth=1
}
ok, nevermind
oh wait you don't need to specify build.host?
TIL
what do you think it is 
no, i mean where is it coming from?
well you have this thing called a Jinxfile
i know
post_package_strip() {
if [ -z "$strip_command" ]; then
strip_command="${OS_TRIPLET}-strip"
fi
for f in $(find "${dest_dir}"); do
if file "$f" | grep 'not stripped' >/dev/null; then
echo "* stripping '$f'..."
stripped_file="$(mktemp)"
${strip_command} "$f" -o "$stripped_file"
chmod --reference="$f" "$stripped_file"
mv -f "$stripped_file" "$f"
fi
done
}
it's just a bunch of shell scripts
this is what i have in there
Idk
Clanker said it isn't
But I don't get it
The recipes that I've seen just run cargo install on cargo
But like where is it coming from?
steal my recipes
i have cargo and rustc
yeah, I've seen it
But you just call cargo install in here https://github.com/zinnia-os/bootstrap/blob/main/host-recipes/cargo
Imagedeps???

Also, is there a way to get the host tripple?
I wanted to run the build server on an arm board
doesn't it get it automatically?
I don't get it
I yoinked the cargo recipe, and it should be working fine, but it still can't find cargo
how
what's the error
uname -m 
did you add the cargo to hostdeps
yes
show
my cargo recipe is different
find install thing doesn't fail, so it should be fine
cargo install?
#! /bin/sh
name=cargo
from_source=cargo
revision=1
imagedeps="build-essential libssl-dev pkg-config cargo"
hostrundeps="gcc rust"
allow_network=yes
build() {
CARGO_HOME="${build_dir}/.cargo" \
cargo install \
--target x86_64-unknown-linux-gnu \
--target-dir "${build_dir}" \
--path "${source_dir}" \
-j${parallelism} \
--root "${build_dir}/out"
}
package() {
CARGO_HOME="${build_dir}/.cargo" \
cargo install \
--target x86_64-unknown-linux-gnu \
--target-dir "${build_dir}" \
--path "${source_dir}" \
-j${parallelism} \
--root "${dest_dir}${prefix}"
# Strip binaries
strip_command=strip \
post_package_strip
}
this is mine
I'm rebuilding it
Still cargo not found
this has to be something dumb
If I add ls /usr/local, it's empty
Even though it does install it
Yeah, it's ignoring hostdeps for some reason...
It works if I comment source_dir out?????
Yeah, it breaks as soon as I add it...
Just if I remove .jinx-cache and sources and build directory, and run ../jinx build pmbus with this recipe, it just gets the debian image, and doesn't even try to compile the compilers and anything
#!/bin/sh
name=pmbus
version=1.0.0
revision=1
source_dir=userspace/ps2d
deps="libc pmos-rust-lib"
hostdeps="cargo rust"
allow_network=yes
prepare() {
CARGO_HOME="${build_dir}/.cargo" \
cargo fetch --target ${JINX_ARCH}-unknown-pmos
}
build() {
CARGO_HOME="${build_dir}/.cargo" \
cargo build --target ${JINX_ARCH}-unknown-pmos --jobs ${parallelism}
}
package() {
CARGO_HOME="${build_dir}/.cargo" \
DESTDIR="${dest_dir}" \
RUSTFLAGS="-C link-arg=--sysroot=${SYSROOT} -C linker=clang++ -C link-arg=--target=${JINX_ARCH}-unknown-pmos -C link-arg=-lunwind -C link-arg=-static" \
cargo install --target ${JINX_ARCH}-unknown-pmos --root ${dest_dir} --path ${source_dir}
}
because the jinx cache isnt where the built tools are
make sure the cargo host tool is built correctly
i think the directory is called host-pkgs
there should be cargo in there
and it should be installed under $prefix, so /ust/local for tools
so the final path for the executable should be host-pkgs/cargo/usr/local/bin/cargo
But it's not even trying to build it
ls host-pkgs/cargo
it probably built but is incomplete somehow
maybe your recipe is messed up
but I don't see anything wrong with it
if I comment source_dir out then it starts doing some stuff
where is binutils even
and source dir isn't even important here
like what it's set to
and shell scripts are too complicated for me idk
how is shell complicated π
anyway let me clone and try building
or just take a look but on pc this time
which jinx version are you using?
i see you didn't check in the jinx script and you don't have a makefile target to download it
yeah
that'd be nice
0.8 I think
ok time to build this thing
yeah
ok it took me way too long to find out
but
you are running cargo in prepare
that's part of the source recipe, not the recipe itself
so you need source_hostdeps="cargo rust"
after changing source_dir to pmbus:```
[iretq@raptor build]$ ../jinx build pmbus
- building package: pmbus
error: failed to getpmosas a dependency of packagepmbus v0.1.0 (/base_dir/userspace/pmbus)
Caused by:
failed to load source for dependency pmos
Caused by:
Unable to update /base_dir/userspace/rust/pmos
Caused by:
failed to read /base_dir/userspace/rust/pmos/Cargo.toml
Caused by:
No such file or directory (os error 2)```

More trolling 
(I'll probably figure it out tomorrow)
I think it's finally building it
real
I've no idea what I'm doing
why is it unsupported
you're missing a dynamic_linking: true
holy
Time to recompile rustc for the millionth time...
Also, I need a script to assemble all of this into an image
The only saving thing is my 5900X
It takes forever on my laptop...
yeah this tbh
i like rust as a language
but jfc tooling is horrible
Nah, I think I've gotten it to work
It's just because nobody's using rust with Jinx, and it's not very well documented?
btw, I think your rust recipe might be brokenΒΏ
why

Jinx is trolling again (totally not because shit build scripts done by me)
What am I looking at?
Why does everything build limine as a normal recipe and not host recipe


Time to downgrade limine 
Why do u need such an old revision
Or upgrade it
I yoinked the 10.6.0 recipe
Cool, I've managed to build the system image...
The only issue is that userspace doesn't work for some reason...
Cool, it fully works
wdym
everyone, not everything
only i build it as a normal recipe
I can't speak today
jinix does the same
astral for example doesn't
i do it because i have no need for limine's host tool
and it's more like a normal package for my os
This is very nice of flanterm...
how do you install limine w/o the host tool?
cp
i don't support bios boot anyways
i just copy the BOOTX64.EFI to the esp
that's it
I build it as both host and recipe
I need to figure out risc-v and other arches now...
Since zinnia does this? https://github.com/zinnia-os/bootstrap/blob/main/GNUmakefile
But I haven't seen $ARCH be used anywhere?
Huh?
Is it normal that there are 2 variables?
use a newer qemu, that's the only solution sorry
it is the latest version
really?
I like how it says ANIC
wild P
Time to set up the build server...
lol, who even uses docker (coudflare) on weekends...
(it's blocked by my isp again)
vpn time?
I guess I'll just wait
I think I'll merge it to main today
Btw, I think the project structure here is outdated https://codeberg.org/Mintsuki/jinx/src/branch/trunk/DOCUMENTATION.md#basic-project-structure
(I can send patches)
I've merged it
You can now actually build everything with make qemu-x86
(if someone wants to try it for some reason)
Bruh, I want to do disk...
Aparently, this is a skill issue somewhere inside Rust?#1385970208631427173 message
I think it's a printf skill issue 
I think I should finally add rights to memory objects?
But I don't really know how to handle them (like do I do weak/strong references??)
GNU/Hurs is very well documented, as usual https://www.gnu.org/software/hurd/microkernel/mach/memory_object.html
Surprisingly, it was very easy...
This is nice...
I guess it's time to figure out Rust's coroutines 
And integrate https://discord.com/channels/440442961147199490/1479184639145938974 
Also, I think I figured out how I should do multithreaded servers?
I'll just make programs (e.g. libc) explicitly request rights that correspond to the right cores
The kernel doesn't have to do anything
The Rust's futures are weird af
I think I'd need my own runtime for my IPC?
I wonder how fucked my userspace would be if I introduce blocking send()

Which I think I kinda have to do for Rust...
Hm?
Which I think I kinda have to do for Rust...
^ this sounds weird
Rust doesn't force you into a particular IPC model?
My kernel only lets me get the message that's at the front of the queue, and I think I'll have to have a future per right, so I'll have to get messages eagerly and push those the the future's queue (so there aren't deadlocks), so someone can easily DOS my rust servers by sending a lot of messages and making it OOM
So the solution is limiting how many messages can be sent
Idk, I still don't quite get what I have to do
how do you avoid this in C?
there should be no need to have a separate queue that buffers stuff
Rust's future design certainly doesn't require it
I don't
I mean maybe it doesn't matter
It's only an issue if you don't immediately await on the future
I mean unbounded queues are problematic in general?
Rust doesn't require you to add an unbounded queue
they are unbounded in the kernel
that sounds like a problem indeed
but anyway, I don't see how Rust futures make it more (or less) problematic
Yeah, but I might as well fix it
I mean C uses callbacks
why does that matter?
you can convert callback based code to Rust futures or vice versa
Then it's kinda your fault (in my eyes) if you don't register the callbacks in the right order
i don't get it. you can have a rust future that registers a callback and completes the future on completion
you just have some kind of control block that stores the future's current waker
or similar
I want send to make new futures
It's not a problem with the callbacks/futures, but with the order of doing things being important if I carry on with unbound queues
in kernel
Since I'd have to buffer everything in userspace, and it's bad
(infinitely)
So I think I'll make it bounded
This would also solve the problem of not needing to allocate on every send
Like if I make it bounded, then the buffers can be preallocated, and it can't fail on OOM or weirdness like that, which is kinda important for drivers
(Since I can't just block them on oom)
you can just do that
there is no need to buffer anything in user space
Yeah, I wanted to do that
But still, it's problematic
Like you create 2 futures, then if await on only one of them, the second one can deadlock everything
why?
Also, I think my IPC is a bit different from Managarm's?
Because you can only pop_front from my IPC
you want the future to do the actual work at await time, not at future creation time
Idk if I'm not explaining it well
But I have (recieve) ports, which then have many recieve rights (bound to a port)
You can only get messages from the front of the port
I want to make futures wait on rights
So if there is a message for the given right, and I can't move it to the future (it's not being polled), I have to block
So it creates a deadlock
Or I'll have to throw messages away
Or I have to buffer them indefinitely in userspace
Or you have to wait on all of the futures immediately
^
No, it does the work at await time
The Stream/Waker would be polling the message queue
I think managarm just lets you wait on any stream, no?
wdym by "on any stream"? Managarm allows you to submit multiple IPC ops concurrently
My kernel doesn't
Yes, but can you wait on several ops from one thread at the same time?
yes. but if you can't do that, why are you trying to use an async runtime anyway
I don't know how to explain it
It works if you buffer it
My AHCI driver is fully async in C++
why does it matter which operation completes in what order?
i don't quite understand what your problem with rust's async is
ah i think i see your problem
Let's say you have rights A and B, both can recieve multiple messages
You receive a a b in this order (which is buffered in kernel)
You would get a, move that to the future, then you would get a again. You either have to throw it away, or buffer it, or block on it. If you block on a, but you're awaiting on B before a, you can't make progress, since you can't recieve b because a is at the front
I mean I had an argument with a clanker and it really insisted that I don't do that
If you buffer a a in stream, then you can recieve b and there is no issue. But since my queues are unbounded, and there is no way to stop new messages, someone can just send a lot of messages, and it might DoS my server
i would have to look at your ipc model more closely but it really doesn't sound too bad, do you have a kernel api that lets you receive something? you're saying "recv A, recv A, recv B" - what syscalls are involved in this process? what are A and B in this case?
actually lemme take a look at the ipc link you posted
The second link is userspace C++ wrapper over syscalls
I think my async C++ thing is also somewhere in there
Like I can just ignore it and keep the order in mind and it will be fine, but it won't be "fearless concurrency"
sounds to me like you need a select-like syscall
or recv-many or whatever
But my queues are just a list/deque of messages
same idea i guess
So I would need to redo it
Or, if you make it bounded, then you can preallocate the buffers in userspace, and just do it in there
But with any reasonable executor, all futures can make progress at the same time
You get a, process it, you create another future that gets the next a, you process it, you get b
that's the "i can just keep the order right myself" thing
seems like that's also how it works in c++
It's not really a future, but a Stream in Rust
Yeah, it's also problematic, but I've only noticed it now
I think your issue stems from confusion about push and pull
It would be both I guess?
Rust futures/streams pull things from an object
It seems that you want to make it push based
I guess?
But my kernel doesn't have the API to make it pull based
And I would need to move the message queues to the rights
If I want to be able to pull on rights instead of ports
But like also why not do this
I wanted to add a field that says that it's not the last message in the queue
So you can push several messages into the futures
Also, it doesn't matter, it's an abstraction over IPC
If something builds on top of it, it would be pull based
Ah i think i get your problem now
You want to distribute messages from a common receiver to multiple consumers but you don't know the consumers in advance
yes
Yeah that sounds like a design issue indeed
Or if I know them in advance, then I have to buffer
But one that you'd also have with callbacks
yeah
that's why I said C++ is also problematic
But with C/C++ you can just say "it's on you to do the things in the right order"
Well one thing that you can do is have a stream that returns (message, target) pairs
And have higher level logic deal with this issue
I don't want to do that
Then why would you want async in the first place
If you can only wait on one port
This is just moving the issue to that higher level logic
That's true
I mean that higher level logic is what I'm trying to write
But higher level logic may be better equipped to solve it (maybe. Depends on your design)
But unbounded queues are also problematic on other abstractions/stuff that builds on top of it, e.g. Unix pipes
Which have to block if they're full
Or not...

No, with pipes, you'll just wait for the reply
Idr, there were a bunch of issues with having no way to set a boundary on how many messages can be in the queue
But with my ports/rights thing, it should be somewhat straightforward to be able to add limits on rights
(with the biggest issue being the scheduler/blocking, which needs improving)
Which I also need for futex
Though I think my issue is that I don't quite understand VFS
Namely how the directory tree should be, what to do with mountpoints and hardlinks...

Small progress update -- I ended up doing it in Rust
And I'm currently fighting the borrow checker and stuff like that
This insanity works??
(create_named_stream does a request to bootstrapd)
(also, I think mut isn't needed here...)
Anyway, since I can't be bothered with writing a proper posix_spawn, I think I'll be launching filesystem drivers through bootstrapd
Namely, I think I'll first be launching drivers to probe the partitions, and then doing it again on mount
I need to look into the other operating systems 
The clanker just repeated what I said to it
whenever somebody says that AI will fully replace software engineers in the short term I am reminded of stuff like this
Wait, are all filesystems all inside of libblockfs and POSIX server in managarm?
on-disk fses are handled by libblockfs yes
but its a dso that is linked into storage drivers, not a central server
But this seems to be very complicated
I don't think separate servers are substantially more complicated