home *** CD-ROM | disk | FTP | other *** search
/ Gold Fish 2 / goldfish_vol2_cd1.bin / files / hard / misc / galer / source / galertest / port.asm < prev    next >
Encoding:
Assembly Source File  |  1993-12-21  |  16.3 KB  |  708 lines

  1.  
  2. *
  3. * This file is the interface between the software
  4. * and the hardware of GALer. The routines of this file
  5. * control the hardware.
  6. * register parameter, 32 bit integer
  7. *
  8. * used Assembler: assembler of SAS-C 6.0
  9. * assemble: asm Port.asm
  10. *
  11.  
  12.  
  13.  
  14. GAL16V8        EQU    1        ; GAL-Typ
  15. GAL20V8        EQU    2
  16.  
  17. IC1        EQU    3        ; IC-Nummer
  18. IC3        EQU    0
  19. IC4        EQU    1
  20. IC5        EQU    2
  21. IC6        EQU    0
  22. IC7        EQU    1
  23.  
  24. ON        EQU    1        ; für LED-Steuerung
  25. OFF        EQU    0
  26.  
  27. PROG        EQU    1        ; Edit-Mode für GAL
  28. VERIFY        EQU    0
  29.  
  30.  
  31.  
  32. ciaaprb        EQU    $BFE101
  33. ciaaddrb    EQU    $BFE301
  34. ciabpra        EQU    $BFD000
  35. ciabddra    EQU    $BFD200
  36.  
  37.  
  38.  
  39.     SECTION    code,CODE
  40.  
  41.  
  42.     XDEF    @InitParPort        ; Parallel-Port initialisieren
  43.     XDEF    @RestoreParPort        ; Parallel-Port restaurieren
  44.     XDEF    @InitGALer        ; GALer initialisieren
  45.     XDEF    @WriteByte        ; Byte in Schiebereg. schreiben
  46.     XDEF    @ReadByte        ; Byte aus Schiebereg. lesen
  47.     XDEF    @SetGAL            ; GAL-Type festlegen
  48.     XDEF    @VeditOn        ; Edit-Spannung aufbauen
  49.     XDEF    @VeditOff        ; Edit-Spannung abschalten
  50.     XDEF    @LED            ; LED ansteuern
  51.     XDEF    @EnableVcc        ; Vcc anlegen
  52.     XDEF    @DisableVcc        ; Vcc abschalten
  53.     XDEF    @EnableVEdit        ; Edit-Spannung anlegen
  54.     XDEF    @DisableVEdit        ; Edit-Spannung abschalten
  55.     XDEF    @EnableOutput        ; Ausgangs-Treiber aktivieren
  56.     XDEF    @DisableOutput        ; Ausgangs-Treiber deaktiviern
  57.     XDEF    @SetRow            ; Adresse an RAG0-RAG5 anlegen
  58.     XDEF    @SDIn            ; Lege ein Bit an SDIn-Eingang
  59.     XDEF    @SDOut            ; Bit vom SDOut-Ausgang holen
  60.     XDEF    @Clock            ; Clock-Impuls an SCLK-Eingang
  61.     XDEF    @STRImpuls        ; STR-Impuls erzeugen
  62.     XDEF    @EditMode        ; setzt Bits für Edit-Mode
  63.     XDEF    @ExitEditMode        ; Edit-Mode verlassen und Vcc weg
  64.     XDEF    @SetPV            ; VERIFY oder PROG
  65.     XDEF    @SetVolt        ; Edit-Spannung einstellen
  66.  
  67.  
  68.     XREF    _GALType
  69.     XREF    _outIC1
  70.     XREF    _outIC3
  71.     XREF    _outIC4
  72.     XREF    _outIC5
  73.  
  74.     XREF    @WaitForTimer
  75.  
  76.     XREF    _LVOForbid
  77.     XREF    _LVOPermit
  78.  
  79.     XREF    _prog_volt
  80.  
  81.  
  82.  
  83.  
  84. * initialisiere den Parallel-Port
  85. @InitParPort:
  86.     move.b    ciaaddrb,cia_addrb        ; Datenrichtung der CIAs
  87.     move.b    ciabddra,cia_bddra        ; merken
  88.  
  89.     move.b    #%11111111,ciaaddrb    ; Datenleitungen auf Ausgang schalten
  90.     and.b    #%11111110,ciabddra    ; BUSY auf Eingang
  91.     rts
  92.  
  93.  
  94. * Parallel-Port restaurieren
  95. @RestoreParPort:
  96.     move.b    cia_addrb,ciaaddrb    ; Datenrichtungen der CIAs restau-
  97.                     ; rieren. Der Zustand der Ausgänge
  98.     move.b    cia_bddra,d0        ; wird nicht wieder hergestellt, da
  99.     and.b    #%11111110,ciabddra    ; sonst der angeschlossene GAL-Brenner
  100.     and.b    #%00000001,d0        ; ein unerwünchstes Signal empfangen
  101.     or.b    d0,ciabddra        ; könnte (z.B. Vcc oder VEdit anlegen)
  102.     rts
  103.  
  104.  
  105.  
  106. * GALer initialisieren: alle Ausgänge von IC1 auf LOW (kein OutputEnable
  107. * für IC3,4,5 aber Register-Inhalt von IC3,4,5 auf LOW stellen)
  108. * Parameter: keine
  109. @InitGALer:
  110.     or.b    #%00001000,ciaaprb    ; PD3=H: Adressdecoder deaktivieren!
  111.     and.b    #%00001000,ciaaprb    ; alle anderen Datenleitungen auf LOW
  112.             ; ACHTUNG!!!: PD3 darf nur auf LOW-Pegel gehen
  113.             ; (Adressdecoder aktiviert werden), wenn durch PD0 und
  114.             ; PD1 das IC, das angesprochen werden soll, bereits
  115.             ; selektiert ist. Ansonsten bekommt ein IC einen Takt-
  116.             ; impuls und beim nächsten Strobe liegen dann die
  117.             ; falschen Daten an.
  118.     move.l    #IC1,d1
  119.     moveq    #0,d0
  120.     bsr    @WriteByte        ; Ausgänge von IC1 auf LOW    
  121.  
  122.     move.l    #IC3,d1
  123.     moveq    #0,d0
  124.     bsr    @WriteByte        ; Ausgänge von IC3 auf LOW    
  125.  
  126.     move.l    #IC4,d1
  127.     moveq    #0,d0
  128.     bsr    @WriteByte        ; Ausgänge von IC4 auf LOW    
  129.  
  130.     move.l    #IC5,d1
  131.     moveq    #0,d0
  132.     bsr    @WriteByte        ; Ausgänge von IC5 auf LOW    
  133.     rts
  134.  
  135.  
  136.  
  137. * SetGAL:
  138. * Setzte GAL-Type fest (GAL16V8, GAL20V8)
  139. * Aufruf: SetGAL(type);
  140. *
  141. @SetGAL:
  142.     move.l    d0,_GALType
  143.     rts
  144.  
  145.  
  146.  
  147. * VeditOn:
  148. * schaltet den Sperrwandler an (IC9); siehe auch VeditOff
  149. * Auruf: VeditOn();
  150. @VeditOn:
  151.     move.l    #IC1,d1
  152.     or.l    #%00001,_outIC1        ; Q1 von IC1 auf HIGH => VeditOn
  153.     move.l    _outIC1,d0
  154.     bsr    @WriteByte        ; IC1 setzen
  155.     rts
  156.  
  157.  
  158. * VeditOff:
  159. * schaltet den Sperrwandler aus (IC9); siehe auch VeditOn
  160. * Auruf: VeditOff();
  161. @VeditOff:
  162.     move.l    #IC1,d1
  163.     and.l    #%11111110,_outIC1    ; Q1 von IC1 auf LOW => VeditOff
  164.     move.l    _outIC1,d0
  165.     bsr    @WriteByte        ; IC1 setzen
  166.     rts
  167.  
  168.  
  169. * EnableVEdit:
  170. * schaltet die Edit-Spannung (+16.5V) auf Pin 2 oder Pin 4 vom Textool
  171. * (abhänging vom eingestellten GAL-Typ)
  172. * Aufruf: EnableVEdit();
  173. @EnableVEdit:
  174.     move.l    #IC1,d1            ; IC1 einstellen
  175.     cmp.l    #GAL16V8,_GALType    ; 16V8 eingestellt?
  176.     bne.s    1$            ; nein, dann wird 20V8 angenommen!
  177.     moveq    #%00000100,d0        ; Q3 von IC1 auf HIGH
  178.     bra.s    2$
  179. 1$    moveq    #%00000010,d0        ; Q2 von IC1 auf HIGH
  180. 2$    or.l    d0,_outIC1
  181.     move.l    _outIC1,d0
  182.     bsr    @WriteByte
  183.     rts
  184.  
  185.  
  186. * DisableVEdit:
  187. * schaltet die Edit-Spannung (+16.5V) an Pin 2 oder Pin 4 aus
  188. * (abhänging vom eingestellten GAL-Typ)
  189. * Aufruf: DisableVEdit();
  190. @DisableVEdit:
  191.     move.l    #IC1,d1        ; IC1 einstellen
  192.     cmp.l    #GAL16V8,_GALType    ; 16V8 eingestellt?
  193.     bne.s    1$            ; nein, dann wird 20V8 angenommen!
  194.     move.l    #%11111011,d0        ; Q3 von IC1 auf LOW
  195.     bra.s    2$
  196. 1$    move.l    #%11111101,d0        ; Q2 von IC1 auf low
  197. 2$    and.l    d0,_outIC1
  198.     move.l    _outIC1,d0
  199.     bsr    @WriteByte
  200.     rts
  201.  
  202.  
  203.  
  204.  
  205. * LED:
  206. * schaltet die LED aus bzw. an
  207. * Aufruf: LED(ON/OFF);
  208. @LED:
  209.     cmp.l    #ON,d0
  210.     bne.s    2$
  211.     or.l    #%01000000,_outIC1
  212.     bra.s    1$
  213. 2$    and.l    #%10111111,_outIC1
  214. 1$    move.l    #IC1,d1
  215.     move.l    _outIC1,d0
  216.     bsr    @WriteByte        ; IC1 setzen
  217.     rts
  218.  
  219.  
  220.  
  221. * EnableVcc:
  222. * schaltet die Spannungsversorgung ein; siehe auch DisableVcc
  223. * bei GAL16V8: Pin22 vom Textool-Sockel
  224. * bei GAL20V8: Pin24 vom Textool-Sockel
  225. * Aufruf: EnableVcc();
  226. @EnableVcc:
  227.     movem.l    d0-d7/a0-a6,-(sp)    ; Register retten
  228.     move.l    #300000,d0        ; 300 ms warten
  229.     jsr    @WaitForTimer
  230.     movem.l    (sp)+,d0-d7/a0-a6
  231.  
  232.     move.l    #IC1,d1            ; IC1 selektieren
  233.     cmp.l    #GAL16V8,_GALType    ; 16V8 eingestellt?
  234.     bne.s    1$            ; nein, dann wird 20V8 angenommen!!!
  235.     moveq    #%00011000,d0        ; Q4,5 von IC1 auf HIGH=>+5V an Pin22
  236.     bra.s    2$
  237. 1$    moveq    #%00010000,d0        ; Q5 auf HIGH => +5V an Pin 24    
  238. 2$    or.l    d0,_outIC1
  239.     move.l    _outIC1,d0
  240.     bsr    @WriteByte        ; IC1 setzen
  241.     rts
  242.  
  243.  
  244. * DisableVcc:
  245. * schaltet die Spannungsversorgung aus; siehe auch EnableVcc
  246. * bei GAL16V8: Pin22 vom Textool-Sockel
  247. * bei GAL20V8: Pin24 vom Textool-Sockel
  248. * Aufruf: DisableVcc();
  249. @DisableVcc:
  250.     movem.l    d0-d7/a0-a6,-(sp)    ; Register retten
  251.     move.l    #50000,d0        ; sicherheitshalber 50mS warten, bis
  252.     jsr    @WaitForTimer        ; das GAL die letzte Aktion richtig
  253.     movem.l    (sp)+,d0-d7/a0-a6
  254.  
  255.     move.l    #IC1,d1            ; IC1 selektieren
  256.     cmp.l    #GAL16V8,_GALType    ; 16V8 eingestellt?
  257.     bne.s    1$            ; nein, dann wird 20V8 angenommen!!!
  258.     move.l    #%11100111,d0        ; Q4,5 von IC1 auf LOW
  259.     bra.s    2$
  260. 1$    move.l    #%11101111,d0        ; Q5 auf HIGH
  261. 2$    and.l    d0,_outIC1
  262.     move.l    _outIC1,d0
  263.     bsr    @WriteByte        ; IC1 setzen
  264.     rts
  265.  
  266.  
  267.  
  268. * EnableOutput:
  269. * OutputEnable-Eingang (OE) von IC3, IC4, IC5 auf HIGH
  270. * Aufruf: EnableOutput();
  271. @EnableOutput:
  272.     move.l    #IC1,d1
  273.     or.l    #%00100000,_outIC1
  274.     move.l    _outIC1,d0
  275.     bsr    @WriteByte
  276.     rts
  277.  
  278. * DisableOutput:
  279. * OutputEnable-Eingang (OE) von IC3, IC4, IC5 auf LOW
  280. * Aufruf: DisableOutput();
  281. @DisableOutput:
  282.     move.l    #IC1,d1
  283.     and.l    #%11011111,_outIC1
  284.     move.l    _outIC1,d0
  285.     bsr    @WriteByte
  286.     rts
  287.  
  288.  
  289.  
  290. * ReadByte:
  291. * lese ein Byte aus dem IC "ICx", wobei ICx=IC6 (nur ein Bit) oder IC7 ist
  292. * Aufruf: byte=ReadByte(IC);
  293. * PD3 ist bereits HIGH (muß es auch!, siehe InitGAL und Beschreibung zu PD3)
  294. @ReadByte:
  295.     cmp.l    #IC6,d0            ; IC6 angesprochen?
  296.     bne.s    IC7$            ; nein, dann IC7
  297.     or.b    #%00000001,ciaaprb    ; PD0 auf HIGH=>HIGH am Clk vom IC7
  298.                     ; PD0 auf HIGH setzen=>IC6a selektiert
  299.  
  300.     movem.l    d0-d7/a0-a6,-(sp)    ; Register retten
  301.     move.l    #1,d0            ; 1 us warten
  302.     jsr    @WaitForTimer
  303.     movem.l    (sp)+,d0-d7/a0-a6
  304.  
  305.     moveq    #0,d0
  306.     move.b    ciabpra,d0
  307.     not.b    d0            ; invertieren
  308.     and.b    #%00000001,d0        ; BUSY-Bit ausmaskieren
  309.     bra.s    ready$            ; Pin22 (über IC6) ist ausgelesen
  310. IC7$
  311.     moveq    #0,d0
  312.  
  313.     and.b    #%11111110,ciaaprb    ; PD3 ist HIGH=>Lesen möglich
  314.     nop
  315.     or.b    #%00000100,ciaaprb    ; PD2 (Strobe) auf HIGH-> Daten werden
  316.     and.b    #%11111011,ciaaprb    ; vom Eingangsreg. in das Schiebereg.
  317.                     ; übernommen. Dann PD2 wieder auf LOW.
  318.                     ; PD3 ist auf HIGH=>Lesen ist möglich
  319.     move.l    d2,-(sp)
  320.     moveq    #7,d2            ; Schleifenzähler
  321. l$    rol.b    #1,d0
  322.     move.b    ciabpra,d1        ; BUSY-Bit holen
  323.     and.b    #%00000001,d1        ; BUSY-Bit ausmaskieren
  324.     or.b    d1,d0            ; BUSY-Bit in D0 eintragen
  325.     and.b    #%11111110,ciaaprb    ; PD0 auf LOW=>LOW am Clk-Eingang (IC7)
  326.     or.b    #%00000001,ciaaprb    ; PD0 auf HIGH=>HIGH am Clk-Eingang
  327.                     ; ==> nächstes Bit steht am Ausgang
  328.     nop
  329.     nop
  330.     and.b    #%11111110,ciaaprb    ; PD0 auf LOW=>IC6b ist selektiert (=>lesen möglich)
  331.     dbf    d2,l$            ; 8 Bits auslesen
  332.     not.b    d0            ; invertieren
  333.     move.l    (sp)+,d2
  334. ready$
  335.     rts                ; D0=Rückgabewert (gelesenes Byte)
  336.  
  337.  
  338.  
  339.  
  340. * WriteByte:
  341. * schreibt das Byte "byte" in das IC "IC", wobei IC=IC1, IC3, IC4 oder IC5
  342. * sein kann
  343. * zuerst wird das MSB übertragen!!!
  344. * Aufruf: WriteByte(byte,IC)
  345. @WriteByte:
  346.     movem.l    d2/d3,-(sp)        ; Register retten
  347.                     ; Datenbyte in D0
  348.                     ; IC in D1
  349.                 ; geschriebenes Byte mitprotokolieren
  350.     cmp.l    #IC1,d1
  351.     bne.s    1$
  352.     move.l    d0,_outIC1
  353.     bra.s    cont$
  354. 1$    cmp.l    #IC3,d1
  355.     bne.s    2$
  356.     move.l    d0,_outIC3
  357.     bra.s    cont$
  358. 2$    cmp.l    #IC4,d1
  359.     bne.s    3$
  360.     move.l    d0,_outIC4
  361.     bra.s    cont$
  362. 3$    move.l    d0,_outIC5
  363. cont$
  364.  
  365.     and.b    #%11111100,ciaaprb    ; PD0 und PD1 setzen (IC aus-
  366.     or.b    d1,ciaaprb        ; wählen)
  367.     and.b    #%11110111,ciaaprb    ; Adressdecoder aktivieren
  368.  
  369.     moveq    #7,d3            ; Schleifenzähler
  370.     ror.b    #3,d0            ; MSB nach D4 (Datenleitung)
  371.  
  372. loop$    move.b    d0,d2            ; Datenbyte sichern
  373.     and.b    #%00010000,d2        ; Datenbit ausmaskieren
  374.     or.b    d2,ciaaprb        ; Datenbit (PD4) vom Par.-Port setzen
  375.  
  376.     or.b    #%00001000,ciaaprb    ; Clock-Impuls durch PD3 geben
  377.     and.b    #%11110111,ciaaprb    ; LOW-HIGH Übergang
  378.  
  379.     and.b    #%11101111,ciaaprb    ; Datenbit (PD4) auf LOW
  380.  
  381.     rol.b    #1,d0            ; nächstniedrigeres Bit senden
  382.     dbf    d3,loop$
  383.  
  384.     or.b    #%00001000,ciaaprb    ; Adressdecoder wieder deaktivieren!!!
  385.                     ; (sehr WICHTIG, siehe InitGAL:)
  386.     or.b    #%00000100,ciaaprb    ; PD2 (Strobe) auf HIGH-> Daten werden
  387.     and.b    #%11111011,ciaaprb    ; vom Schieberegister in das Datenreg.
  388.                     ; übernommen. Dann PD2 wieder auf LOW.
  389.     movem.l    (sp)+,d2/d3
  390.     rts
  391.  
  392.  
  393. * SetRow:
  394. * Adresse an RAG0-RAG5 anlegen
  395. * Aufruf: SetRow(row);
  396. * row:      zu adressierende Zeile (0-63)
  397. @SetRow:
  398.  
  399.                     ; RAG5 setzen (Pin bei 16 und 20V8 gleich)
  400.     move.l    d0,-(sp)        ; Row (D0) auf Stack
  401.  
  402.     and.l    #$fe,_outIC5        ; Bit0(=RAG5) löschen
  403.     asr.b    #5,d0            ; Bit0 von D0=RAG5
  404.     or.l    d0,_outIC5        ; RAG5=Bit von D0=> RAG5 gesetzt
  405.  
  406.     cmp.l    #GAL16V8,_GALType    ; GAL16V8?
  407.     bne.s    GAL20V8$        ; nein, dann GAL20V8 annehmen
  408. GAL16V8$                ; RAG0 setzen
  409.     move.l    (sp),d0            ; row holen
  410.     and.l    #$ef,_outIC3        ; Bit4(=RAG0) löschen
  411.     and.l    #1,d0            ; Bit0 von "row" ausmaskieren
  412.     asl.b    #4,d0
  413.     or.l    d0,_outIC3        ; Bit4(=RAG0) setzen
  414.                     ; RAG1-RAG4 setzen
  415.     move.l    (sp),d0            ; row holen
  416.     and.l    #$0f,_outIC4        ; Bit4-7(=RAG1-RAG4) löschen
  417.     and.l    #%00011110,d0        ; Bit1-4 von "row" ausmaskieren
  418.     asl.l    #3,d0            ; an Bit4-7 schieben
  419.     or.l    d0,_outIC4        ; RAG1-RAG4 setzen
  420.     bra.s    write$
  421. GAL20V8$                ; RAG0 für GAL20V8 setzen
  422.      move.l    (sp),d0            ; row holen
  423.     and.l    #%11011111,_outIC3    ; Bit5(=RAG0) löschen
  424.     and.l    #1,d0            ; Bit0 von "row" ausmaskieren
  425.     asl.b    #5,d0
  426.     or.l    d0,_outIC3        ; Bit5(=RAG0) setzen
  427.                     ; RAG4 setzen
  428.     move.l    (sp),d0            ; row holen
  429.     and.l    #%01111111,_outIC4    ; Bit7(=RAG4) löschen
  430.     and.l    #%00010000,d0        ; Bit4 von "row" ausmaskieren
  431.     asl.l    #3,d0
  432.     or.l    d0,_outIC4        ; Bit7(=RAG4) setzen
  433.                     ; RAG1-RAG3 setzen
  434.     move.l    (sp),d0            ; row holen
  435.     and.l    #%11100011,_outIC4    ; Bit2-4(=RAG1-RAG3) löschen
  436.     and.l    #%00001110,d0        ; Bit1-3 aus "row" ausmaskieren
  437.     asl.l    #1,d0
  438.     or.l    d0,_outIC4        ; RAG1-RAG3 setzen
  439.  
  440. write$                    ; errechnete Werte in ICs schreiben
  441.     move.l    #IC3,d1
  442.     move.l    _outIC3,d0
  443.     bsr    @WriteByte
  444.  
  445.     move.l    #IC4,d1
  446.     move.l    _outIC4,d0
  447.     bsr    @WriteByte
  448.  
  449.     move.l    #IC5,d1
  450.     move.l    _outIC5,d0
  451.     bsr    @WriteByte
  452.  
  453.     addq.l    #4,sp            ; Stack korrigieren
  454.     rts
  455.  
  456.  
  457.  
  458. * SDIn:
  459. * lege ein Bit an den SDIn-Eingang (Pin 11 vom Textool-Sockel)
  460. * Aufruf: SDIn(bit);    bit: 0=LOW; 1=HIGH
  461. @SDIn:
  462.                     ; Bit steht in d0
  463.     asl.b    #2,d0            ; an die richtige Stelle schieben
  464.     and.l    #%11111011,_outIC5    ; SDIn-Bit löschen
  465.     or.l    d0,_outIC5        ; Bit auf LOW oder HIGH setzen
  466.     move.l    #IC5,d1
  467.     move.l    _outIC5,d0
  468.     bsr    @WriteByte
  469.     rts
  470.  
  471.  
  472. * SDOut:
  473. * ein Bit aus dem SDOut-Ausgang lesen
  474. * Pin 14 (GAL16V8), Pin 15 (GAL20V8) am Textool-Sockel
  475. * Aufruf: bit=SDOut();
  476. * bit: 0: SDOut-Pin ist LOW; 1: SDOut-Pin ist HIGH
  477. @SDOut:
  478.     move.l    #IC7,d0            ; ein Byte aus IC7 holen
  479.     bsr    @ReadByte        ; Bit0=Pin14, Bit1=Pin15
  480.  
  481.     cmp.l    #GAL16V8,_GALType    ; GAL16V8 eingestellt?
  482.     bne.s    1$            ; nein, dann GAL20V8
  483.     and.l    #1,d0            ; Bit0 ausmaskieren
  484.     bra.s    2$            ; D0=Bit
  485.                     ; GAL20V8
  486. 1$    asr.l    #1,d0            ; SDOut-Bit an Bit-Pos. 0
  487.     and.l    #1,d0
  488. 2$                    ; 32-Bit-Ergebnis in D0
  489.     rts
  490.  
  491.  
  492.  
  493.  
  494. * Clock:
  495. * erzeuge Clock-Impuls (Low-High-Low-Übergang) am SCLK-Eingang (Pin 10
  496. * vom Textool-Sockel
  497. * Aufruf: Clock();
  498. @Clock:
  499.     or.l    #%00000010,_outIC5    ; SCLK-Bit auf HIGH
  500.     move.l    #IC5,d1
  501.     move.l    _outIC5,d0
  502.     bsr    @WriteByte
  503.  
  504.     and.l    #%11111101,_outIC5    ; SCLK-Bit auf LOW
  505.     move.l    #IC5,d1
  506.     move.l    _outIC5,d0
  507.     bsr    @WriteByte
  508.  
  509.     rts
  510.  
  511.  
  512.  
  513. * STRImpuls:
  514. * setzt /STR-Eingang (Pin 13 am Textool-Socker) für die Dauer von "STRLength"
  515. * auf LOW
  516. * Aufruf: STRImpuls(long STRLength);
  517. * STRLength: Dauer des Low-Impulses in Mikrosekunden (Langwort!)
  518. @STRImpuls:
  519.     movem.l    d0-d7/a0-a6,-(sp)    ; Register retten
  520.  
  521.     move.l    4,a6
  522.     jsr    _LVOForbid(a6)
  523.  
  524.     and.l    #%11110111,_outIC5    ; STR-Pin auf LOW
  525.     move.l    #IC5,d1
  526.     move.l    _outIC5,d0
  527.     bsr    @WriteByte
  528.  
  529.     cmp.l    #100,(sp)        ; bis ein Wert in ein IC getaktet wird
  530.     bls.s    1$            ; vergehen ca. 100us => keinen Timer
  531.     move.l    (sp),d0            ; Dauer des Impulses in Mikrosekunden
  532.     jsr    @WaitForTimer        ; Low-Impuls
  533. 1$
  534.     or.l    #%00001000,_outIC5    ; STR-Pin wieder auf HIGH
  535.     move.l    #IC5,d1
  536.     move.l    _outIC5,d0
  537.     bsr    @WriteByte
  538.  
  539.     jsr    _LVOPermit(a6)
  540.  
  541.     movem.l    (sp)+,d0-d7/a0-a6    ; Registerinhalte zurückholen
  542.     rts
  543.  
  544.  
  545.  
  546. * SetPV:
  547. * Legt am P/V-Pin den entsprechenden Pegel für "Programmieren" bzw.
  548. * "Verify" an.
  549. * Aufruf:  SetPV(mode);
  550. * mode :   VERIFY (lesen, P/V low), PROG (schreiben, P/V high)
  551. @SetPV:
  552.                     ; Mode steht in D0
  553.     cmp.l    #GAL16V8,_GALType    ; GAL16V8?
  554.     bne.s    1$            ; nein, dann 1
  555.  
  556.     move.l    _outIC3,d1
  557.     and.l    #%11111011,d1
  558.     asl.b    #5,d0            ; Mode-Bit zu Bit 5 schieben
  559.     or.l    d0,d1
  560.     move.l    d1,d0            ; P/V setzen
  561.     move.l    #IC3,d1            ; IC3 setzen
  562.     bsr    @WriteByte
  563.     bra.s    2$
  564. 1$    
  565.     move.l    _outIC3,d1
  566.     and.l    #%11111101,d1
  567.     asl.b    #6,d0            ; Mode-Bit zu Bit 6 schieben
  568.     or.l    d0,d1
  569.     move.l    d1,d0            ; P,/V-Bit setzen
  570.     move.l    #IC3,d1            ; IC3 setzen
  571.     bsr    @WriteByte
  572. 2$
  573.     rts
  574.  
  575.  
  576.  
  577.  
  578.  
  579. * Edit-Mode:
  580. * schaltet das GAL in den Edit-Mode; /STR auf HIGH; P/V auf LOW
  581. * Aufruf: EditMode(mode);
  582. * mode: PROG oder VERIFY (für Spannungseinstellung)
  583. @EditMode:
  584.     movem.l    d0-d7/a0-a6,-(sp)    ; Register sichern
  585.  
  586.                     ; GAL-Typ auswählen
  587.     cmp.l    #GAL16V8,_GALType   ; GAL16V8?
  588.     bne.s    1$            ; nein, dann 1
  589.  
  590.     move.l    #IC3,d1            ; IC3, P/V auf LOW
  591.     move.l    #%00000000,d0
  592.     bsr    @WriteByte
  593.  
  594.     move.l    #IC4,d1
  595.     move.l    #%00000000,d0        ; IC4 initialisieren
  596.     bsr    @WriteByte
  597.  
  598.     move.l    #IC5,d1            ; /STR auf HIGH
  599.     move.l    #%00011000,d0        ; IC5 initialisieren
  600.     bsr    @WriteByte
  601.     bra.s    2$
  602. 1$                    ; GAL20V8
  603.     move.l    #IC3,d1            ; IC3, P/V auf LOW
  604.     move.l    #%00000000,d0
  605.     bsr    @WriteByte
  606.  
  607.     move.l    #IC4,d1
  608.     move.l    #%00000000,d0        ; IC4 initialisieren
  609.     bsr    @WriteByte
  610.  
  611.     move.l    #IC5,d1            ; /STR auf HIGH
  612.     move.l    #%00101000,d0        ; IC5 initialisieren
  613.     bsr    @WriteByte
  614. 2$
  615.  
  616.                     ; richtige Spannung auswählen
  617.     cmp.l    #VERIFY,(sp)        ; Lesen?
  618.     bne.s    3$            ; nein, dann Programmieren!
  619.     move.l    #4,d0            ; ja, dann 12.00 Volt einstellen
  620.     bsr    @SetVolt
  621.     bra.s    4$
  622. 3$
  623.     move.l    _prog_volt,d0        ; Programmierspannung einstellen
  624.     bsr    @SetVolt
  625. 4$        
  626.  
  627.     bsr    @VeditOn        ; Edit-Spannung aufbauen
  628.  
  629.     move.l    #50000,d0        ; 50 ms warten, bis sich die
  630.     jsr    @WaitForTimer        ; Edit-Spannung aufgebaut hat
  631.  
  632.     bsr    @EnableOutput        ; Bits anlegen
  633.     bsr    @EnableVcc        ; Vcc anlegen
  634.  
  635.     move.l    #100000,d0        ; Prellzeit der Relais überbrücken
  636.     jsr    @WaitForTimer
  637.  
  638.     bsr    @EnableVEdit        ; Edit-Spannung anlegen
  639.                     ; GAL befindet sich jetzt im Edit-Mode
  640.     move.l    #5,d0            ; 5 us warten bevor nächste Aktion
  641.     jsr    @WaitForTimer        ; erlaubt ist
  642.  
  643.     movem.l    (sp)+,d0-d7/a0-a6    ; Registerinhalte zurückholen
  644.     rts
  645.  
  646.  
  647.  
  648. * ExitEditMode:
  649. * Schaltet zuerst VEdit und VCC ab, dann wird der Inhalt der ICs
  650. * zurückgesetzt.
  651. * Aufruf: ExitEditMode();
  652. @ExitEditMode:
  653.     movem.l    d0-d7/a0-a6,-(sp)    ; Register sichern
  654.  
  655.     bsr    @DisableVEdit
  656.  
  657.     bsr    @DisableVcc
  658.  
  659.     bsr    @InitGALer
  660.  
  661.     bsr    @EnableOutput
  662.  
  663.     movem.l    (sp)+,d0-d7/a0-a6
  664.     rts
  665.  
  666.  
  667.  
  668. * SetVolt:
  669. * selektiert durch IC 10 und IC11 die gewünschte Spannung
  670. * Aufruf: SetVolt(value);
  671. * value:  0=16.50 Volt; 1=15.75 Volt; 2=14.5 Volt; 3=14.00 Volt; 4=12.00 Volt
  672. *
  673. @SetVolt:
  674.                     ; Parameter in D0
  675.     move.l    d0,-(sp)        ; Wert sichern
  676.  
  677.     and.l    #%00000001,d0
  678.     rol.l    #7,d0
  679.     and.l    #%01111111,_outIC1
  680.     or.l    d0,_outIC1        ; Q8 (Pin 11) von IC1 setzen
  681.     move.l    _outIC1,d0
  682.     move.l    #IC1,d1
  683.     bsr    @WriteByte
  684.  
  685.     move.l    (sp)+,d0
  686.     and.l    #%00000110,d0
  687.     rol.l    #5,d0
  688.     and.l    #%00111111,_outIC5
  689.     or.l    d0,_outIC5        ; Q7 und Q8 von IC5 setzen
  690.     move.l    _outIC5,d0
  691.     move.l    #IC5,d1
  692.     bsr    @WriteByte
  693.  
  694.     rts
  695.  
  696.  
  697.  
  698.  
  699.     SECTION    data,DATA
  700.  
  701.  
  702. ; Zwischenspeicher, um Register zu retten ohne den Stack zu benützen
  703.  
  704. cia_addrb:    dc.b    0
  705. cia_bddra:    dc.b    0
  706.  
  707.     END
  708.