
******************************************
* Programm: ICONDESK.S                   *
******************************************
* Ver”ffentlich in: ST-DIGITAL           *
******************************************
* Statte das schlichte Atari-Desktop mit *
* individuellen Programmicons aus.       *
* L„uft nur aus dem Auto-Ordner!         *
******************************************
* XBRA-Kennung: 'IDSK' (f. Trap #2)      *
******************************************
******************************************
* Tabulatorweite: 10                     *
******************************************
* (C)1989 by Stefan Becker               *
* Assembler: DRI, Turbo-C-Assembler, o.„ *
******************************************

***************
* Version:    *
* 24.6.1989   *
***************

v0        equ       1                   * Versionsnr. vor dem "Punkt"
v1        equ       2                   * Versionsnr. hinter dem "Punkt"

****************
* Trap-Equals: *
****************

Gemdos    equ       1                   * Trapnummern:
Bios      equ       13
Xbios     equ       14

********************
* Funktionsnummern *
********************

fsfirst   equ       $4e                 * TOS-Funktionsnummern
mshrink   equ       $4a
malloc    equ       $48
fread     equ       $3f
fclose    equ       $3e
fopen     equ       $3d
ptermres  equ       $31
supexec   equ       38
fgetdta   equ       $2f
cconws    equ       9

vgtext    equ       8                   * VDI: Grafiktext
copyrtr   equ       121                 * VDI: Copy raster transparent
clipping  equ       129                 * VDI: Set-Clipping

basepag   equ       4                   * Basepage-Konstanten:
text_sg   equ       12
data_sg   equ       20
bss_sg    equ       28

_sysbase  equ       $4f2                * Systemvariablen...
vblqueue  equ       $456

**************
* Konstanten *
**************

kennung   equ       'IDSK'              * XBRA-Kennung

stacksize equ       800                 * Programm-Stackgr”že
asciinull equ       48                  * =Ord('0') im ASCII-Zeichensatz
tos_len   equ       $30000              * L„nge des TOS (192K)
maxstr    equ       64                  * Max. L„nge eines VGTXT-Strings
anzparam  equ       16                  * Anzahl registrierter VDI-Parameter
maxcalls  equ       30                  * Max. Zahl aufnehmbarer VDI-Calls
mlen      equ       16                  * L„nge eines Match-Strings in Bytes
hpos      equ       13                  * Position des Hexbytes in Matchstr.
ppos      equ       8                   * Position des Punktes in Matchstr.
paclen    equ       5*anzparam+3        * L„nge eines gesp. VDI-Aufrufs

*****************
* Hauptprogramm *
*****************

prgstart: move.l    basepag(a7),a0      * Startadresse des Programms nach a0
          clr.l     d0
          move.w    #$100,d0            * Programml„nge: 256 Bytes Base-Page
          add.l     text_sg(a0),d0      * + L„nge des Text-Segments
          add.l     data_sg(a0),d0      * + L„nge des Data-Segments
          add.l     bss_sg(a0),d0       * + L„nge des BSS-Segments
          move.l    d0,bedarf           * Speicherbedarf merken
          lea       stacktop,a7         * Stack setzen...

          move.l    bedarf,-(a7)        * Mshrink(prgstart-256,bedarf)
          move.l    #prgstart-256,-(a7)
          clr.w     -(a7)
          move.w    #mshrink,-(a7)
          trap      #Gemdos
          adda.w    #12,a7

          bsr       checkaut            * Programm in Auto-Ordner?

          move.w    #11,-(a7)           * Nicht installieren, falls
          trap      #Bios               * Shift (o.„.) Taste gedrckt ist!!!
          addq.l    #2,a7
          tst.b     d0
          bne       endprg              * Ja => nicht installieren

          bsr       readdata            * Icons + Zuordnung von Disk laden
          bsr       initbuf             * Variablen vorbelegen!
          bsr       init                * Žndere VDI-Routinen

          pea       installst           * Installiert-Meldung ausgeben
          move.w    #cconws,-(a7)
          trap      #Gemdos
          addq.l    #6,a7

          clr.w     -(a7)               * Return-Code 0
          move.l    bedarf,-(a7)        * Speicherbedarf
          move.w    #ptermres,-(a7)     * Ptermres
          trap      #1                  * ausfhren => Programmende

***************************************
* Icondesk aus Auto-Ordner gestartet? *
* Ja => O.K., Nein => Programmabbruch *
***************************************

checkaut: pea       readslot(pc)        * Fr VBL-Zugriff in Supervisormode
          move.w    #supexec,-(a7)
          trap      #Xbios
          addq.l    #6,a7

          tst.l     slot0               * Slot 0 belegt?
          bne       noauto              * Ja d.h. kein Auto-Start
          rts                           * Nein, d.h. Auto-Start (O.K.)

noauto:   lea       onlyauto,a0         * Meldung: Icondesk l„uft nur aus
          bra       error               * dem Auto-Ordner + Programmabbruch

readslot: move.l    vblqueue,a0         * Slot-0 VBL-Queue auslesen
          move.l    (a0),slot0          * =0 d.h. Auto-Ordner-Start
          rts

*************************************
* Programmabbruch mit Fehlermeldung *
* Fehlermeldungsstring in a0        *
*************************************

error:    move.l    a0,-(a7)            * Fehlermeldung ausgeben
          move.w    #cconws,-(a7)
          trap      #Gemdos
          addq.l    #6,a7

          pea       taste               * "Bitte Taste drcken!" ausgeben
          move.w    #cconws,-(a7)
          trap      #Gemdos
          addq.l    #6,a7

          move.w    #2,-(a7)            * Bconin(2) (Auf Taste warten)
          move.w    #2,-(a7)
          trap      #Bios
          addq.l    #4,a7

endprg:   clr.w     -(a7)
          trap      #Gemdos             * Programmabbruch!!!

****************************
* Lese Daten von Disk ein  *
* (Ikonen+Zuordnungsdatei) *
****************************

readdata: lea       iname,a0            * Icons laden (Versuch 1)
          bsr       rdalloc
          tst.l     d0                  * Erfolg?
          bne       foundd1             * Ja, weiter
          lea       iname2,a0           * Nein, 2. Versuch
          bsr       rdalloc
          tst.l     d0                  * Erfolg?
          bne       foundd1             * Ja, weiter
nfnd:     lea       notfound,a0         * Nein => Fehlermeldung
          bra       error               *         + Programmabbruch
foundd1:  move.l    d0,icons            * Iconadresse merken

          lea       mname,a0            * Matches laden (Versuch 1)
          bsr       rdalloc
          tst.l     d0                  * Erfolg?
          bne       foundd2             * Ja, weiter
          lea       mname2,a0           * Nein, 2. Versuch
          bsr       rdalloc
          tst.l     d0                  * Erfolg?
          bne       foundd2             * Ja, weiter
          bra       nfnd                * Nein, Abbruch+Fehlermeldung (s.o.)
foundd2:  move.l    d0,matches          * Adresse merken
          lsr.l     #4,d1               * L„nge/16=Anzahl d. Eintr„ge
          move.l    d1,matchlen         * L„nge der matches merken

          rts                           * O.K., weiter im Text...

**********************************************************
* Lese Datei ein und reserviere gleich Speicher dafr    *
**********************************************************
* Ausgbe: d0=Adresse des Puffers =0 falls nicht gefunden *
*         d1=L„nge der Datei                             *
**********************************************************

rdalloc:  move.l    a0,name             * Namen merken
          clr.w     -(a7)               * Fsfirst(name,0)
          move.l    a0,-(a7)
          move.w    #fsfirst,-(a7)
          trap      #Gemdos
          addq.l    #8,a7
          tst.l     d0                  * Ergebnis?
          bge       found1              * OK => weiter im Text
nf:       clr.l     d0                  * Nix gefunden
          rts
found1:   move.w    #fgetdta,-(a7)      * Adresse des DTA Puffers
          trap      #Gemdos
          addq.l    #2,a7
          move.l    d0,a0
          move.l    26(a0),len          * Dateil„nge auslesen
          move.l    len,-(a7)           * Malloc(len)
          move.w    #malloc,-(a7)
          trap      #Gemdos
          addq.l    #6,a7
          tst.l     d0
          bne       enough              * Genug Speicher da?
          lea       noram,a0            * Nein => Fehlermeldung
          bra       error
enough:   move.l    d0,ptr              * Speicheradresse merken
          clr.w     -(a7)               * Fopen(name,0)
          move.l    name,-(a7)
          move.w    #fopen,-(a7)
          trap      #Gemdos
          addq.l    #8,a7
          tst.w     d0                  * Geklappt?
          bpl       found2              * Ja => weiter im Text
          bra       nf                  * Nein => Fehlermeldung+Abbruch
found2:   move.w    d0,fhandle
          move.l    ptr,-(a7)           * Fopen(fhandle,len,ptr)
          move.l    len,-(a7)
          move.w    d0,-(a7)
          move.w    #fread,-(a7)
          trap      #Gemdos
          lea       12(a7),a7
          cmp.l     len,d0              * geklappt?
          beq       gelesen             * Ja => weiter
          lea       rderror,a0          * Lesefehler+Abbruch
          bra       error
gelesen:  move.w    fhandle,-(a7)       * Fclose(fhandle)
          move.w    #fclose,-(a7)
          trap      #Gemdos
          addq.l    #4,a7
          move.l    ptr,d0              * Ergebnisse liefern!
          move.l    len,d1
          rts

fhandle:  dc.w      0
name:     dc.l      0
ptr:      dc.l      0
len:      dc.l      0

*******************************
* Initialisiere die Variablen *
*******************************

initbuf:  move.l    #vdibuf,vdiptr      * VDI-Puffer initialisieren...
          clr.w     vdicount
          clr.w     clpvalid            * Clipping-Daten leer
          rts

**************************
* H„nge neue VDI-Routine *
* ein &                  *
* Setze os_start und     *
* os_end                 *
**************************

init:     pea       inmain(pc)          * Inmain in S-Mode starten
          move.w    #supexec,-(a7)
          trap      #Xbios
          addq.l    #6,a7
          rts

inmain:   move.l    _sysbase,a0         * Anfang des TOS suchen:
          move.l    8(a0),d0            * aus Header holen und
          move.l    d0,os_start         * merken
          add.l     #tos_len,d0         * + TOS-L„nge
          move.l    d0,os_end           * = TOS-Ende

          move.l    $88,d0              * alten Vektor merken
          move.l    d0,xbra+8           * & in XBRA-Tabelle schreiben
          move.l    d0,oldvdi           * aužerdem merken
          lea       newvdi,a0           * Trap #2 bis zum Start v. GEM
          move.l    a0,$88              * „ndern
          rts

*************************
* Neue Trap VDI-Routine *
*************************

xbra:     dc.l      'XBRA'              * XBRA-Struktur anlegen:
          dc.l      kennung             * Identifikation: ICONDESK
          dc.l      0                   * vorerst 0, dann alte Trap#2-Adr.

newvdi:   cmp.w     #$73,d0             * VDI-Aufruf?
          beq       vdicall             * Ja, VDI-Aufruf genauer ansehen...
          move.l    oldvdi,-(a7)        * AES o.„. => weiter wie gehabt
          rts
*
* Hier geht's nun fr's VDI lang:
*
vdicall:  movem.l   d0-d2/d4/d6-d7/a0-a3/a6,-(a7)   * Register retten

          move.l    11*4+2(a7),d0       * Aufrufadresse holen!
          cmp.l     os_start,d0         * Liegt sie im ROM (TOS)?
          blt       vdiback             * Nein => nichts „ndern!
          cmp.l     os_end,d0
          bgt       vdiback             * Nein => nichts „ndern!

          move.l    d1,a0               * Adresse VDI-Parameterblock
          move.l    d1,vdid1            * merken
          move.l    (a0),a0             * Hole Funktionsnummer...
          move.w    (a0),d0
          cmp.w     #copyrtr,d0         * Copy-Raster?
          beq       cpyr
          cmp.w     #vgtext,d0          * Text?
          beq       gtxt
          cmp.w     #clipping,d0        * Set-Clipping
          beq       clip

vdiback:  movem.l   (a7)+,d0-d2/d4/d6-d7/a0-a3/a6   * Nix besonderes:Regs restaurieren
          move.l    oldvdi,-(a7)        * Weiter, wie gehabt zum VDI.
          rts                           * Ende des VDI-Aufrufs!

vdicancel:movem.l   (a7)+,d0-d2/d4/d6-d7/a0-a3/a6   * Aufruf "abwrgen"!!! (Nicht
          rte                           * an's VDI weitergeben!)

**********************
* Vergleiche 2 Icons *
* Ic1=^a0, Ic2=^a1   *
* gerade Adressen!!! *
**********************
* d0=0 => "<>"       *
* d0=1 => "="        *
**********************

cmpicn:   moveq     #(128/4)-1,d0
icmplp:   cmpm.l    (a0)+,(a1)+
          bne       noteqic
          dbf       d0,icmplp
          moveq     #1,d0
          rts
noteqic:  clr.w     d0
          rts

*********************************************
* Testet Typ des Icons, das mit Copyraster  *
* gemalt werden soll.                       *
* d0<=0 Icondaten, d0<=1 Maske,             *
* d0<=2 d.h. Kein Datei- oder Programmicon! *
*********************************************

getictyp: move.l    vdid1,a2
          move.l    (a2),a2             * Control-Array
          move.l    14(a2),a2           * Source-MFDB=^^Rasterdaten
          move.l    (a2),a2             * a2=^Rasterdaten

          move.l    a2,a0               * Vergleiche akt. Icon mit
          lea       dat,a1              * Datei-Icon
          bsr       cmpicn              * "="?
          tst.w     d0
          beq       nix1                * Nein, weitersuchen
daten:    clr.w     d0                  * Ja: liefere Daten
          bra       exictyp
nix1:     move.l    a2,a0
          lea       prg,a1              * Programm-Icon
          bsr       cmpicn              * "="?
          tst.w     d0
          beq       nix2                * Nein, weitersuchen
          bra       daten               * Ja: Daten

nix2:     move.l    a2,a0
          lea       datmsk,a1           * Datei-Maske?
          bsr       cmpicn
          tst.w     d0
          beq       nix3                * Nein, weitersuchen
maske:    moveq     #1,d0               * Ja => liefere Maske
          bra       exictyp
nix3:     move.l    a2,a0
          lea       prgmsk,a1           * Programm-Maske?
          bsr       cmpicn
          tst.w     d0
          beq       garnix              * Nein => gesamtes Suchen erfolglos!
          bra       maske               * Ja => liefere "Maske"

garnix:   moveq     #2,d0               * Nix "vernnftiges"!
exictyp:  rts

***********************************
* Kopiert d0 Worte von a0 nach a1 *
***********************************

wcopyl:   move.w    (a0)+,(a1)+
wcopy:    dbra      d0,wcopyl
          rts

**********************************
* Speichert VDI-Parameter in ^a0 *
**********************************

savevdi:  move.l    vdid1,a1
          move.l    (a1),a1             * Adr. Control-Array
          move.w    (a1),d0             * Funktionsnummer
          move.b    d0,(a0)+            * erst Fnktnr. speichern (1 Byte)
          cmp.w     #copyrtr,d0         * Copyraster?
          bne       nocprtr             * Nein, dann Folgewerte egal
          move.l    a0,-(a7)            * Ja: a0 kurz retten
          bsr       getictyp            * Was fr ein Icon?
          move.l    (a7)+,a0            * a0 wiederholen
          move.b    d0,(a0)+            * Typ als Folgewert speichern
          move.l    vdid1,a1            * Iconadresse speichern(!):
          move.l    (a1),a1             * Zeiger auf Control-Array
          move.l    14(a1),a1           * Zeiger auf Source-MFDB
          move.l    (a1),(a0)+
          bra       svdicont
nocprtr:  addq.l    #5,a0               * Zeiger weiter auf eigentl. Daten
svdicont: move.l    vdid1,a3            * a3 Zeiger auf VDI-Array
          move.l    a0,a1               * Zieladresse setzen
          moveq     #5-1,d7             * 5 Schleifendurchl„ufe
svelp:    move.l    (a3)+,a0            * Quelladresse setzen (VDI-Arrays)
          moveq     #anzparam,d0        * Anzahl=Anzparam
          bsr       wcopy               * Worte kopieren
          dbf       d7,svelp
          move.l    a1,a0               * Endadresse bergeben
          rts

*****************************
* Neue Set-Clipping-Routine *
*****************************

clip:     lea       clpbuf,a0           * 1 Aufruf in clpbuf speichern
          bsr       savevdi
          move.w    #1,clpvalid         * Flagge: clpbuffer gefllt
          bra       vdiback

****************************************
* Neue Copy-Raster-Transparent-Routine *
****************************************

cpyr:     bsr       getictyp            * Was fr ein Icon?
          cmp.w     #2,d0               * Vernnftig? PRG oder DATEI?
          bne       dofake
          bra       vdiback             * Aufruf normal durchfhren.
dofake:   tst.w     clpvalid            * War vorher ein Clipping-Aufruf?
          beq       noclipp             * Nein! Dann auch nix kopieren.
          lea       clpbuf,a0           * Clipping-Aufruf erst kopieren!:
          move.l    vdiptr,a1
          move.w    #paclen,d0
          bsr       wcopy
          clr.w     clpvalid            * Jetzt ist Clipping-Puffer leer!
          move.l    a1,vdiptr           * vdiptr auf neuesten Stand bringen
          addq.w    #1,vdicount         * Z„hler erh”hen
noclipp:  move.l    vdiptr,a0
          bsr       savevdi             * akt. Aufruf speichern
          move.l    a0,vdiptr           * Zeiger zurckspeichern
          addq.w    #1,vdicount         * Z„hler erh”hen
          bra       vdicancel           * Aufruf hier "abwrgen"!

*************************
* Neue VDI-Text-Routine *
*************************

gtxt:     tst.w     vdicount            * Steht 'was im Puffer?
          beq       bufempty            * Nein, trivialer Fall! (nix machen)
          bsr       gettext             * Textstring auslesen
          bsr       testname            * Passendes Icon suchen
          bsr       putakt              * akt. VDI-Parameter kurz retten
          bsr       playcall            * aufgeschobene Aufrufe starten
          bsr       getakt              * akt. VDI-Parameter wiederholen
bufempty: bra       vdiback             * zurck tum TXT-Aufruf

******************************************
* Lese den Stringparameter fr gtext aus *
******************************************

gettext:
          lea       string,a0           * Stringpuffer leeren!
          clr.b     d0                  * (12 Words mit 0 beschreiben)
          moveq     #12-1,d7
gtxtclp:  move.b    d0,(a0)+
          dbf       d7,gtxtclp

          move.l    vdid1,a0            * Zeiger auf AES-Parameterblock
          move.l    4(a0),a1            * Intin-Array: a1=Zeiger auf Str.
          move.l    (a0),a0
          move.w    6(a0),d7            * L„nge des Strings nach d0
          lea       string,a0           * Zeiger auf eigenen Stringpuffer
          subq.w    #1,d7
gettlp:   move.w    (a1)+,d0            * String kopieren und auf
          move.b    d0,(a0)+            * Bytebuchstaben umformen
          dbf       d7,gettlp
          clr.b     (a0)                * Nullterminator setzen!
          rts

*************************************
* Rette die aktuellen VDI-Parameter *
*************************************

putakt:   lea       clpbuf,a0           * akt. Parameter kurz in Clpbuf
          bsr       savevdi
          rts

**********************************************
* Kopiere die aktuellen VDI-Parameter zurck *
**********************************************

getakt:   lea       clpbuf+6,a0         * Funktionsnummer*Ic-Adr. berlesen
          move.l    vdid1,a2            * Adr. VDI-Parameterfeld
          moveq     #5-1,d7             * 5 Arrays
getlp:    move.l    (a2)+,a1            * Adr. d. akt. Arrays
          moveq     #anzparam,d0        * Parameter dieses Arrays kopieren
          bsr       wcopy
          dbf       d7,getlp            * Noch ein Array?
          rts

*******************************************
* Spiele gespeicherte VDI-Calls wieder ab *
*******************************************

playcall:
          move.l    #vdibuf,vdiptr      * An den Anfang des Puffers!
          move.w    vdicount,d6         * Anzahl gespeicherter Aufrufe
          bra       endplp

plp:      move.l    vdiptr,a0           * Zeiger auf Puffer f. Aufrufe
          cmp.b     #copyrtr,(a0)       * Copyraster?
          bne       daten1              * Nein => weiter

          move.l    2(a0),oldicon       * alte Iconadresse holen
          clr.w     icoffset            * Offset fr ICON 0=Daten, 128=Maske
          tst.b     1(a0)               * Icon oder Daten?
          beq       daten1
          move.w    #128,icoffset

daten1:   addq.l    #6,a0               * Funktionsnummer+Ic.-Info berlesen
          move.l    vdid1,a2            * Adresse VDI-Parameterfeld
          moveq     #5-1,d7             * 5 Arrays...
plp2:     move.l    (a2)+,a1            * ...kopieren
          moveq     #anzparam,d0        * Jeweils "anzparam" viele Worte
          bsr       wcopy
          dbf       d7,plp2             * N„chstes Array
          move.l    a0,vdiptr           * vdiptr auf neuesten Stand bringen

          move.l    vdid1,a0            * Was fr ein Aufruf?...
          move.l    (a0),a0
          cmp.w     #copyrtr,(a0)       * Ist's ein Copyraster-Aufruf?
          bne       norasta             * Nein, dann einfach abspielen
          bsr       fakecall            * Ja => f„lschen!!!
norasta:  move.w    d6,-(a7)            * Schleifenz„hler retten
          move.l    vdid1,d1            * Es folgt ein VDI-Aufruf
          moveq     #$73,d0             * s.o.
          trap      #2                  * => VDI
          move.w    (a7)+,d6            * Schleifenz„hler wiederholen
endplp:   dbf       d6,plp              * N„chster Aufruf

          bsr       initbuf             * Puffer leeren
          rts

***********************************
* F„lsche einen Copyraster-Aufruf *
***********************************

fakecall: move.l    vdid1,a0
          move.l    (a0),a0             * Zeiger auf Control-Array
          move.l    14(a0),a0           * Zeiger auf Source-MFDB
          tst.w     nomatch             * Kein Match => altes Icon nehmen!
          bne       putold
          move.l    newicon,a6          * Zeiger auf mein Icon
          adda.w    icoffset,a6         * aužerdem evtl. Maske malen
          bra       icpatch
putold:   move.l    oldicon,a6
icpatch:  move.l    a6,(a0)             * Bumm, rein in seinen MFDB!
hoerauf:  rts

********************************************************
* Sehe nach passendem "Matching" fr akt. Dateinamen   *
* Dabei "newicon" setzen.                              *
********************************************************
* Das Matchen ist noch verbesserungsf„hig, schon klar! *
********************************************************

testname: move.l    matches,a3          * Start der Matchtabelle
          move.l    matchlen,d4         * L„nge der Matchtabelle
tlstar:   tst.l     d4                  * =0?
          beq       nochance            * Ja => fertig
          move.l    a3,a0               * passt dieser Eintrag?
          move.l    a3,-(a7)
          move.l    d4,-(a7)
          bsr       match1
          move.l    (a7)+,d4
          move.l    (a7)+,a3
          tst.w     d0
          bne       gotit               * Yeah, Yeah, Yeah!
          adda.w    #mlen,a3            * Nein, n„chsten Eintrag...
          subq.l    #1,d4               * L„nge runtersetzen
          bra       tlstar              * Und nun das Ganze wieder von vorn!

nochance:
          move.w    #1,nomatch          * Nix gefunden: Flagge setzen!
          rts

gotit:
          clr.w     nomatch             * Flagge auf "gefunden" setzen
          move.l    a3,a0               * Gefunden, Heureka!
          bsr       seticon             * Berechne passendes Icon
          rts

***************************************************
* Berechne zum Eintrag in a0 passende Iconadresse *
* Im wesentlichen Hex->Dez-Routine                *
* Schreibe diese in "newicon".                    *
***************************************************

seticon:  move.b    hpos(a0),d0         * Position der ersten Hexziffer
          bsr       pos
          move.b    d1,d2
          asl.w     #4,d2               * *16
          move.b    hpos+1(a0),d0       * | Position der 2. Hexziffer
          bsr       pos
          or.w      d1,d2
          and.l     #$ff,d2             * Nur dieses Hexbyte
          lsl.l     #8,d2               * *256 (Iconl„nge)
          move.l    icons,d1
          add.l     d1,d2               * + Iconstartadresse
          move.l    d2,newicon          * = Adresse des neuen Icons
          rts

********************************************
* Suche Offset eines Zeichens im Hexstring *
* Nur aufrufen, falls Zeichen auch darin!! *
********************************************

pos:      clr.b     d1                  * Startposition 0
          lea       hexstr,a1
poslp:    cmp.b     (a1)+,d0            * Zeichen gefunden?
          beq       posf                * Ja => Position zurckliefern
          addq.b    #1,d1               * Position++
          bra       poslp               * Wieder suchen
          trap      #7                  * Nix da, hier ausgeschlossen!!! (?)
posf:     rts

***********************************
* Ist String in ^a0 matchf„hig?   *
* (mit "string" (s. BSS))         *
*                                 *
* Erlaubt: 'XXXXXXXX.*  ' (1)     *
*          '*       .XXX' (2)     *
*          'XXXXXXXX.XXX' (3)     *
* Ergebnis ist sonst undefiniert! *
***********************************
* Ergebnis:                       *
* d0: 0=passt nicht, 1=passt      *
***********************************

match1:
          cmp.b     #'*',ppos+1(a0)     * Fall1 ?
          beq       backjok             * Ja, weiter dort
          cmp.b     #'*',(a0)           * Fall2 ?
          beq       frontjok            * Ja, weiter dort
          bra       direct              * Beides nicht, Fall3

*************************
* Matche '*       .XXX' *
*************************

frontjok: adda.w    #ppos+1,a0          * Suche erst ab Punkt
          lea       string,a1           * Suche den Punkt in ^a1
          moveq     #ppos,d7
fjlp:     cmp.b     #'.',(a1)+          * Steht da ein Punkt?
          beq       fpoint              * Ja, weiter mit Extension...
          dbf       d7,fjlp
fnix:     clr.w     d0                  * Kein Punkt, kein Match!
          rts
fpoint:   moveq     #3-1,d7             * Maximal 3 Zeichen hinter dem Punkt
fexcmp:   move.b    (a1),d0             * Lese akt. Zeichen
          cmp.b     (a0),d0             * =?
          bne       fchkend             * Nein, dann nachsehen, weiter
          addq.l    #1,a0               * Ja, weitervergleichen
          addq.l    #1,a1
          dbf       d7,fexcmp
ffound:   moveq     #1,d0
          rts
fchkend:  tst.b     (a1)                * Desktop-String zu Ende?
          bne       fnix                * Nein, kein Match!
          cmp.b     #' ',(a0)           * ' ' d.h. Ende des Matchstrings?
          beq       ffound              * Ja, gefunden!
          cmp.b     #'=',(a0)           * '=' d.h. Ende des Matchstrings?
          beq       ffound              * Ja, gefunden!
          bra       fnix                * Nein, leider verloren!

*************************
* Matche 'XXXXXXXX.*  ' *
*************************

backjok:  lea       string,a1
          moveq     #8-1,d7             * Maximal 8 Zeichen vor dem Punkt
bexcmp:   move.b    (a1),d0             * Lese akt. Zeichen
          cmp.b     (a0),d0             * =?
          bne       bchkend             * Nein, dann nachsehen, weiter
          addq.l    #1,a0               * Ja, weitervergleichen
          addq.l    #1,a1
          dbf       d7,bexcmp
bfound:   moveq     #1,d0               * Heureka!
          rts
bchkend:  tst.b     (a1)                * Desktop-String zu Ende?
          beq       st1end              * Ja! => weiter
          cmp.b     #'.',(a1)           * s.o.
          beq       st1end              * s.o
          bra       bnix                * Strings k”nnen nicht matchen!
st1end:   cmp.b     #'.',(a0)           * '.' d.h. Ende v. Matchstr.-Name?
          beq       bfound              * Ja, gefunden!
          cmp.b     #' ',(a0)           * ' ' d.h. Ende v. Matchstr.-Name?
          beq       bfound              * Ja, gefunden!
bnix:     clr.w     d0                  * Kein Punkt, kein Match! (Seufz!)
          rts

*************************
* Matche 'XXXXXXXX.XXX' *
*************************

direct:   move.l    a0,a2               * direct:=Name+Extension gleich:
          bsr       backjok             * Name gleich?
          tst.w     d0
          beq       dfail               * Nein, Strings ungleich
          move.l    a2,a0               * Originalzeiger wiederholen.
          cmp.b     #' ',ppos+1(a0)     * Existiert Extension?
          beq       dfound              * Nein => gefunden!
          bsr       frontjok            * Extension gleich?
          tst.w     d0
          beq       dfail               * Nein, Strings ungleich!
dfound:   moveq     #1,d0               * Beides gleich => Match gefunden!
          rts
dfail:    clr.w     d0                  * Nix gefunden!
          rts

******************************
* Gespeicherte Standardicons *
* (zum Vergleichen)          *
******************************

          DATA
          even
          dc.b      "SYS-ICONS:"                            * Hier evtl. ge-
*                                                           * „nderte System-(!)
*                                                           * ICONS reinpatchen!

dat:      dc.b      $00,$00,$00,$00,$1F,$FF,$FF,$80         * Datei-Icon
          dc.b      $10,$00,$00,$80,$10,$00,$00,$E0
          dc.b      $10,$00,$00,$A0,$10,$00,$00,$B8
          dc.b      $10,$00,$00,$A8,$10,$00,$00,$A8
          dc.b      $10,$00,$00,$A8,$10,$00,$00,$A8
          dc.b      $10,$00,$00,$A8,$10,$00,$00,$A8
          dc.b      $10,$00,$00,$A8,$10,$00,$00,$A8
          dc.b      $10,$00,$00,$A8,$10,$00,$00,$A8
          dc.b      $10,$00,$00,$A8,$10,$00,$00,$A8
          dc.b      $10,$00,$00,$A8,$10,$00,$00,$A8
          dc.b      $10,$00,$00,$A8,$10,$00,$3F,$A8
          dc.b      $10,$00,$21,$A8,$10,$00,$23,$28
          dc.b      $10,$00,$26,$28,$10,$00,$2C,$28
          dc.b      $10,$00,$38,$28,$1F,$FF,$F0,$28
          dc.b      $04,$00,$00,$28,$07,$FF,$FF,$E8
          dc.b      $01,$00,$00,$08,$01,$FF,$FF,$F8

datmsk:   dc.b      $00,$00,$00,$00,$1F,$FF,$FF,$80         * Datei-Maske
          dc.b      $1F,$FF,$FF,$80,$1F,$FF,$FF,$E0
          dc.b      $1F,$FF,$FF,$E0,$1F,$FF,$FF,$F8
          dc.b      $1F,$FF,$FF,$F8,$1F,$FF,$FF,$F8
          dc.b      $1F,$FF,$FF,$F8,$1F,$FF,$FF,$F8
          dc.b      $1F,$FF,$FF,$F8,$1F,$FF,$FF,$F8
          dc.b      $1F,$FF,$FF,$F8,$1F,$FF,$FF,$F8
          dc.b      $1F,$FF,$FF,$F8,$1F,$FF,$FF,$F8
          dc.b      $1F,$FF,$FF,$F8,$1F,$FF,$FF,$F8
          dc.b      $1F,$FF,$FF,$F8,$1F,$FF,$FF,$F8
          dc.b      $1F,$FF,$FF,$F8,$1F,$FF,$FF,$F8
          dc.b      $1F,$FF,$FF,$F8,$1F,$FF,$FF,$F8
          dc.b      $1F,$FF,$FF,$F8,$1F,$FF,$FF,$F8
          dc.b      $1F,$FF,$FF,$F8,$1F,$FF,$FF,$F8
          dc.b      $07,$FF,$FF,$F8,$07,$FF,$FF,$F8
          dc.b      $01,$FF,$FF,$F8,$01,$FF,$FF,$F8

prg:      dc.b      $00,$00,$00,$00,$00,$00,$00,$00         * Prg-Icon
          dc.b      $00,$00,$00,$00,$00,$00,$00,$00
          dc.b      $7F,$FF,$FF,$FC,$40,$00,$00,$04
          dc.b      $55,$55,$55,$56,$40,$00,$00,$06
          dc.b      $7F,$FF,$FF,$FE,$40,$00,$00,$06
          dc.b      $40,$00,$00,$06,$40,$00,$00,$06
          dc.b      $40,$00,$00,$06,$40,$00,$00,$06
          dc.b      $40,$00,$00,$06,$40,$00,$00,$06
          dc.b      $40,$00,$00,$06,$40,$00,$00,$06
          dc.b      $40,$00,$00,$06,$40,$00,$00,$06
          dc.b      $40,$00,$00,$06,$40,$00,$00,$06
          dc.b      $40,$00,$00,$06,$40,$00,$00,$06
          dc.b      $40,$00,$00,$06,$40,$00,$00,$06
          dc.b      $40,$00,$00,$06,$40,$00,$00,$06
          dc.b      $40,$00,$00,$06,$7F,$FF,$FF,$FE
          dc.b      $1F,$FF,$FF,$FE,$00,$00,$00,$00

prgmsk:   dc.b      $00,$00,$00,$00,$00,$00,$00,$00         * Prg-Icon
          dc.b      $00,$00,$00,$00,$00,$00,$00,$00
          dc.b      $7F,$FF,$FF,$FC,$7F,$FF,$FF,$FC
          dc.b      $7F,$FF,$FF,$FE,$7F,$FF,$FF,$FE
          dc.b      $7F,$FF,$FF,$FE,$7F,$FF,$FF,$FE
          dc.b      $7F,$FF,$FF,$FE,$7F,$FF,$FF,$FE
          dc.b      $7F,$FF,$FF,$FE,$7F,$FF,$FF,$FE
          dc.b      $7F,$FF,$FF,$FE,$7F,$FF,$FF,$FE
          dc.b      $7F,$FF,$FF,$FE,$7F,$FF,$FF,$FE
          dc.b      $7F,$FF,$FF,$FE,$7F,$FF,$FF,$FE
          dc.b      $7F,$FF,$FF,$FE,$7F,$FF,$FF,$FE
          dc.b      $7F,$FF,$FF,$FE,$7F,$FF,$FF,$FE
          dc.b      $7F,$FF,$FF,$FE,$7F,$FF,$FF,$FE
          dc.b      $7F,$FF,$FF,$FE,$7F,$FF,$FF,$FE
          dc.b      $7F,$FF,$FF,$FE,$7F,$FF,$FF,$FE
          dc.b      $1F,$FF,$FF,$FE,$00,$00,$00,$00

***********
* Strings *
***********

hexstr:   dc.b      "0123456789ABCDEF",0

iname2:   dc.b      "\ICONS"            * Name fr 2. Versuch erweitert
iname:    dc.b      "\ICONS.IMG",0      * Dateinamen fr Icondatei (Versuch 1)
mname2:   dc.b      "\ICONS"            * Name fr 2. Versuch erweitert
mname:    dc.b      "\ICONS.MAT",0      * Dateinamen fr Zuordnungsdatei (1.)

rderror:  dc.b      "Lesefehler beim Laden der Parameter!",13,10,0
notfound: dc.b      "ICONS.IMG oder ICONS.MAT nicht gefunden!",13,10,0
noram:    dc.b      "Zu wenig freier Speicher fr ICONDESK!",13,10,0
taste:    dc.b      "Bitte Taste drcken!",13,10,0
installst:dc.b      "ICONDESK ",v0+asciinull,'.',v1+asciinull
          dc.b      " resident. (C)1989 by St. Becker,"
          dc.b      " und D. Sabiwalsky.",13,10
          dc.b      "Idee: St. Neikes! Thanks: U. Lemke!",13,10,0
onlyauto: dc.b      27,"E"
          dc.b      "Icondesk l„uft nur aus dem AUTO-ORDNER!",13,10,0

***************
* Bss-Segment *
* (Variablen) *
***************

          BSS

string:   ds.w      ((maxstr+1)/2)+1    * Speicher fr VGTEXT-String!

clpbuf:   ds.w      paclen              * Puffer fr 1x Set-Clipping
vdibuf:   ds.w      maxcalls*paclen     * Puffer: aufgeschobene VDI-Calls

nomatch:  ds.w      1                   * Flagge: =1 kein Match gefunden!
icoffset: ds.w      1                   * Offset f. Newicon. 0=Daten, 128=Maske
clpvalid: ds.w      1                   * Flagge: 1 Gltige Clip-Daten
vdicount: ds.w      1                   * Anzahl VDI-Calls in vdibuf

slot0:    ds.l      1                   * Slot-0 VBL-Inhalt
matchlen: ds.l      1                   * L„nge der Matchdatei in Eintr„gen
icons:    ds.l      1                   * Zeiger auf geladene eigene Icons
matches:  ds.l      1                   * Zeiger auf geladene Zuordnungstab.
oldicon:  ds.l      1                   * Zeiger auf normales Desktop-Icon
newicon:  ds.l      1                   * Zeiger auf passendes Icon
vdid1:    ds.l      1                   * Zeiger auf akt. VDI-Parameter
vdiptr:   ds.l      1                   * Zeiger auf akt. Stelle v. vdibuf
os_start: ds.l      1                   * Start des Betrieystems
os_end:   ds.l      1                   * Ende des Betrieystems
oldvdi:   ds.l      1                   * Alter Vektor f. VDI-Aufrufe
bedarf:   ds.l      1                   * Speicherbedarf des Programms

stack:    ds.w      stacksize/2         * Speicher fr Programm-Stack
stacktop: ds.w      1

          end

