Universal Boot

Anything QL Software or Programming Related.
User avatar
Mark Swift
Bent Pin Expansion Port
Posts: 86
Joined: Fri Jul 18, 2014 9:13 am
Location: Blackpool, Lancs, UK
Contact:

Universal Boot

Post by Mark Swift »

Recently in-between life, work and DIY I have been working on a "universal boot" proof of concept,

The objective is to be able to remove all references to physical media from a boot file and replace those references with "HOME_DIR$", "HOME_FILE$", "HOME_CURR$" etc while still being compatible with any system and any media,

The implementation relies on the fact that while a BASIC program is loading, BV_COMCH holds the channel ID of the program file. So in this cut-down incarnation, HOME_DIR$, HOME_FILE$ and HOME_CURR$ are only updated if used on a numberless line within a BASIC program.

I wasn't concerned in creating a full feature "HOME_" extension system. I just needed the "HOME_" extentions to be available to BASIC so that the "boot" program knew where it was running from.

So far I have only tested it under emulation, but it seems to work.

Here's the first working draft (Version 1.01)
UniversalBoot.zip
(187.72 KiB) Downloaded 30 times

It includes a working Q-emulator MDV file, a 720K floppy disk image, a QXL.WIN file and the BASIC files listed below.

"BOOT"

Code: Select all

PRINT "Installing 'WHERE'"
REMark --- Install the BASIC extension 'WHERE'
REMark --- You'll lose 214 bytes every time you do this
REMark --- But there's no reason to run the main boot program more than once
R=RESPR(214):P=R
FOR i=0 TO 15:C="067250000012052121000000001016078146078117000000"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
FOR i=0 TO 15:C="000000000002000012005087072069082069000000112241"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
FOR i=0 TO 15:C="052121000000001022078146083067102242048054152000"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
FOR i=0 TO 15:C="103236176124001000100230086064008128000000072192"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
FOR i=0 TO 15:C="209174000088082137038073040110000024042110000028"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
FOR i=0 TO 15:C="048054200000176124008000103006176124009000102046"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
FOR i=0 TO 15:C="036110000032212246200002016054152000176054168000"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
FOR i=0 TO 15:C="102028072128083064082137082138018054152000178054"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
FOR i=0 TO 15:C="168000102010081200255240034054200004096010034075"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
FOR i=0 TO 15:C="080140185205102186114000040001114006052121000000"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
FOR i=0 TO 15:C="001026078146034110000088034004032001103018048060"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
FOR i=0 TO 15:C="008031047001210129105006083064046129096246034031"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
FOR i=0 TO 15:C="093174000088034110000088061128152000045129152002"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
FOR i=0 TO 6:C="120002112000078117000"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
CALL R

PRINT "Installing 'HOME_FILE$', 'HOME_DIR$' and 'HOME_CURR$'"
REMark --- Install the BASIC extension 'HOME_DIR$'
REMark --- This only happens if its not already loaded
W=WHERE("HOME_DIR$")
IF W=0 THEN R=RESPR(580):P=R
IF W=0 THEN FOR i=0 TO 15:C="067250000012052121000000001016078146078117000000"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="000000000005000042010072079077069095070073076069"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="036000000038009072079077069095068073082036000040"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="010072079077069095067085082082036000000000187203"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="102080097000000082096026187203102070097000000072"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="071235000038096012187203102056097000000058071235"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="000076058019082069002069255254034005052121000000"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="001026078146155174000088034110000088075246152000"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="058027058197096002026219081205255252120001112000"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="078117112241078117072231124140112000078065097000"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="000168038011040104000120040046000132229076216196"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="040084040044000004103000000136075232000072114016"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="042021103000000124083065103118042069186132102240"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="075237000036120000056029058004084069054197096002"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="022221081204255252120000024044000029229140075232"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="001000219196042085024045000020216060000048022196"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="022252000095075236000050056029218068096002022221"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="081204255252038067054133073235000038075235000076"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="056027056196058196096004024211026219081205255250"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="038067073235000038075235000076097000000174058148"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="038067076223049062078117072231096064071232000184"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="032019103022038064012107000004000042102242012171"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="072077074083000044102232096116038072116000034060"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="000000000166112024078065074128102104193075039124"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="049046048049000038055124000004000042039124072077"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="074083000044067235000048039073000016035124084072"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="071037000000035124000000000002000004051124000004"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="000008035124065066067068000010051124000004000046"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="035124069070071072000048051124000004000084035124"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="073074075076000086067232000184038145034139038107"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="000016080139076223002006078117072231092132042076"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="056029103072096006152124000001103064012029000095"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="102244034013146140085065042001056133096006152124"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="000001103040012029000095102244034013146140085065"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="056129032076038060000000000001114255112001078066"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="074128102008058020112002078066096216056133076223"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 4:C="033058078117000"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN CALL R

REMark --- Install the BASIC extension 'LRESPR'
REMark --- This only happens if its not already loaded
W=WHERE("LRESPR")
IF W=0 THEN R=RESPR(368):P=R
IF W=0 THEN FOR i=0 TO 15:C="067250000012052121000000001016078146078117000001"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="000016006076082069083080082000000000000000000000"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="126001097000000086102000000080040012097000001014"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="112241187203102000000036034042000000072231064032"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="112014078065034072076223004004074128102000000012"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="042009032068118255112072078067046000032010103006"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="032074112025078065074132103006032068112002078066"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="032007102004032069078208078117097000000030102024"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="114000050054152000032073038007114255078068112001"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="078066074128102002040072078117072231074032187203"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="103000000144034110000088074118184002107010112015"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="192054184001083000102040047013075235000008052121"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="000000001022078146042095074128102104045073000088"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="114003210118152000008129000000211174000088096074"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="114000050054184002107074231137210174000024124000"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="060054024002220174000032114000018054104000082129"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="008129000000056001084129052121000000001026078146"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="034110000088220068083137029182104000152000083134"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="081204255244083137066054152000071235000008112000"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="096002112241074128076223004082078117072231049080"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="114064116255112024078065074128102030036072032068"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="034074116064118255112071078067074128103012046000"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 15:C="032074112025078065149202032007076223010140078117"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN FOR i=0 TO 0:C="000"(i*3+1 TO i*3+3):POKE P,C:P=P+1:END FOR i
IF W=0 THEN CALL R

PRINT "Init Done"

REMark The first call at boot time fails because the directory device driver list (SV_DDLST) loops on itself
Temp$=HOME_DIR$:

REMark I'm uncomfortable not knowing why there's no loop in SV_DDLST by the second call
PRINT "Running directory = ";HOME_DIR$

LRUN HOME_DIR$&"boot_here"
"BOOT_HERE"

Code: Select all

PRINT "Running directory = ";HOME_DIR$

1000 REMark --- Continue here with a bog standard BASIC boot install program
1010 REMark --- Requires 'WHERE', 'HOME_FILE$', 'HOME_DIR$', 'HOME_CURR$' and 'LRESPR'
1020 REMark --- which by the time you get here, are all guaranteed to exist.
1030 :
1040 CLEAR
1050 REMark -- Install TK2 TOOLKIT --
1060 IF WHERE("TK2_EXT")=0 THEN
1070  LRESPR HOME_DIR$&"TK2_TK236_bin"
1080  TK2_EXT
1090 END IF
1100 REMark -- Set default directories --
1110 PROG_USE HOME_DIR$
1120 DEST_USE HOME_DIR$
1130 :
1140 REMark --- Do something useful
1150 REMark --- Requires 'FREE_MEM' which is part of TKII above
1160 :
1170 REMark -- SYSTEM INFO --
1180 CLEAR:DIM Dat$(20)
1190 Dat$=DATE$:CLS#2:PRINT#2;\" BASIC version ";VER$\" ";HUMAN$(FREE_MEM);" free"\" ";DAY$;" ";Dat$(10 TO 11);Dat$(5 TO 9);Dat$(1 TO 4)\\
1200 :
1210 STOP
1220 :
1230 DEFine FuNction HUMAN$(n)
1240  LOCal nl,nh,h$
1250  nl=n:nh=INT(nl/1024)
1260  IF nh<2 THEN
1270   h$=nl&" B"
1280  ELSE
1290   nl=nh:nh=INT(nl/1024)
1300   IF nh<2 THEN
1310    h$=nl&" KB"
1320   ELSE
1330    nl=nh:nh=INT(nl/1024)
1340    IF nh<2 THEN
1350     h$=nl&" MB"
1360    ELSE
1370     h$=nh&" GB"
1380    END IF
1390   END IF
1400  END IF
1410  RETurn h$
1420 END DEFine

RUN

Is this a possible solution, or am I missing something?


User avatar
bwinkel67
QL Wafer Drive
Posts: 1511
Joined: Thu Oct 03, 2019 2:09 am

Re: Universal Boot

Post by bwinkel67 »

On a close tangent, is there a way to remove rarely used features of a ROM (or toolkit) to replace it with new things like Mark is working on. That way you can simplify some of these extensions. You rework a new version of a ROM (JS, MinervaO or toolkit (TK2) to add some needed features.


User avatar
RalfR
QL Wafer Drive
Posts: 1171
Joined: Fri Jun 15, 2018 8:58 pm

Re: Universal Boot

Post by RalfR »

If you want to load the "Home" extension separately into QemuLator, you can use this file.

I just saved it, didn't test it. The "Home" extension on Dilwyn's site doesn't work.
Attachments
Home.zip
(636 Bytes) Downloaded 28 times


7000 4E75
User avatar
Mark Swift
Bent Pin Expansion Port
Posts: 86
Joined: Fri Jul 18, 2014 9:13 am
Location: Blackpool, Lancs, UK
Contact:

Re: Universal Boot

Post by Mark Swift »

Hi RalfR,
RalfR wrote: Fri Jan 31, 2025 8:31 am If you want to load the "Home" extension separately into QemuLator, you can use this file.
I just mis-read this hoping that it would be a working version of the full HOME_ extensions...
...wondered why it was so small, then realised that I had just downloaded my own code :D

If you do test the extension via LRESPR, please be aware that it's not a full HOME_ implementation.

...and it only works if you reference the extension in a numberless line in your BASIC.
Also, numberless lines stop LRUN from running, so you need a numberless "RUN" at the end of your BASIC.

Something like this:

Code: Select all

DUMMY$=HOME_DIR$:DUMMY$=HOME_DIR$

1000 PRINT "HOME_FILE$ = ";HOME_FILE$
1010 PRINT "HOME_DIR$  = ";HOME_DIR$
1020 PRINT "HOME_CURR$ = ";HOME_CURR$

RUN
There's currently a bug that means you have to reference it twice the very first time it is run.
...work in progress.


User avatar
RalfR
QL Wafer Drive
Posts: 1171
Joined: Fri Jun 15, 2018 8:58 pm

Re: Universal Boot

Post by RalfR »

Mark Swift wrote: Sat Feb 01, 2025 9:49 amIf you do test the extension via LRESPR, please be aware that it's not a full HOME_ implementation.

...and it only works if you reference the extension in a numberless line in your BASIC.
Also, numberless lines stop LRUN from running, so you need a numberless "RUN" at the end of your BASIC.

Something like this:

Code: Select all

DUMMY$=HOME_DIR$:DUMMY$=HOME_DIR$

1000 PRINT "HOME_FILE$ = ";HOME_FILE$
1010 PRINT "HOME_DIR$  = ";HOME_DIR$
1020 PRINT "HOME_CURR$ = ";HOME_CURR$

RUN
There's currently a bug that means you have to reference it twice the very first time it is run.
...work in progress.
Oh, I'm sorry, I should have explained that better. It's your extension, of course, I just thought it would be easier for other purposes under QDOS if you could load it using LRESPR, so I just saved it.

I know it's not a complete implementation, but it's completely sufficient for the purposes mentioned. Especially since the extension by Wolfgang Lenerz, which is available at Dilwyn, is known not to work.

Better than no Home extension :)

Have you looked at the source code of Wolfgang's Home extension (the one at Dilwyn)? There must be one or more errors in there.


7000 4E75
User avatar
XorA
Site Admin
Posts: 1609
Joined: Thu Jun 02, 2011 11:31 am
Location: Shotts, North Lanarkshire, Scotland, UK

Re: Universal Boot

Post by XorA »

bwinkel67 wrote: Fri Jan 31, 2025 4:23 am On a close tangent, is there a way to remove rarely used features of a ROM (or toolkit) to replace it with new things like Mark is working on. That way you can simplify some of these extensions. You rework a new version of a ROM (JS, MinervaO or toolkit (TK2) to add some needed features.
Yes, its called programming?


User avatar
bwinkel67
QL Wafer Drive
Posts: 1511
Joined: Thu Oct 03, 2019 2:09 am

Re: Universal Boot

Post by bwinkel67 »

XorA wrote: Sat Feb 01, 2025 10:37 am Yes, its called programming?
How easy would it be? I haven't looked at the source of any ROMs but are parts of it modular to where you can easily remove commands and replace them with your own?


User avatar
tofro
Font of All Knowledge
Posts: 3056
Joined: Sun Feb 13, 2011 10:53 pm
Location: SW Germany

Re: Universal Boot

Post by tofro »

bwinkel67 wrote: Sat Feb 01, 2025 12:38 pm
XorA wrote: Sat Feb 01, 2025 10:37 am Yes, its called programming?
How easy would it be? I haven't looked at the source of any ROMs but are parts of it modular to where you can easily remove commands and replace them with your own?
Hmm. What would you dare to remove so some of your (or other people's) programs using it would cease to run? :)


ʎɐqǝ ɯoɹɟ ǝq oʇ ƃuᴉoƃ ʇou sᴉ pɹɐoqʎǝʞ ʇxǝu ʎɯ 'ɹɐǝp ɥO
User avatar
XorA
Site Admin
Posts: 1609
Joined: Thu Jun 02, 2011 11:31 am
Location: Shotts, North Lanarkshire, Scotland, UK

Re: Universal Boot

Post by XorA »

tofro wrote: Sat Feb 01, 2025 2:10 pm
bwinkel67 wrote: Sat Feb 01, 2025 12:38 pm
XorA wrote: Sat Feb 01, 2025 10:37 am Yes, its called programming?
How easy would it be? I haven't looked at the source of any ROMs but are parts of it modular to where you can easily remove commands and replace them with your own?
Hmm. What would you dare to remove so some of your (or other people's) programs using it would cease to run? :)
The obvious thing to remove would be micro-drive support, followed by network support!


User avatar
bwinkel67
QL Wafer Drive
Posts: 1511
Joined: Thu Oct 03, 2019 2:09 am

Re: Universal Boot

Post by bwinkel67 »

XorA wrote: Sat Feb 01, 2025 4:28 pm The obvious thing to remove would be micro-drive support, followed by network support!
I'd have to look, but there are some commands that wouldn't really impact much. For instance, RENUM, is handy but if I could replace that in JS/JSU ROM with last-line recall, or a built-in JOBS/RJOB command, that would be worth it.


Post Reply