Introducing... PUNIX! A Puny UNIX
Re: Introducing... PUNIX! A Puny UNIX
Martin_H wrote:
I don't know if you're looking for inspiration, but NitrOS-9 is an 8-bit Unix like OS for the Radio Shack Color Computer and other 6809 based machines. It's written in assembler and based on the venerable OS-9 which exploits the 6809's ability to have position independent code. This makes a direct port impossible, but there might be some ideas that could be borrowed.
"The key is not to let the hardware sense any fear." - Radical Brad
Re: Introducing... PUNIX! A Puny UNIX
Paganini wrote:
I haven't studied OS9, but I do know about it. I have a CoCo2 in my closet upstairs. 
However, a 65816 can address far more memory than a CoCo3 with a GIME chip. That's why I think it would be awesome for a Unix like OS project.
Last edited by Martin_H on Fri Jan 30, 2026 5:43 pm, edited 1 time in total.
-
No True Scotsman
- Posts: 127
- Joined: 22 Mar 2023
Re: Introducing... PUNIX! A Puny UNIX
A nice feature of the CoCo2 ecosystem is that the modem and RS-232 cartridges both contain the same terminal program in ROM at the same address, making them ready to use out of the box as well as interchangeable. By contrast, the same cartridges for the C-64 plugged into the user port instead of the expansion port.
Re: Introducing... PUNIX! A Puny UNIX
I had the good luck to take Doug Comer's final XINU class. One of the highlights of my time in college. It was a simple, non memory protected system that implemented some basic OS concepts without overly being complex.
One thing I'll suggest about your task switching code is that you don't have to copy all 256 bytes of the hardware stack during a task switch. If you just transfer the stack pointer into Y and copy from $100,Y up to $1FF you will save a great deal of needless data moving.
I wrote a preemptive thread scheduler for my 6502 Java VM but went with a much simpler cooperative fiber scheduler for PLASMA. Both have their places but I found the 6502 was better suited for a single thread/task. The 65816 does seem to be a better match to more sophisticated OS concepts.
One thing I'll suggest about your task switching code is that you don't have to copy all 256 bytes of the hardware stack during a task switch. If you just transfer the stack pointer into Y and copy from $100,Y up to $1FF you will save a great deal of needless data moving.
Code: Select all
TSX
TXA
TAY
.save_hw_stack: ; Active HW stack
LDA $0100,Y
STA (R0),Y
INY
BNE .save_hw_stack
- GARTHWILSON
- Forum Moderator
- Posts: 8773
- Joined: 30 Aug 2002
- Location: Southern California
- Contact:
Re: Introducing... PUNIX! A Puny UNIX
resman wrote:
One thing I'll suggest about your task switching code is that you don't have to copy all 256 bytes of the hardware stack during a task switch.
http://WilsonMinesCo.com/ lots of 6502 resources
The "second front page" is http://wilsonminesco.com/links.html .
What's an additional VIA among friends, anyhow?
The "second front page" is http://wilsonminesco.com/links.html .
What's an additional VIA among friends, anyhow?
-
GlennSmith
- Posts: 162
- Joined: 26 Dec 2002
- Location: Occitanie, France
Re: Introducing... PUNIX! A Puny UNIX
Gosh, you guys 'n gals, since I came back to the forum (a number of years ago now), I have sooo many times seen subjects that attracted my attention, firstly said something to myself along the lines of "I'm too old to go down that hole...", and finally taken the plunge :
- but soon I think my neighbors will have forgotten who I am !
Thanks, for all of the above - and more, to Drogon, BDD, 8-Bit, resman, Garth and the many other contributors who keep my few remaining brain cells running at 110% !
- CPLD logic design and programming (with home-built HW)
- Choosing and adapting a new HL language (PLASMA), and finally writing a personal VM to use it
- Writing my own WDC 65C02 disassembler (twice!)
- Trying-out and adopting novel HW (the RP6502 'pico' computer using a Pi Pico(2) to provide a monitor and file I/O)
- Writing my own self-hosting WDC 65C02 assembler in PLASMA
- Currently consolidating documents and ideas to create my own text-editor
- Starting to play with the 65C816 using the same 'pico' architecture (WIP)
- ... and now the idea of a multi-tasking environment has started it's magnetic attraction...
Thanks, for all of the above - and more, to Drogon, BDD, 8-Bit, resman, Garth and the many other contributors who keep my few remaining brain cells running at 110% !
Glenn-in-France
Re: Introducing... PUNIX! A Puny UNIX
GARTHWILSON wrote:
Jonathan Halliday... divides the stack area up into a few portions, one for each task, and then when he switches tasks, he only copies out the one that ran longest ago to make room for the new one; and if you only have a few tasks running, you may not need any copying at all. Look at the page, and you'll find it very impressive.
"The key is not to let the hardware sense any fear." - Radical Brad
Re: Introducing... PUNIX! A Puny UNIX
This thread is giving me ideas and making me waste time.
First, I skimmed the Fuzix code and they have 6502 and 65816 ports, but it is for cc65. Last I looked at its code output it wasn't the best, especially for the 65816.
Second, I started reading the NitrOS-9 source. It's big and interesting but written in 6809 assembly language. Probably the most useful part of it is the kernel definition, data structures, and interface files.
Must go back to my main project...
First, I skimmed the Fuzix code and they have 6502 and 65816 ports, but it is for cc65. Last I looked at its code output it wasn't the best, especially for the 65816.
Second, I started reading the NitrOS-9 source. It's big and interesting but written in 6809 assembly language. Probably the most useful part of it is the kernel definition, data structures, and interface files.
Must go back to my main project...
Re: Introducing... PUNIX! A Puny UNIX
Paganini wrote:
GARTHWILSON wrote:
Jonathan Halliday... divides the stack area up into a few portions, one for each task, and then when he switches tasks, he only copies out the one that ran longest ago to make room for the new one; and if you only have a few tasks running, you may not need any copying at all. Look at the page, and you'll find it very impressive.
If the stack is copied, it still is divided into kernel space stack an active task stack. The active task's stack is basically copied from stack pointer to upper bound, so only the used stack is copied.
That works well as usually only one task is active, except if you use pipes or background processing.
André
Author of the GeckOS multitasking operating system, the usb65 stack, designer of the Micro-PET and many more 6502 content: http://6502.org/users/andre/
Re: Introducing... PUNIX! A Puny UNIX
Here is a big update! I was on the road for about the last 10 days and didn't have access to my hardware. I think the most exciting thing is that, when I got homem, all the code I wrote while travelling assembled immediately, and when I put it on a ROM, all the stuff that was already working continue to work! YAY I didn't break anything! The code is not fully tested yet, and I have tracked down a few bugs already. But what's working right now is:
The RTC (NMIs are happening, system ticks is updating)
The scheduler (processes successfully switch back and forth)
The SLEEP system call (Calling SLEEP with 1 tick works as a sort of cooperative YIELD call)
The CREATE system call (new processes)
The VFS interface to the I/O (currently, only the WRITE call has been tested)
The GETMEM system call (memory allocator). FREEMEM hasn't been tested yet.
The code file is a little disorganized - I was adding syscalls to the bottom, and there are two or three separate places with lots of self-documentation. I should reorganize it eventually, but for now, / (or cmd+F) is my friend.
The RTC (NMIs are happening, system ticks is updating)
The scheduler (processes successfully switch back and forth)
The SLEEP system call (Calling SLEEP with 1 tick works as a sort of cooperative YIELD call)
The CREATE system call (new processes)
The VFS interface to the I/O (currently, only the WRITE call has been tested)
The GETMEM system call (memory allocator). FREEMEM hasn't been tested yet.
The code file is a little disorganized - I was adding syscalls to the bottom, and there are two or three separate places with lots of self-documentation. I should reorganize it eventually, but for now, / (or cmd+F) is my friend.
"The key is not to let the hardware sense any fear." - Radical Brad
Re: Introducing... PUNIX! A Puny UNIX
After a bit of testing, I rewrote the scheduler again. My "pseudopriority" worked great, and just how I thought it would - because I only thought about how it would work with 1, 2, or 3 processes! Of course, with a larger number of processes, it will always select the highest numbered ready PID that didn't just run, which means it will flip back and forth between those two processes and starve everyone else! I went back to simple round robin, but with a zero check so that the NULL process doesn't waste time every go-round.
Code: Select all
LDY #$0F ; Check processes 1 - F
.next_proc:
INC current_pid
LDA current_pid
AND #$0F ; Only 16 PIDs
STA current_pid
BEQ .next_proc ; Skip PID 0
; Check if READY
ASL
ASL
ASL
ASL
TAX
BIT PROCTAB+PSTAT,X
BVS .found ; Bit 6 set = READY
DEY
BNE .next_proc
; None ready - use PID 0
STZ current_pid
LDX #$00
.found:
; Step 5 - Mark it RUN
LDA #RUN
STA PROCTAB+PSTAT,X"The key is not to let the hardware sense any fear." - Radical Brad
- BigDumbDinosaur
- Posts: 9425
- Joined: 28 May 2009
- Location: Midwestern USA (JB Pritzker’s dystopia)
- Contact:
Re: Introducing... PUNIX! A Puny UNIX
Paganini wrote:
After a bit of testing, I rewrote the scheduler again. My "pseudopriority" worked great, and just how I thought it would - because I only thought about how it would work with 1, 2, or 3 processes! Of course, with a larger number of processes, it will always select the highest numbered ready PID that didn't just run, which means it will flip back and forth between those two processes and starve everyone else! I went back to simple round robin, but with a zero check so that the NULL process doesn't waste time every go-round.
Coming up with an efficient and fair scheduling algorithm is no simple matter and will naturally involve a variety of tradeoffs. Ultimately, the goal is to achieve maximum MPU utilization, which means avoiding spin loops. With a register-poor, eight-bit MPU that is saddled with blocking I/O, that goal may be elusive.
x86? We ain't got no x86. We don't NEED no stinking x86!
Re: Introducing... PUNIX! A Puny UNIX
Paganini wrote:
After a bit of testing, I rewrote the scheduler again. My "pseudopriority" worked great, and just how I thought it would - because I only thought about how it would work with 1, 2, or 3 processes! Of course, with a larger number of processes, it will always select the highest numbered ready PID that didn't just run, which means it will flip back and forth between those two processes and starve everyone else! I went back to simple round robin, but with a zero check so that the NULL process doesn't waste time every go-round.
Each task has a fixed timeslot and I could start to fiddle with all that to give some tasks a higher or lower timeslot value but I've not needed to do that yet. Maybe in the future I'll write a "nice" command...
-Gordon
--
Gordon Henderson.
See my Ruby 6502 and 65816 SBC projects here: https://projects.drogon.net/ruby/
Gordon Henderson.
See my Ruby 6502 and 65816 SBC projects here: https://projects.drogon.net/ruby/
Re: Introducing... PUNIX! A Puny UNIX
That sounds vaguely like the original windows 16 message handler, Gordon, except for the ability to force a switch if a task decided to hog the processor.
Neil
Neil
- BigDumbDinosaur
- Posts: 9425
- Joined: 28 May 2009
- Location: Midwestern USA (JB Pritzker’s dystopia)
- Contact:
Re: Introducing... PUNIX! A Puny UNIX
barnacle wrote:
That sounds vaguely like the original windows 16 message handler, Gordon, except for the ability to force a switch if a task decided to hog the processor.
x86? We ain't got no x86. We don't NEED no stinking x86!