***************************************
*                                     *
*  DESKSWITCH                         *
*                                     *
*  Copyright 1988 Charles F. Johnson  *
*  All Rights Reserved                *
*                                     *
***************************************

* -----------------------------------
*  Last revision: 04/27/88  23:11:24
* -----------------------------------

gemdos  =       1
aesvdi  =       2
bios    =       13
xbios   =       14

        .text

        move.l  #prog_end,d0    ; Get address of end of program
        sub.l   4(sp),d0        ; Subtract start of basepage
        move.l  4(sp),a5        ; Get start of basepage and save in a5
        lea     ustack,sp       ; Allocate a stack frame
        move.l  d0,-(sp)        ; Push the number of bytes to save
        move.l  a5,-(sp)        ; Push the start address
        clr     -(sp)           ; Dummy
        move    #$4A,-(sp)      ; Mshrink this bad boy
        trap    #gemdos
        lea     12(sp),sp
        tst.l   d0              ; Mshrink error? (shouldn't happen)
        bmi     exit            ; If so, bail out

        tst.b   128(a5)         ; Look at the length byte of the command line
        beq.s   getdrv          ; If zero, do the file selector

        clr.w   -(sp)           ; Open for read
        pea     129(a5)         ; Push the command line address
        bra     openit          ; Go do it

getdrv: move    #$19,-(sp)      ; Get current drive
        trap    #gemdos
        addq    #2,sp
        add.b   #'A',d0         ; Make it an ASCII letter
        lea     infdir,a0
        move.b  d0,(a0)+        ; Move it to the fsel directory string

        lea     inftxt,a1
        move    #7,d0
dir:    move.b  (a1)+,(a0)+     ; Move in the rest of the path specification
        dbf     d0,dir

        lea     addrin,a0
        move.l  #infdir,(a0)    ; The fsel_input control block pointer is
        move.l  #infnam,4(a0)   ; already in aespb
        move.l  #title1,8(a0)   ; Title strings for Start Selector
        move.l  #title2,12(a0)
        bsr     aes

        tst.b   infnam          ; Got a filename?
        beq     exit            ; No, bail out
        cmp.w   #1,intout+2     ; Clicked on OK?
        bne     exit            ; Nope, bailski

        lea     filename,a1     ; My filename area
        lea     infdir,a0       ; Fsel directory string
.loop1: move.b  (a0)+,(a1)+     ; Copy bytes until a zero is found
        bne     .loop1
.loop2: cmp.b   #'\\',-(a1)     ; Search backward for the backslash
        bne     .loop2
        tst.b   (a1)+           ; Move pointer to next character
        lea     infnam,a0
.loop3: move.b  (a0)+,(a1)+     ; Append filename to end of path string
        bne     .loop3

        clr.w   -(sp)           ; Open for read only
        pea     filename        ; Address of path/filename

openit: move    #$3D,-(sp)      ; GEMDOS Fopen call
        trap    #gemdos
        addq    #8,sp
        tst.l   d0              ; Error?
        bmi     exit            ; I guess so
        move    d0,handle       ; Save file handle

readit: pea     dtbuff          ; Address of buffer for DESKTOP.INF
        move.l  #4096,-(sp)     ; 4K maximum size
        move    handle,-(sp)    ; Push handle on stack
        move    #$3F,-(sp)      ; Read it
        trap    #gemdos
        lea     12(sp),sp
        tst.l   d0              ; Error?
        bmi     closit

        lea     dtbuff,a5
        cmp.b   #'#',(a5)       ; 1st char should be a number sign
        bne     closit
        cmp.b   #'a',1(a5)      ; 2nd char should be lower case 'a'
        bne     closit

        move.l  #s_put,aespb    ; Shel_put
        move    d0,intin        ; Length of DESKTOP.INF
        move.l  a5,addrin       ; Address of buffer
        bsr     aes

        move    #-1,d7          ; Initialize baud rate parameter

        lea     dtbuff,a5
        lea     baud_ascii,a0
        move    #15,d2
        moveq   #0,d1
        move.b  3(a5),d0        ; Get baud rate setting
ckbaud: cmp.b   (a0)+,d0
        beq.s   ckb2
        addq    #1,d1
        dbf     d2,ckbaud
        bra.s   ckrtct
ckb2:   move    d1,d7           ; Store baud parameter in d7

ckrtct: moveq   #0,d6
        move.b  6(a5),d6        ; Get rts/cts setting
        sub     #'0',d6
rs232:  moveq   #-1,d0
        move.l  d0,-(sp)        ; Don't change the MFP registers
        move.l  d0,-(sp)
        move    d6,-(sp)        ; rts/cts
        move    d7,-(sp)        ; Baud rate
        move    #15,-(sp)       ; rsconf
        trap    #xbios
        add     #14,sp

        tst.b   (a5)+

look1:  cmp.b   #'#',(a5)+      ; Look for next # sign
        bne     look1

        addq    #7,a5           ; Set pointer to end of printer line
        moveq   #0,d0           ; Clear bit vector to start
        move    #5,d1           ; Six bits to check
ckprt1: cmp.b   #'0',-(a5)      ; Is the bit on or off?
        beq.s   ckprt2          ; Off, skip over
        bset    d1,d0           ; Set bit in printer config parameter
ckprt2: dbf     d1,ckprt1       ; You're not leaving 'til you clean your plate

        move    d0,-(sp)        ; The configuration bits are now set
        move    #33,-(sp)       ; setprt
        trap    #xbios
        addq    #4,sp

look2:  cmp.b   #'#',(a5)+      ; Find next # sign
        bne     look2
        tst.b   (a5)+           ; Set pointer to first palette value

        move    #4,-(sp)        ; Get resolution to d0
        trap    #xbios
        addq    #2,sp

        lsl     d0
        lea     trans_table,a0  ; Address of VDI/TOS color translation tables
        move    offval(a0,d0),d3 ; Offset to dclick value from last color
        move    count(a0,d0),d5 ; # of color registers to set
        lsl     d0
        move.l  0(a0,d0),a6     ; Address of translation table based on res

color0: moveq   #0,d4           ; Start color register counter at zero
color1: moveq   #0,d0
        move.b  (a5)+,d0
        sub.b   #'0',d0         ; Convert from ASCII to number (0-7)
        lsl     #8,d0           ; *256 (to get high digit)
        move    d0,d1
        moveq   #0,d0
        move.b  (a5)+,d0
        sub.b   #'0',d0
        lsl     #4,d0           ; *16 (upper nibble of low byte)
        or      d0,d1           ; Mix 'em up
        moveq   #0,d0
        move.b  (a5)+,d0
        sub.b   #'0',d0
        or      d0,d1           ; Mix in the lower nibble
        move    d1,-(sp)        ; Color value
        move.b  0(a6,d4),d0     ; Adjusted register number

        move    d0,-(sp)
        move    #7,-(sp)        ; setcolor
        trap    #xbios
        addq    #6,sp
        addq    #1,d4           ; Increment register
        dbf     d5,color1       ; Do the rest

        add     d3,a5           ; Adjust pointer to desktop data

        moveq   #0,d0
        move.b  (a5)+,d0        ; Get double click rate
        sub.b   #'0',d0         ; Make it binary
        move.l  #e_dclk,aespb   ; Set double click rate with AES evnt_dclick
        move    d0,intin        ; The new rate
        move    #1,intin+2
        bsr     aes

        move.l  a5,bufsav
        pea     click_bell      ; Set click/bell on/off in super mode
        move    #38,-(sp)
        trap    #xbios
        addq    #6,sp
        move.l  bufsav,a5

        lea     deciml,a4       ; For some weird reason, the key delay
        move.l  a4,a1           ; and repeat values are stored in decimal
        move.b  (a5)+,(a1)
        move.b  (a5)+,1(a1)
        clr.b   2(a1)
        bsr.s   decbin
        move    d0,d7
        move.l  a4,a1
        move.b  (a5)+,(a1)
        move.b  (a5)+,1(a1)
        bsr.s   decbin

        move    d0,-(sp)        ; Repeat value
        move    d7,-(sp)        ; Delay value
        move    #35,-(sp)       ; kbrate
        trap    #xbios
        addq    #6,sp

look3:  cmp.b   #'#',(a5)+      ; Next # sign
        bne     look3
look4:  cmp.b   #'#',(a5)+      ; And the next
        bne     look4
        cmp.b   #'E',(a5)       ; Make sure it's the right line
        bne.s   closit

        moveq   #0,d0
        move.b  5(a5),d0        ; Get blitter status
        sub.b   #'0',d0         ; Convert from ASCII

        move    d0,-(sp)        ; Turn blitter on/off
        move    #64,-(sp)
        trap    #xbios
        addq    #4,sp

closit: move    handle,-(sp)    ; Close the file like a good little
        move    #$3E,-(sp)      ; programmer
        trap    #gemdos
        addq    #4,sp

exit:   clr.w   -(sp)           ; Back to our new desktop!
        trap    #gemdos

* -------------
*  Subroutines
* -------------

* Decimal ASCII to binary longword
* Enter with: a1 -> decimal string
* Exit with:  d0 = converted binary number
* Trashes d0-d1/a1

decbin:
        moveq   #0,d0           ; Clear accumulator
.loop:  cmp.b   #'9',(a1)
        bhi.s   decb_x
        cmp.b   #'0',(a1)
        blo.s   decb_x
        lsl.l   #1,d0
        move.l  d0,d1
        lsl.l   #2,d0
        add.l   d1,d0
        move.b  (a1)+,d1
        and.l   #$0F,d1
        add.l   d1,d0
        bra     .loop
decb_x: rts

click_bell:
        lea     $484,a0         ; conterm
        move.l  bufsav,a5
        cmp.b   #'0',(a5)+      ; Is keyclick on?
        bne.s   cb1             ; Yes, skip ahead
        bclr.b  #0,(a0)         ; Clear the bit
        bra.s   cb2
cb1:    bset.b  #0,(a0)         ; Set the bit
cb2:    cmp.b   #'0',(a5)+      ; Is the CTRL-G bell on?
        bne.s   cb3             ; Yes, skip
        bclr.b  #2,(a0)         ; Clear the bit
        bra.s   cb4
cb3:    bset.b  #2,(a0)         ; Set the bit
cb4:    move.l  a5,bufsav
        rts                     ; Outta here

* AES Subroutine

aes:    move.l  #aespb,d1       ; Address of parameter block in d1
        move.l  #$C8,d0         ; Magic word $C8 = AES
        trap    #aesvdi         ; Call the AES ("Hey, AES!")
        rts

        .data
        .even

aespb:  dc.l    f_sel, global, intin, intout, addrin, addrout

f_sel:  dc.w    90, 0, 2, 4, 0
s_put:  dc.w    123, 1, 1, 1, 0
e_dclk: dc.w    26, 2, 1, 0, 0

low_val:
        dc.b    0, 15, 1, 2, 4, 6, 3, 5, 7, 8, 9, 10, 12, 14, 11, 13
med_val:
        dc.b    0, 15, 1, 2, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15
hi_val:
        dc.b    0, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15, 15

trans_table:
        dc.l    low_val, med_val, hi_val
off_table:
        dc.w    0, 36, 42
count_table:
        dc.w    15, 3, 1
offval  =       off_table - trans_table
count   =       count_table - trans_table


title1: dc.b    'Choose a',0
title2: dc.b    'DESKTOP file',0

inftxt: dc.b    ':\\*.INF',0

baud_ascii:
        dc.b    '4015678293:;<=>?'

        .bss
        .even

bufsav: ds.l    1

handle: ds.w    1

* GEM arrays

intin:  ds.w    64
intout: ds.w    64
global:
apvrsn: ds.w    1
apcont: ds.w    1
apid:   ds.w    1
apprvt: ds.l    1
apptre: ds.l    1
ap1rsv: ds.l    1
ap2rsv: ds.l    1
ap3rsv: ds.l    1
ap4rsv: ds.l    1

addrin: ds.l    8
addrout:ds.l    8

infnam: ds.b    16

infdir: ds.b    80

filename:
        ds.b    96

deciml: ds.b    4

dtbuff: ds.b    4098

        ds.l    300             ; Reserve 1200 bytes for stack
ustack: ds.l    1
        ds.w    10

prog_end:
        ds.w    0
