How to get a channel ID for a standard channel?

Anything QL Software or Programming Related.
Post Reply
vol
ROM Dongle
Posts: 22
Joined: Thu Jan 20, 2022 5:07 pm

How to get a channel ID for a standard channel?

Post by vol »

I am doing some assembly programming and I am not still able to comprehend how to use channel IDs in TRAPs. :( I have definitely missed something. I need just a print service, so I use IO.SSTRG (TRAP #3, D0=7). I could hack information that A0 should be 0 for the Basic channel #0, $10001 for #1, and $20002 for #2. But is there a proper way to get these "magic" ID numbers? I tried to work with the SV_CHBAS ($78) pointer to the channel table but it seems this table don't just have channel IDs! I also looked at Basic area at SV_BASIC ($10) but it seems it is just empty! So I am terribly baffled. Any help, hint, advice is very welcome. Thank you.


User avatar
M68008
Trump Card
Posts: 223
Joined: Sat Jan 29, 2011 1:55 am
Contact:

Re: How to get a channel ID for a standard channel?

Post by M68008 »

If you are writing a SuperBASIC extension that accepst a SuperBASIC channel number as a parameter (typically as first parameter and preceded by the '#' separator), you would have to use SV_CHBAS as you say (the channel number is the index in the SV_CHBAS table of 32 bit pointers). That table contains pointers to channel definition blocks, which contain the 16 bit channel tag at offset 16. The channel ID to use in TRAP#3 has two 16 bit fields: the channel tag (high 16 bits if I remember correctly) and the SB channel number (low 16 bits).

However, if you are writing a program rather than a SuperBASIC extension, you would open your own channels by using TRAP#2. The channel open trap (D0=1) returns to you the channel ID in A0, that you can directly pass to TRAP#3 calls.


User avatar
mk79
QL Wafer Drive
Posts: 1349
Joined: Sun Feb 02, 2014 10:54 am
Location: Esslingen/Germany
Contact:

Re: How to get a channel ID for a standard channel?

Post by mk79 »

I think Danielle mixes system channel and basic channel list a bit here. The basic channel list is not a list of pointers, it's a list of continuous channel blocks and each block contain the channel ID at offset 0. I generally use the SMSQ/E headers which have different names for the same offsets, but the resulting code is also QDOS compatible.

Get ID of #0:

Code: Select all

	move.l sb_chanb(a6),a0	; $30(a6)
	move.l ch_chid(a0),a0	; $0(a0)
Gets ID of #1.

Code: Select all

	move.l	sb_chanb(a6),a0
	add.l	#ch.len,a0	; #$28
	move.l	ch_chid(a0),a0
Do not use any magic numbers like $00010001 anymore, code doing this is wrong!

The rest is true, if you don't build a basic extension you have to open the channel yourself.


User avatar
M68008
Trump Card
Posts: 223
Joined: Sat Jan 29, 2011 1:55 am
Contact:

Re: How to get a channel ID for a standard channel?

Post by M68008 »

Thank you for the correction, now I remember the multiplication by #$28.

I was thinking of the system channel table (SV.CHBAS, pointers, tags, etc.), but the index there is not the SuperBASIC channel number, so there is no practical reason to look at it.


vol
ROM Dongle
Posts: 22
Joined: Thu Jan 20, 2022 5:07 pm

Re: How to get a channel ID for a standard channel?

Post by vol »

mk79 wrote:I think Danielle mixes system channel and basic channel list a bit here. The basic channel list is not a list of pointers, it's a list of continuous channel blocks and each block contain the channel ID at offset 0. I generally use the SMSQ/E headers which have different names for the same offsets, but the resulting code is also QDOS compatible.

Get ID of #0:

Code: Select all

	move.l sb_chanb(a6),a0	; $30(a6)
	move.l ch_chid(a0),a0	; $0(a0)
Gets ID of #1.

Code: Select all

	move.l	sb_chanb(a6),a0
	add.l	#ch.len,a0	; #$28
	move.l	ch_chid(a0),a0
Do not use any magic numbers like $00010001 anymore, code doing this is wrong!

The rest is true, if you don't build a basic extension you have to open the channel yourself.
Thank you very much. Your information has helped me a lot. I just incorrectly calculated the base of Basic variables. I needed to add $68 to a value at SV_BASIC or just use A6. BTW the correct code for channel #1 is the next

Code: Select all

         movea.l $30(a6),a0   ; SB.CHANB
         lea.l $28(a6,a0),a0  ; CH.LENCH
         movea.l (a0),a0       ; CH.ID


User avatar
mk79
QL Wafer Drive
Posts: 1349
Joined: Sun Feb 02, 2014 10:54 am
Location: Esslingen/Germany
Contact:

Re: How to get a channel ID for a standard channel?

Post by mk79 »

vol wrote:Thank you very much. Your information has helped me a lot. I just incorrectly calculated the base of Basic variables. I needed to add $68 to a value at SV_BASIC or just use A6.
Well, sv_basic stems from a time when there was only one basic in the system, which isn't true anymore. So do use A6 if possible. Also, the SMSQ/E source code contains the complete TK2 source code and its utility functions, written by the man (Tony Tebby) himself. Every conceivable problem has already been solved there.
BTW the correct code for channel #1 is the next

Code: Select all

         movea.l $30(a6),a0   ; SB.CHANB
         lea.l $28(a6,a0),a0  ; CH.LENCH
         movea.l (a0),a0       ; CH.ID
Ah, of course, forgot to make it a6 relative. But as a matter of fact your code is wrong, too, because you must never derive an absolute pointer when multitasking is enabled. So finally the correct code is

Code: Select all

         movea.l	sb_chanb(a6),a0
         adda.w 	#ch.len,a0
         movea.l	ch_chid(a6,a0.l),a0


Post Reply