;Tabulatoren mit quickbasic programm entfernen
;Text in AVR studio markieren (alles)
;kopieren
;in MS word einfgen
;seitenlayout auf 2cm linke und rechter rand (nicht mehr)
;alles markieren
;courier new  +8 cpi einstellen
;drucken

;------------------------------------------------------------------------------------------------
;
;
;
;                               IEC2IEEE
;
;                          without any warranty
;                                                                        2  C
;                                                                        5  n
;                                                                        s  t
;                                                                        u  r
;                                                                        b  n
;       IEC-BUS                              IEEE-BUS        CENTRONICS  D  c
;at    /       \                                                         -  s
;flashing      normal                         IIIIII           IIIIIIII  p  -
;IIIIIIII      IIIIII                         VVVVVV           VVVVVVVV  l  p
;VVVVVVVV      VVVVVV                                                    u  l
;                                                                        g  u
;                                                                           g
;                     (reset)        
;                   ------------------------- IFC  9 (--I<--)  Prime    16 31
;                  I       
;                  I            ----   ----                                  
;                   --<I--     I1   I I  40I                                 
;                         I    Ipb0  -  vccI--- +5V  (pin7 of C64 joystickport)
;        -----------------     I           I  '-------------------------------
;       I                      I2        39I                                  I
;       I   1 SRQin  -----I>---Ipb1     pa0I- Dt1  1 ---I<---  Data1     2  2 I
;       I                      I           I                                  I
;       I                      I3        38I                                  I
;       I   4 CLKout -----<I---Ipb2  A  pa1I- Dt2  2 ---I<---  Data2     3  3 I
;       I                      I     T     I                                  I
;       I                      I4    M   37I                                  I
;       I   4 CLKin  -----I>---Ipb3  E  pa2I- Dt3  3 ---I<---  Data3     4  4 I
;       I  ------------------' I     L     I                                  I
;       I I                    I5        36I                                  I
;       I I 5 DTAout -----<I---Ipb4  A  pa3I- Dt4  4 ---I<---  Data4     5  5 I
;       I I                    I     V     I                                  I
;       I I                    I6    R   35I                                  I
;       I I 5 DTAin  -----I>---Ipb5     pa4I- Dt5 13 ---I<---  Data5     6  6 I
;       I I                    I     A     I                                  I
;       I I                    I7    T   34I                                  I
;       I I 1 SRQout -----<I---Ipb6  M  pa5I- Dt6 14 ---I<---  Data6     7  7 I
;       I I                    I     E     I                                  I
;       I I       o#1          I8    G   33I                                  I
;CLKin  I I   (JC)o------------Ipb7  A  pa6I- Dt7 15 ---I<---  Data7     8  8 I
;       I  -------o#2      #1  I     8     I                                  I
;       I   6 RSTin -I>----o   I9    5   32I                                  I
;GND     ---------------'  o---Irst  1  pa7I- Dt8 16 ---I<---  Data8     9  9 I
;                        ,-o I I     5     I                                  I
;          --------------' #2I I10       31I                                  I
;         I              (JR)I Ipd0     icpI                                  I
;         I                  I I           I                                  I
;         I   +5V-[r=1kOhm]--  I11       30I                                  I
;         I                    Ipd1     aleI                                  I
;         I                    I           I    ^^                            I
;         I                    I12       29I    II              (+5V)         I
;         I 3 ATNin -----I>----Ipd2    oc1bI----<I--[R=1.8kOhm]---------------
;         I                    I           I                    I
;         I                    I13       28I                    I
;         I                    Ipd3     pc7I- EOI  5            I
;         I                    I           I                    I
;         I                    I14       27I                     -[+C=22uF]-
;         I                    Ipd4     pc6I- DAV  6                        I
;         I                    I           I                                I
;         I                    I15       26I                                I
;         I                    Ipd5     pc5I- NRFD 7                        I
;         I                    I           I                                I
;         I                    I16       25I                                I
;         I                    Ipd6     pc4I- NDAC 8                        I
;         I                    I           I                   #1           I  
;         I                    I17       24I              (JD) o-           I
;         I                    Ipd7     pc3I- ATN 11    -------o      (GND) I
;         I                    I           I           I     #2o--------------
;         I                    I18       23I           I                      I
;         I                    Ixtal2   pc2I---------------I<- Strobe    1  1 I
;         I                    I           I                                  I
;         I                    I19       22I            ,--I<- PaperOut 12 12 I
;         I                    Ixtal1   pc1I--------------I<-- Select   13 13 I
;         I                    I           I I       I  '--I<- Error    15 32 I
;          ------------------, I20       21I  -I<-,  I                        I
;               2 GROUND ------Ignd     pc0I------I  I--[R=10kOhm]------------I
;            (pin8 of C64  I    -----------       I   --[+C=1uF-]-------------I
;             joystickport)I                      I                           I
;                          I                       ----------- Busy     11 11 I
;                          I                                                  I
;                          I                                                 GI
;                          I                                                 NI
;                          I                --REN 17                         DI
;                          I               I                                  I
;                          I               I  GND 18           Ground   18 19 I
;                          I------------------GND  -       ----Ground    -  - I
;                          I                  GND 24      I    Ground   25 30 I
;                          I                              I                   I
;                           -------------------------------------------------- 
;
; +5V can be taken from pin 7 of C64 joystick-port
; Gnd can be taken from pin 8 of C64 joystick-port
;           
;
;
; -I>- 74LS244 ( I-I>-O)
;
;
; -<I- 7407    ( O-<I-I)
;
;
; I = input    O = output
;
;    ^^   LED 
;    II   2mA  = Error LED (not 15mA-type)
;   -<I-  type
;
;
; -I<- Diod 1N4148 (cheap universal silicon)
;
;  #1
;  o-                  usually PC2 is unconnected   
; -o o- = Jumper Debug
;  o-                  when connected to ground, then in debug mode 
;  #2                                            (debug-printing at reset
;                                                  or don't write into
;                                                  debug-buffer)
;
;                                                                     flashing)
; -o#1                 usually pb7 is unconnected (to prevent accidential 
;  o-   = Jumper Clock                                                
; -o#2                 while flashing pb7 is connected to IEC-Clock-in
;   
;
;
;
;  #1
; -o                   usually connected to IEC-Reset-in
;  o-   = Jumper Reset
; -o                   while flashing connected to ground
;  #2
;
;        IEC                            IEEE
;      __   __       _________________________________________
;     /  I I  \      \  12 11 10  9  8  7  6  5  4  3  2  1  /
;    I 5  -  1 I      \                                     /
;    I    6    I       \24 23 22 21 20 19 18 17 16 15 14 13/
;    I 4     2 I        -----------------------------------  
;     \   3   /
;      -------
;
;   1 SRQ            1 Data 1             13 Data 5
;   2 GND            2 Data 2             14 Data 6
;   3 ATN            3 Data 3             15 Data 7
;   4 CLK            4 Data 4             16 Data 8
;   5 DTA            5 End or Identify    17 Remote Enable
;   6 RST            6 Data Valid         18 Ground DAV
;                    7 Not Ready For Data 19 Ground NRFD
;                    8 No Data Accepted   20 Ground NDAC
;                    9 Interface Clear    21 Ground IFC
;                   10 Service Request    22 Ground SRQ
;                   11 Attention          23 Ground ATN
;                   12 Shield             24 Logical Ground
;
;pb7 is SCK while flashing. PB7 mustn't be connected allways to IEC-Clock-in
;because: If C64 would make IEC-Clock accidential to 0V-active when the AVR
;makes a reset, then the AVR could go into flash-mode and it could be that
;the flashROM is overwritten.
;
;74LS244 =   8 Schmitt-trigger-input-driver  not-inverting
;only necessary if one want to switch the AVR off (with switch at +5V power
;supply).
;Reason: An AVR which isn't connected with +5V power supply pulls all pins to
;0V, so the IEC bus is locked. 
;isn't necessary if one never switches off the AVR
;
;7407 =   6 open-collector-busdriver-chip   not-inverting
;only necessary when more than three additional serial devices (additional to
;C64 and AVR) are connected to the IEC-bus.
;Reason: All serial devices have got a 1kOhm pullup-resistor, so it should be
;neccessary that it needs 5mA to pull a wire of the IEC-bus to 0V-active.
;The AVR-output can make 20mA. This should be enough for 1 C64 and 3 devices.
;isn't necessary if there are only  1 - 3 serial devices connected.
;
;All diods and all things at pc2 - pc0 are only necessary if you want to use
;the AVR as printerinterface and if you want to connect a Centronics-printer.
;The printer is also important to print analyse-bytes to find software-bugs.
;
;The 8 diods at the parralel-port pa7-pa0 are only necessary if one want to
;switch off the Centronics-printer.
;Reason: A switched-off printer pulls all lines to 0V, so the parallel
;IEEE-bus is locked.
;isn't necessary if the Centronics-printer is allways switched on.
;The 5 diods at the printer-control-port (pc2-pc0) are allways necessary.
;The connection to prime of Centronics-printer can be made or not just how
;one wants. If it is made then there is allways a printer-reset when you make
;a C64-reset. 
;
;If you just want an interface of IEC- to IEEE-bus then it's possible to use
;an AVR and the cable with plugs only without any additionla chips.
;
;There is no crystal neccessary, the AVR uses the internal 8MHz oscylator.
;
;The switch S is for printing of the analyse-bytes. Switch it on; make a reset;
;switch it off, so the AVR-RAM is printed.
;
;Make a stable +5V power supply.
;
;The Reset pullup resitor isn't allways necessary; you can try without
;
; This program is free software; you can redistribute it and/or modify it
; under the terms of the GNU General Public License as published by
; the Free Software Foundation; either version 2, or (at your option)
; any later version.
;
; Use of this software in other projects is allowed and encouraged; however,
; the author would like to be notified of any such projects.
;
;   Jochen Adler   Near Letter Quantity  
;   Haeldestr.9  D74912 Kirchardt  Germany
;   NLQ@gmx.de  www.nlq.de
;
;
;
;                    without any warranty - own risk
;------------------------------------------------------------------------------------------------




;                     ATMEGA8515 runs at 7.3728MHz (good for RS232-timing)

; JD has two meanings: Jumper Debug      JiffyDos


;------------------------------------------------------------------------------------------------
        .device atmega8515
        .list
;------------------------------------------------------------------------------------------------
        ;0000-001f Registers r00-r31
.def r00=r0       ;old value Iec-bus
.def r01=r1       ;old value analyse-byte 
.def r02=r2       ;old value ieee-parallelport
.def r03=r3       ;old value ieee-controlport
.def r04=r4       ;ieee-analyse Y-vector low
.def r05=r5       ;ieee-analyse Y-vector high
.def r06=r6       ;analyse buffer mode
                  ;7 = save IeeePorts to buffer
                  ;6 = save IecPort to buffer
                  ;5 = save analyse-byte to buffer
                  ;4 = display analyse byte to IeeePort (displays to 8 LEDs)
                  ;3 = print analyse byte to centronics-printer
                  ;          
                  ;1 = jumper d (debug) determines   noprinting (0)   printing (1)
                  ;         JD                       reading analyse   of analyse buffer
                  ;                                  buffer serial      at reset
                  ;                                  when jumper d
                  ;                                  is closed
                  ;       if user has got a printer and wants to print analysebytes to it:
                  ;           => user must set bit1 of r06 to high
                  ;             JD closed: print debug-buffer to printer at reset
                  ;             JD open: no printing (and printer-line isn't locked)
                  ;      
                  ;       if user doesn't want to print the analysebuffer to a printer
                  ;           => user must set bit1 of r06 to low
                  ;             JD closed: AVR doesn't write new values into analysebuffer
                  ;                        => C64 can read analysebuffer with M-R-command
                  ;             JD open: AVR writes new debug values into analysebuffer
                  ; (analysebuffer and debugbuffer is the same)     




                  ;0 = analysebuffer starts at $0200 (0) / $0180 (1)   (-025f)
                  ;  => JiffyDos-load buffer   0100-01ff / 0100-017f
                  ;00=no
                  ;80=IeeePorts 
                  ;40=IecPort
                  ;20=analyse byte
                  ;60=AnalyseByte & IecPort 
                  ;01/03 = special for save analysebytes of JD-LOAD only
        
.def r07=r7       ;temporary memory for bus declicking (counter, flag for AtnMode, at printing)
.def r08=r8       ;temporary memory for bus declicking (port)
.def r09=r9
        ; r10      unimportant temporary counter


        ; r16      Accu of 1541
        ; r17      Xreg of 1541
        ; r18      Yreg of 1541

        ; r24      counter delay *10s  
        ; r25      don't use; for debug printing and debug-LED-------

        ; r26      Xreglow  #$00 (different values only at debug-printing) 
        ; r27      Xreghigh #$ff (different values only at debug-printing) 

        ; r28      Yreglow  for writing into debug buffer
        ; r29      Yreghigh for reading  

        ; r30      Z-register low  (only register for lpm icall ijmp)
        ; r31      Z-register high (for writing...)

;------------------------------------------------------------------------------------------------    
        ; 
        ;0020-005f I/O
;------------------------------------------------------------------------------------------------
        ;0060-025f RAM

        ;0060-007f Stack
        .equ emumod = $80   ;emulation-mode  see tadeem
                            ;Bit 7-5
                            ;%000 $00 = IEEE
                            ;%001 $20 = Centronic
                            ;%010 $40 = RTC & memory read&write
                            ;%011 $60 = RS232
                            ;%100 $80 = IEC additional device-number-translation
                            ;%101 $a0 = 64HDD at additional IEC ((fast) serial)
                            ;%110 $e0 = 64HDD at additional IEC (parallel)
                            ;%111 $f0 = cleared 
                            
                            ;bit 4-0 unused
                             

        .equ devpos = $81   ;device posibilities  see tadepo
                            
                            ;      at Ieee:7   = 0=no floppy 1=floppy
                            ;              6
                            ;              5
                            ;              4-0 = devicenumber to translate to 

                            ;at Centronics:7   = 0=no change 1=CBM-ascii->IBM-ascii at 
                            ;                        secundary address 7
                            ;              6-0   unused     
                            

        .equ flicbb = $82   ;flag iecbus bits
                            ;7 = IecAtnMode($7d) 0=DataMode 1=CommandMode
                            ;6 = IecTalk   ($7a)
                            ;5 = IecListen ($79)
                            ;4 = IecEoi    ($f8) 0=noEoi 1=Eoi (at 1541 inverted!!!) received
                            ;3 =           
                            ;0 = IecEoi at IecOut 0=noEoi 1=Eoi (ldx$82 lda$f2,x and#$08 e92f)  

        .equ icsaco = $83   ;IecSecundaryaddressComplete (all 7 bits) ($84)
        .equ icsawo = $84   ;IecSecundaryAddress without bits whether open,close,SA ($83)         
        .equ iccode = $85   ;IecCommand&Devicenumber
        .equ iccbjd = $86   ;IeC-routines
                            ;$00= CBM
                            ;$01= JiffyDOS-IECIN IECOUT
                            ;$60= JiffyDOS-LOAD
                
                
                            
        .equ fljdal = $8f   ;flag JiffyDOS allowed 
                            ;bit7  0=only CBM allowed  1=JiffyDOS alowed
                            ;bit0  at JD-LOAD: way to see that C64 is ready to receive next block 
                            ;       0=waiting-loops (like 1541) 1=analyse C64-DataOut at fb06
        .equ tadenu = $90   ;- 9f table device numbers
                            ;16 possible   5 Ieee  1 Centronic  1 RTC  1 Rs232  5 Iec-Switch
                            ;7 = 0=present 1=not present (this memory)
                            ;6 = 0=no Talker (f.e.printer) 1=Talker
                            ;5 = 0=no Listener 1=Listener
                            ;4-0 =devicenumber
        .equ tadeem = $a0   ;-af table device emulation
                            ;    in what to emulate (see emumod)   
        .equ tadepo = $b0   ;-bf table device possibilities  see devpos
                            ;    at Ieee:7   = 0=no floppy 1=floppy
                            ;            6
                            ;            5
                            ;            4-0 = devicenumber to translate to 
        .equ tacode = $c0   ;-cf table IEC command & devicenumber
                            ;%010ddddd
                            ;bit 7-5 =talk  important that one bit is set because #$00 is empty
                            ;               and bit 4-0=#$00 could be talk to seriel device 0
                            ;bit 4-0 =device-number
                            ;=> #$00=empty #$40=talk to device 0
                                    
        .equ tatasa = $d0   ;-df table talk-secundary-address
                            ;bit 7  
                            ;bit 6
                            ;bit 5  0=no byte in buffer  1=byte in buffer
                            ;bit 4  0=no EOI  1=EOI
                            ;bit3-0 =secundary address
        
        .equ tataby = $e0   ;-ef table talk-byte        

        .equ avinco = $00f0 ;AVR-internal command        
        .equ eninbu = $00f1 ;end input buffer (+1)
        .equ erbuve = $00f2 ;error buffer vector
        .equ erbuen = $00f3 ;error buffer end 

        ;0100-0129          ;input buffer for AVR-internal
        ;012a-014c          ;error-buffer for AVR-internal                      
  
        ;0100-017f/01ff     ;load-buffer at JiffyDos        
        ;0180/0200-025f     ;analyse-bytes-buffer
;------------------------------------------------------------------------------------------------
                      ;EEPROM

        ;0000-003f          ;empty ($ff)
        ;0040-00bf          ;table 0
        ;00c0-013f          ;table 1
        ;0140-01bf          ;table 2
        ;01c0-01ff          ;empty ($ff)
                            ;there are three identical tables. So the AVR can compare them
                            ;and find and repair an EEPROM-corruption

                       ;tables
        ;tbl0   tbl1   tbl2        
        ;0040 00c0 0140 0000;flag for autorepair EEPROM-corruption ($55=no $aa=yes)
        ;0041 00c1 0141 0001;calibrationbyte for internal oscylator for 7.3728MHz
        ;0042 00c2 0142 0002;analyse buffer mode -> r06
        
        ;004f 00cf 014f 000f;flag JiffyDOS allowed -> $008f-RAM
        
        ;0050 00d0 0150 0010;\
        ; -    -    -    -  ; tadenu = table device numbers ->0090-009f-RAM
        ;005f 00df 015f 001f;/ 
              
        
        ;0060 00e0 0160 0020;\
        ; -    -    -    -  ; tadeem = table device emulation ->00a0-00af-RAM
        ;006f 00ef 016f 002f;/

        ;0070 00f0 0170 0030;\
        ; -    -    -    -  ; tadepo = table device possibilities ->00b0-00bf-RAM
        ;007f 00ff 017f 003f;/ 

        ;0080 0100 0180 0040;\
        ; -    -    -    -  ; empty ($ff)
        ;00bf 013f 01bf 007f;/ 

;------------------------------------------------------------------------------------------------
; timer0 = for timing
; timer1 = for error-LED  cannot be used for timing

;------------------------------------------------------------------------------------------------
        .org $0000
;------------------------------------------------------------------------------------------------
        rjmp l12710    ;external reset
        rjmp l10000    ;external irq 0
        rjmp l10030    ;external irq 1
        rjmp l10030    ;
        rjmp l10030    ;
        rjmp l10030    ;
        rjmp l10030    ;
        rjmp l10030    ;
        rjmp l10030    ;
        rjmp l10030    ;
        rjmp l10030    ;
        rjmp l10030    ;
        rjmp l10030    ;
;------------------------------------------------------------------------------------------------
l10000:                ;                                                           external IRQ 0
                       ;Global Interrupt Enable Bit is cleared
                       ;=>impossible that second IRQ is executed while first one is executed
                       ;=>r26 r27 can have different values than #$00/#$ff
                       ;=C64 makes ATN = active
                       ;=Atn-line edge from inactive to active                     
                       
                                  
        in r27,$3f     ;reads status register
        
        ldi r26,$06    ;$07 at 8MHz
l10010: sbic $10,2     ;2 skips if IecAtn=active
        rjmp l10020    ;  =IecAtn=inactive (too short IecAtn-peek => no reaction)
        dec r26        ;1
        brne l10010    ;2   5*6=30 = 4s at 7.3728MHz    

        cbi $18,4      ;PortB = pulluprestor-off/push to 0V
        sbi $17,4      ;sets data to active as answer to C64-ATN=active by making DDRB to output  

        out $3b,r26    ;#$00 makes no more IRQ = also flag for ATN-IRQ

l10020: out $3f,r27    ;restores status register
        
        ldi r26,$00
        ldi r27,$ff

l10030: reti
;================================================================================================
l10040: ldi r16,$20    ;LED on                                                             LED on
        rjmp l10070   
        ;---------------
l10050: ldi r16,$10    ;LED blink
        rjmp l10070
        ;---------------
l10060: ldi r16,$30    ;LED off
l10070: out $2f,r16    ;Timer/Counter1ControlRegisterA 

        ldi r16,$0c    ;%00001100 Clear Timer1 on Compare match    CK/256  7.3728MHz/256=
        out $2e,r16    ;Timer/Counter1ControlRegisterB          

        ldi r16,$00
        out $2d,r16    ;Timer/Counter1 high
        out $2c,r16    ;Timer/Counter1 low    make Timer1 = $0000
        
        ldi r16,$30    ;about 80 flashes per minute  
        out $2b,r16    ;T/C1 Output Compare Register A high
        ldi r16,$00
        out $2a,r16    ;T/C1 Output Compare Register A low value resets timer to 0000

        ldi r16,$01    
        out $29,r16    ;T/C1 Output Compare Register B high
        ldi r16,$00
        out $28,r16    ;T/C1 Output Compare Register B low changes LED-pin OC1B
        
        ret
;================================================================================================
l10080: ldi r25,$b0    ;b0--
        rcall l12490
            

        rcall l10120   ;searches wanted buffer                     talk-buffer-open if necessary 
        brcs l10110    ;b.i.buffer to this DN & SA already exists
        
        ldi r25,$b1    ;b1--
        rcall l12490
            


;  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -   
l10090: ldi r25,$b3    ;b3--
        rcall l12490
            
        ldi r30,$f0    ;                                                         talk-buffer-open
        ldi r31,$00    ; z = writevector = $00f0
        ldi r28,$ef
        ldi r29,$00    ; y = readvector =$00ef
l10100: ld r16,-y      ;copies c0-c1 ce->cf d0->d1 de->df e0->e1 ee->ef
        st -z,r16      ;(writes wrong values to d0 e0
        cpi r28,$c0
        brne l10100
        lds r16,iccode ;Iec Command & devicenumber 7-5=%010=Talk  4-0=devicenumber
        sts $c0,r16    ;stores as actual value of table command & devicenumber
        lds r16,icsawo ;Iec secundaryeaddress without bits for open,close,after listen/talk
                       ;Bit 7=0 ?
                       ;bit 6
                       ;bit 5=0 =no byte in talk-buffer
                       ;bit 4=0 =no EOI
                       ;bit 3-0 =secundary address
        sts $d0,r16    ;stores as actual value of table secundary-address at talk 
                       ;in e0 stays wrong value
        
        ldi r25,$b4    ;b4--
        rcall l12490
            

l10110: ldi r25,$b5    ;b5--
        rcall l12490
        
        lds r16,$d0    ;actual talk-bits & secundary address 
        andi r16,$20   ;masks bit for byte in talk-buffer
        ret            ;equal=no byte in talk-buffer  not-equal=byte in talk-buffer
;------------------------------------------------------------------------------------------------
l10120: ldi r25,$b6    ;b6--
        rcall l12490
        
        andi r16,$1f   ;masks devicenumber bits        talk-buffer search&copy to actual position
        ori r16,$40    ;makes bits for talk (important when close talk-error-buffer at listen)
        ldi r28,$e0                                  
        ldi r29,$00    ; y =read-vector = $00e0  r16=devicenumber r17=secundayr address
l10130: ld r18,-y      ;reads table secundary-address at talk  (predecremented)
        andi r18,$0f   ;masks scundary-address
        cp r17,r18     ;compares table-value with searched value
        breq l10150    ;b.i. searched value is this table value
        
l10140: cpi r28,$d0    ;read from 00df to end 00d0?
        brne l10130    ;b.i.not end
                
        ldi r25,$b7    ;b7--
        rcall l12490
        
        clc            ;flag f.no entry for this devicenumber and this secundary-address      
        ret
        ;------

l10150: ldi r25,$b8    ;b8--
        rcall l12490
            
        clc
        sbci r28,$10   ;d0->c0 ... df->cf
        
        ld r18,y       ;table command&devicenumber
        cp r18,r16     ;searched devicenumber
        breq l10160    ;b.i.wanted

        clc 
        sbci r28,$f0   ;c0->d0
        rjmp l10140    ;b.i.not wanted 

        ;---------     ; y = readvector showes to wanted entry

l10160: ldi r25,$b9    ;b9--    =correct devicenumber and correct secundary address
        rcall l12490
        
        cpi r28,$c0
        breq l10200    ;b.i.searched entry is already at actual position
  
        ldi r25,$ba    ;ba--
        rcall l12490
 
        mov r18,r28    ;backup vector-low where wanted entry is 
        
        rcall l10180   ;copies c0-c(x) -> c1-c(x+1)

        rcall l10170   ;copies d0-d(x) -> d1-d(x+1) 

                       ;copies e0-e(x) -> e1-e(x+1)
l10170: ldi r25,$bb    ;bb--
        rcall l12490
            
        clc
        sbci r18,$f0   ;c1->d1 cf->df d1->e1 df->ef
        mov r28,r18    ;increments vector +$10

l10180: ld r16,y       ;backup wanted (->actual) value
        mov r30,r28    ; z = writevector low
        ldi r31,$00    ; z high
        inc r30        ;increments write vector 
l10190: ld r17,-y      ;copies c0->c1
        st -z,r17
        mov r17,r28    ;lowbyte read-vector
        andi r17,$0f   ;masks bit 3-0
        brne l10190    ;b.i.not 00c0 00d0 00e0

        st y,r16       ;writes actual value to 00c0 00d0 00e0 

l10200: ldi r25,$bc    ;bc--
        rcall l12490
       
        sec            ;flag for entry present (and at actual position) 
        ret
;------------------------------------------------------------------------------------------------
l10210: ldi r25,$bd    ;bd--
        rcall l12490
            
        rcall l10120   ;searches wanted buffer                     talk-buffer-close if necessary
        brcc l10240    ;b.i.wanted buffer doesn't exist
;  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -  -
l10220: ldi r25,$be    ;be--
        rcall l12490
       
        ldi r30,$c0    ;                                           talk-buffer-close actual entry 
        ldi r31,$00    ; z = writevector =$00c0                  
        ldi r28,$c1    ;                                           changes: Y-vector      
        ldi r29,$00    ; y = readvector =$00c1                              Z-vector
l10230: ld r16,y+      ;reads from c1 cf d1 df e1 ef                        r16
        st z+,r16      ;write to   c0 ce d0 de e0 ee
        cpi r28,$f0
        brne l10230    ;b.i.not at end
     
        ldi r25,$bf    ;bf--
        rcall l12490
    
        sts $cf,r26    ;#$00
        sts $df,r26
        sts $ef,r26
l10240: ret     

;================================================================================================
l10250: push r16       ;2 (+3 for rcall)                                        10s waiting loop
        ldi r16,$15    ;1 ($17at8MHz)
l10260: dec r16        ;1  
        brne l10260    ;2/1
        pop r16        ;2
        ret            ;4 3+2+1+21*(1+2)-1+2+4=74cycles=10s at 7.37MHz    
;------------------------------------------------------------------------------------------------
l10270: push r16       ;2 (+3 for rcall)                                    r24*10s waiting loop 
        ldi r16,$16    ;1 ($18at8MHz)
l10280: dec r16        ;1  3*22-1=65
        brne l10280    ;2 in loop    1 not in loop
        nop            ;1
        pop r16        ;2
        dec r24        ;1  2+1+65+1+2+1+2=74
        brne l10270    ;2 in loop    1 not in loop
        ret            ;4
;================================================================================================
l10290: ldi r25,$10    ;$10--                               e902       wait until IecAtn=inactive
        rcall l12490

l10300: ldi r18,$07    ;e902
l10310: sbis $10,2     ;2 skips if AtnIn=inactive  e8d2
        rjmp l10300    ;  =Atn=active
        dec r18        ;1
        brne l10310    ;2 7*5=35 = 4s at 7.3728MHz
        
        lds r18,flicbb ;=IecAtn=inactive
        andi r18,$7f
        sts flicbb,r18 ;clears flag f.Atn-mode 
                       ;is also made here, because it could be that there is an error at
                       ;sending a byte f.e.to Ieee => could be that then flag would never be
                       ;cleared???

        ldi r25,$11    ;$11--
        rcall l12490

        ret
;------------------------------------------------------------------------------------------------
l10320: cli            ;disbale IRQs                       read byte after ATN-edge          e85b
        
        cbi $18,4
        sbi $17,4      ;sets bit4 of DDRB = DataOut=active
                       ; (should be so from IRQ-routine)
                       ; (important when IecAtnIn changes from inactive to active while 
                       ;    IecOut or IecIn (when IRQs inhibited)) 
                       ;AtnAck-hardware isn't present
                       ;Pullup-resistors aren't necessary because
                       ;-there are resistors at the inputs-pins of the AVR (if no driver chips)
                       ;-the 7407-inputs pullup strongly enough (if driver chips)
        

        ldi r25,$02    ;02--
        rcall l12490
            
        ldi r16,$80
        sts flicbb,r16 ;sets flag for Iec-Atn clears flag for Iec-Listen,-Talk,-Eoi
        ldi r16,$7f
        out $3d,r16    ;stackpointerlow = 7f
        out $3e,r26    ;stackpointer high to 0 => stackpointer to 007f    
                
        cbi $18,6      ;clears bit6 of PortB 
        cbi $17,6      ;clears bit6 of DDRB = SrqOut=inactive (because input)
        cbi $18,2      
        cbi $17,2      ;clears bit2 of DDRB = ClockOut=inactive (because input)
        
        ldi r25,$03    ;03-- 
        rcall l12490

        sts icsaco,r26 ;clears if case that there is no secundary address
        sts icsawo,r26 ;open10,10 instead of open10,10,0
        sts iccode,r26
                       ;emumod & devpos mustn't be cleared because at unlisten/untalk it is
                       ;important to which emulated device the command goes
                        
        sts iccbjd,r26 ;#$00 clears flag f. JiffyDos Iec routines

l10330: rcall l10690   ;reads IEC-bus (Atn & Clock&Data&Srq) (If IecAtn=inactive -> l10640)
        brpl l10330    ;b.i.IecClock=active      waits until C64 makes Clock=inactive (c41:e87b)
                       ;                                                   
        ldi r25,$04    ;04--
        rcall l12490
       
                       ;JiffyDOS waits here 350s (but JD doesn't wait              (j41:e879)                 
                       ;until C64 makes Clock=active (l10330)
                         
l10340: rcall l10770   ;reads one byte from C64 (r16) DataOut=active  ClockOut=inactive    e884
                       ; (allways CBM-routines)
                         
        ldi r25,$05    ;05--
        rcall l12490
        
        mov r25,r16    ;xx--     displays received IEC-byte to the 8 LEDs
        rcall l12490
     
        cpi r16,$3f     
        brne l10380    ;b.i.not unlisten 
                       ;=UNLISTEN----------                                 
       
        rcall l10290   ;waits until IecAtn=inactive

                       ;at Unlisten, Untalk, SecundaryAddress after Listen/Talk:
                       ;   (not at Listen, Talk)
                       ;wait at once after having received the final command-byte for
                       ;Iec-Atn=inactive because:
                       ;example: 28 Listen to 8 (1541)
                       ;         6f SA to command/error-channel of 1541
                       ;         ...
                       ;         3f Unlisten
                       ;         48 Talk to 8
                       ;C64 sends Untalk => C64 makes IecAtn=inactive
                       ;C64 sends at once Talk => C64 makes IecAtn=active again
                       ;Time-period where IecAtn=inactive is very short
                       ;If AVR wouldn't wait for IecAtn=inactive here but would send the Unlisten
                       ;to an IEEE device, it wouldn't see that IecAtn was inactive (while it 
                       ;had sent to IEEE) and would wait at the end (at 1541 e902) in an endless-
                       ;loop that C64 makes IecAtn=inactive after Unlisten while C64 made
                       ;IecAtn=active at Talk =>AVR would be in endless loop            
                       ;AVR-DataOut is active => C64 waits when Talk until AVR is ready
       
        ldi r25,$3f    ;3f--
        rcall l12490
        
        sts iccode,r16 ;stores read IEC-command byte to IecCommand&Devicenumber 

        lds r17,emumod ;emulation mode
        cpi r17,$00
        brne l10350    ;b.i.not IEEE
 
        rcall l11880   ;IEEEATNOUT (r16=#$3f=unlisten)
        cbi $14,3      ;DdrC3=input
        sbi $15,3      ;PortC3 =PullUpOn = IeeeAtn=inactive
        rjmp l10370

l10350: cpi r17,$20
        brne l10360    ;b.i.not Centronic
        rjmp l10370    ;=Centronic  do nothing at unlisten?

l10360: nop            ;do nothing at AVR-internal?          
        
l10370: lds r16,flicbb ;flag IecBusBits
        andi r16,$df   ;clears bit 5 
        sts flicbb,r16  ;clears flag f.listen
        rjmp l10640    ;not l10680 as in 1541 because waiting for IecAtn=inactive was before
                       ;-------------------------------------------------------------------------
l10380: cpi r16,$5f
        brne l10410    ;b.i.not untalk
        
        rcall l10290   ;waits until C64 makes IecAtn=inactive  (see Unlisten)

        ldi r25,$5f    ;5f--
        rcall l12490

        sts iccode,r16 ;stores read IEC-command byte to IecCommand&Devicenumber

        lds r17,emumod ;emulation mode
        cpi r17,$00
        brne l10390    ;b.i.not IEEE

        rcall l11880   ;IEEEATNOUT (r16=#$3f=unlisten)
        cbi $14,3      ;DdrC3=input
        sbi $15,3      ;PortC3 =PullUpOn = IeeeAtn=inactive
        rjmp l10400

l10390: ;nop           ;do nothing at Centronics / AVR internal
 
l10400: lds r16,flicbb ;flag IecBusBits
        andi r16,$bf   ;clears bit6
        sts flicbb,r16  ;clears flag f. talk
        rjmp l10640    ;not l10680 (see Unlisten)
                       ;-------------------------------------------------------------------------
          
l10410:                ;                          Listen      Talk        SecAd Open  Close  
        mov r17,r16    ;received Iec-command-byte 20 2f 30 3e 40 4f 50 5e 60 6f e0 ef f0 ff
        andi r17,$60   ;01100000                  20 20 20 20 40 40 40 40 60 60 60 60 60 60
        
        mov r25,r17    ;displays Listen-/Talk-/SA-bits
        rcall l12490   ;xx-- 

        ldi r28,$a0    ;ylow   y=00a0 Vector to 00a0 (90-9f = table)
        ldi r29,$00    ;yhigh
        
        cpi r17,$40
        brne l10480    ;b.i.not Talk

l10420: ld r17,-y      ;009f-0090 predecremented
        andi r17,$df   ;%11011111 masks Listen-bit off
        cp r16,r17
        breq l10440    ;b.i.Talk to this device in table device numbers
        cpi r28,$90
        brne l10420
        
        cpi r16,$40    ;compares with devicenumber #$00 = avr-internal
        breq l10430    ;b.i.avr-internal
        
        rjmp l10670    ;Talk but not to AVR = all inactive&wait until C64 makes Atn=inactive

l10430: ldi r17,$40    ;#$40->emumod = AVR-internal
        ldi r18,$00    ;#$00->devicepossibilities
        rjmp l10450    ;

l10440: clc            ;Talk to AVR r29=pointer in tadenu
        sbci r28,$f0   ;adds #$10  90->a0 91->a1 9f->af
        ld r17,y       ;loads emulationmode

        clc 
        sbci r28,$f0   ;adds #$10  a0->b0  a1->b1  ...  af->bf
        
        ld r18,y       ;device-posibilities
 
l10450: sts iccode,r16 ;stores read IEC-command byte to IecCommand&Devicenumber
        sts emumod,r17
        sts devpos,r18

        cpi r17,$00
        brne l10460    ;b.i.not Talk to Ieee             

        ldi r25,$a0    ;a0--
        rcall l12490
        
        ld r16,y       ;loads b0-bf device possibilities
        andi r16,$1f   ;masks device-number-bits
        ori r16,$40    ;set Talk-bit   = device-number-translation
        rcall l11880   ;sends byte to Ieee with AtnHigh ATNOUT
       
        brcc l10470    ;b.i.ok
        rjmp l10670    ;error (device not present  time out)

    
l10460:                ;Talk to Centronic-printer (not possible)
        
        cpi r17,$40    ;AVR-internal (do what?) 
        
l10470: ldi r16,$c0    ;11000000
        sts flicbb,r16 ;sets flag f.Talk clears flag f.Listen  (Atn-flag stays active)
        
        ldi r25,$a1    ;a1--
        rcall l12490        
                
        rjmp l10620





l10480: cpi r17,$20
        breq l10490    ;b.i.Listen 20-3e %001.....
        rjmp l10570    ;not Listen 20-3e %001.....
               
l10490: ld r17,-y      ;009f-0090 predecremented
        andi r17,$bf   ;masks Talk-bit off
        cp r16,r17
        breq l10510    ;b.i.Listen to this device in table device numbers
        cpi r28,$90
        brne l10490
        
        cpi r16,$20    ;compares with devicenumber #$00 = avr-internal
        breq l10500    ;b.i.avr-internal
    
        rjmp l10670    ;Listen but not to AVR = all inactive&wait until C64 makes Atn=inactive
        
l10500: ldi r17,$40    ;#$40->emumod = AVR-internal
        ldi r18,$00    ;#$00->devicepossibilities
        rjmp l10520    ;

l10510: ldi r25,$a0    ;a0--
        rcall l12490
        
        clc            ;Listen to AVR r29=pointer in tadenu
        sbci r28,$f0   ;adds #$10  90->a0 91->a1 9f->af
        ld r17,y       ;loads emulationmode

        clc 
        sbci r28,$f0   ;adds #$10  a0->b0

        mov r25,r17
        rcall l12490
        
        ld r18,y       ;device-posibilities

l10520: sts iccode,r16 ;stores read IEC-command byte to IecCommand&Devicenumber   
        sts emumod,r17
        sts devpos,r18

        andi r18,$80   ;masks bit whether floppy
        breq l10530    ;b.i.no floppy (=chanel 15 = normal channel = no errorchannel)

        ldi r17,$0f    ;=SA for command/errorchannel (r16=devicenumber-bits but listen not talk)
        rcall l10210   ;close errorchannel to listened device if entry exists
        lds r16,iccode ;restores IEC command & devicenumber
        lds r17,emumod ;restores emulation-mode

l10530: cpi r17,$00
        brne l10540    ;b.i.not Ieee             

        ldi r25,$80
        rcall l12490
        
        lds r16,devpos ;loads b0-bf device possibilities
        andi r16,$1f   ;masks device-number-bits
        ori r16,$20    ;set Listen-bit   = device-number-translation
        rcall l11880   ;sends byte to Ieee with AtnHigh ATNOUT

        brcc l10560    ;b.i.ok
        rjmp l10670    ;error (device not present  time out)

    
l10540: cpi r17,$20
        brne l10550    ;b.i.not listen to centronics-printer
        
        ldi r25,$25    ;25--
        rcall l12490
        
        rcall l12050   ;tests if centronic-printer is present
        brcc l10560    ;b.i.printer is present 
        rjmp l10670    ;=printer not connected or off = data=inactive wait until Atn=inactiv  

l10550: cpi r17,$40    ;AVR-internal  (do what)

l10560: ldi r16,$a0    ;10100000
        sts flicbb,r16 ;sets flag f.listen clears flag f.talk  (Atn-flag stays active)
        rjmp l10620

l10570: cpi r16,$61    ;compares received commandbyte with SA=$61 = SA for SAVE  (Je89f)
        brne l10580
       
        lds r18,flicbb ;flag Iec Bus B
        cpi r18,$c0    ;compares with flag f.Talk flag f.not-Listen
        brne l10580    ;b.i.not TALK

        ldi r16,$60    ;loads SA for LOAD    =TALK+SAforSAVE=illegal=flag for JiffyDOS-LOAD
        sts iccbjd,r16 ;IeC CBM/JD  = JD-LOAD
                       ;AVR received TALK + SAforSAVE from C64
                       ;AVR sends TALK + SAforLOAD to IEEE-floppy => IEEE-floppy sends bytes 

l10580: cpi  r17,$60   ;e8b7           
        breq l10590    ;b.i.open,close,secundary-address

        rjmp l10670    ;not open,close,secundary-address   (= command isn't to AVR)
        
                       ;                                          = open,close,secundary-address

                       ;listen+open: talk-error-buffer is already closed when listen received
                       ;               at l10520-l10530
                       ;             unknown whether the here-opened-file is later for writing
                       ;               into file (listen) or for reading from file (talk)
                       ;               => don't open a new talk buffer after liste+open
                       ;                  open a new talk-buffer when 
                       ;                  (after listen+open+filename+unlisten) talk+SA is
                       ;                  received (then you know that it's talk)
                       ;                  (if it would be listen then it would be:
                       ;                    listen+open+filename+unlisten+listen+SA)
                       ;listen+close: talk-error-buffer is already closed when listen received
                       ;               at l10520-l10530 
                       ;listen+SA:  talk-error-buffer is already closed when listen received
                       ;               at l10520-l10530 
                       ;talk+SA:
                       ; -if no floppy => nothing (look if talk-buffer already exists
                       ;                           else open it) 
                       ; -if floppy => (look if talk-buffer already exists, else open it)
                       ;    -if data-channel (0-14) => close error-talk-buffer         
                       ;    -if error-chanel (15) => nothing additional 

                       ;there are two kinds of talk-buffers: - a talk-data-buffer (=talk-buffer)
                       ;                                     - a talk-error-buffer 
                         

l10590: rcall l10290   ;waits until C64 makes IecAtn=inactive (see Unlisten) 

        ldi r25,$06    ;06--    
        rcall l12490
        lds r17,emumod ;emulation mode
        cpi r17,$00
        brne l10610    ;b.i.not Ieee
 
        ldi r25,$07    ;07--
        rcall l12490

        mov r18,r16    ;=read IEC-command-byte
        rcall l11900   ;IEEEOUT r16=read Iec command byte  -----r18 mustn't change----
        ;brcc l10600    ;b.i.ok   do what if error?????????????????   

                        ;IEEE-lines aren't set for Talk here, because it's possible that there
                        ; is no SA address (f.e. open2,8,"xyz)

l10600: mov r16,r18    ;restores IEC-command byte

l10610: sts icsaco,r16 ;Iec-secundary-address-complete
        mov r17,r16
        andi r16,$0f
        sts icsawo,r16 ;SA-only without bits whether open/close/SA
        mov r16,r17    ;SA (complete)
        andi r16,$f0
        cpi  r16,$e0
        brne l10640    ;b.i.not close    not brne l10680 as at 1541 because waiting for
                       ; C64-Atn=inactive was made before  (see Unlisten)
        
        ldi r25,$08    ;08--
        rcall l12490

        ;nop           ;close
                       ;at close in 1541 continues here
                       ;after close there should be sent an Unlisten  (Listen, Close, Unlisten)
                       ;(after Open and SecAddr a.ListenTalk there are databytes sent)
                       ;between close and unlisten C64 makes Atn=inactive for short period of
                       ;  time                        
                       ;=>when 1541/AVR has closed then it's perhaps faster to receive the 
                       ;Unlisten here at once without waiting for C64 makes IecAtn=inactive
                       ;At 1541: There should be a hardwareIRQ and the flag for a
                       ;         Atn-active-change should be set
                       ;At AVR: AVR forgets to see that C64 had made IecAtn=inactive for a 
                       ;         short time-period
                       ;If there should be a problem here perhaps a rjmp l10640 could help???   

l10620: ldi r16,$0f    ;e8d2
l10630: sbis $10,2     ;skips if AtnIn=inactive  e8d2
        rjmp l10340    ;=Atn=active  -> read next command byte
        dec r16
        brne l10630 

l10640: lds r16,flicbb ;=Atn-mode is finished   AtnIn=inactive ----------------------------- e8d7
        andi r16,$7f
        sts flicbb,r16 ;clears flag f.Atn-mode
                       ;there is no AtnAck-Hardware
                       ;                                                    AVR-DataOut is active
                       
        ldi r25,$09    ;09--
        rcall l12490
         
        ldi r16,$40    ;%01000000 
        out $3b,r16    ;General IRQ mask register allows int0 irq
        sei            ;enable IRQs
                       ;=> AVR-AtnAck-emulation on
                       ;if C64 makes C64-Atn=active then the AVR makes an IRQ and sets 
                       ;AVR-DataOut=active (but AVR-DataOut is already active)
                       ;=> C64 waits 
                           
        lds r16,flicbb ;flag f.listen e8e3
        andi r16,$20
        breq l10650    ;b.i.no listen
        
        ldi r25,$0a    ;0a--
        rcall l12490
        
        lds r16,iccode ;IEC command&devicenumber                                          =listen
        lds r17,icsawo ;IEC secundary address without bits for open/close/SA 
        rcall l10210   ;close this (listened to) talk-buffer (data-channel (0-14)
                       ;                                       or error-channel (15)) 

        rcall l11580   ;jsr $ea2e reads bytes from C64 and sends to Ieee/printer/AVRinternal
                       ;IecIn disables IRQ= switches AtnAck-emulation off 
        rjmp l13220

l10650: lds r16,flicbb
        andi r16,$40
        breq l10660    ;b.i.not talk
        
        ldi r25,$a8    ;a8--
        rcall l12490
        
        cbi $17,4      ;DataOut=inactive perhaps waitingloop here???                        =talk
        sbi $17,2      ;ClockOut=active


                       ;AVR-DataOut is now inactive!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
                       ;=>if C64 makes now ATN=active then the AVR-IRQ-routine (l10000) must
                       ;make AVR-DataOut fast enough to active to show to the C64 that the AVR
                       ;isn't ready
                       ;if there will be a routine where the IRQ cannot be disabled 
                       ;(f.e. later secundary IEC-bus-routines with any fastloader)
                       ;then the AVR must perhaps make AVR-DataOut to active while the IRQ is
                       ;disabled and make it to inactive when the IRQ can be enabled ??
                                
                       ;perhaps waiting here at least 40s because 1541 is so slow    
                       ; (only if 360s JD loop would be deleted)  

        ldi r24,$28    ;=40
        rcall l10270   ;400s waiting loop ;perhaps 360s delay at first byte? (fb0f)  
                       ;JiffyDos makes 360s delay-loop at fb0f if JD-DataOut or JD-Load
                       ; (not at CBM-DataOut)  (don't know why)
                       ;AVR makes 400s delay loop allways (at JD-DataOut, JD-Load, CBM-DataOut)
                       ;if the delaylopp would be deleted at CBM-DataOut then there should be
                       ; at least a 50s delayloop that allows the C64 to read the lines even if
                       ; there should be a C64-badline)
                          
        rcall l11690   ;e8f7 job when Talk received       jsr e909  IRQ is enabled

l10660:                ;cbi $17,2       ;e8fa ea4e      
                       ;cbi $17,4
                       ;C64 can send f.e. a new Talk-command while AVR has send old Untalk to 
                       ;Ieee. AVR must let IecDataOut to active to prevent that C64 thinks that
                       ;AVR would be in receive-routine and C64 would begin to send the Talk
                       ; while AVR isn't yet in receive-routine but in main-waiting-loop
        rjmp l13220    ;to main-waiting-loop
        
l10670: cbi $17,2      ;ClockOut=inactive drive isn't listened/talked to e8fd
        cbi $17,4      ;DataOut=inactive

l10680:                ;e902

        rcall l10290   ;waits until Atn=inactive

        rjmp l10640    ;=Atn is inactive

;------------------------------------------------------------------------------------------------
;l-99011: mov r08,r16  ;copies actual value -> old value            test of Atn-mode-change  ea59
                       ;    (error at first time)
;        ldi r16,$05
;        mov r07,r16   ;  counter register
;        
;l-99021: in r16,$10   ;1 PortD = IecAtnIn
;        andi r16,$04  ;1 masks Bit2 = IecAtnIn
;        cpse r08,r16  ;2 compares old and actual value of IecAtnIn
;        rjmp l-99011  ;  b.i.IecAtnIn is not constant
;        ;----------
;        dec r07       ;1  7*5=35  =  4s at 8Mhz 
;        brne l-99021  ;2  (1541 makes 1541:lda$1800 cmp$1800 = 4s bus constant)

                       ;=IecAtn-line is constant for 4s   <-------mode1------------------------



l10690: clr r08        ;clears r08                                  test of Atn-mode-change  ea59

        ldi r16,$03    ;                 routine changed => perhaps check timing???????????????? 
        mov r07,r16    ;counter for 3 times 

l10700: in r16,$10     ;1 PortD = IecAtnIn 
        andi r16,$04   ;1 masks Bit2 = IecAtnIn
        add r08,r16    ;1
        
        ldi r16,$03    ;1
l10710: dec r16        ;1      3*3-1 +1 = 9 +1+1+1 + 1 + 1+2 = 16 = 2s
        brne l10710    ;2/1   

        mov r16,r08    ;1

        dec r07        ;1     reads IecBus 3 times  4s and takes average <----mode2-----------
        brne l10700    ;2                       3210=bits of PortD 
                       ;      0000  0000  0000  0100
                       ;      0000  0000  0100  0100
                       ;      0000  0100  0100  0100
                       ;      ----  ----  ----  ----
                       ;      0000  0100  1000  1100

        
        lds r07,flicbb ;flag f. Atn-mode                           
        rol r07        ; AtnMode bit -> carry
        
        andi r16,$08   ;masks IecAtnIn

        brcc l10720    ;b.i.not in Atn-mode
                       ;               =Atn-mode
        breq l10730    ;b.i.in Atn-mode and AtnIn=active  = mode stays Atn-mode

        push r25
        
        ldi r25,$40    ;40--
        rcall l12490

        pop r25
        rcall l12490   ;xx--  (analysebyte from routine above to debugbuffer)

        mov r25,r20    ;conter for IecIn bits perbyte
        rcall l12490

        mov r25,r17    ;so far read IecIn byte
        rcall l12490
        
        ldi r16,$7f    ;mode changes from Atn- to data-mode
        out $3d,r16    ;stackpointerlow = 7f
        rjmp l10640    ;to routine at end of Atn !!stack is at C64 wrong!!
        ;---
l10720:                ;               =not in Atn-mode=in Data-mode

        brne l10730    ;b.i.in Data-mode and AtnIn=inactive  = mode stays in data-mode
        
                       ; (DataOut=active is important but made at follow routine)

        ;ldi r25,$20   ;20-- 
        ;rcall l12490  ;temporary !!!must be fast enough to make data fast enough to active
        
        rjmp l10320    ;reads byte after Atn-edge  = change from data- to Atn-mode 
;------------------------------------------------------------------------------------------------
;l-99031: mov r08,r16  ;copies actual value -> old value                 reads IEC-bus-port  e9c0
;                      ;    (error at first time)
;        ldi r16,$05   ;                                                 
;        mov r07,r16   ;counter 
;        
;l-99041: in r16,$16   ;1 PortB = IecPort
;        andi r16,$2a  ;1 %00101010 masks Bit 5,3,1 = DataIn ClockIn SrqIn
;        cpse r08,r16  ;2 compares old and actual value
;        rjmp l-99031  ;  b.i.value is not constant
;        ;----------
;        dec r07       ;1  7*5=35  =  4s at 8Mhz 
;        brne l-99041  ;2  (1541 makes 1541:lda$1800 cmp$1800 = 4s bus constant)



l10730: clr r08        ;clears r08 

        ldi r16,$03    ;                 routine changed => perhaps check timing????????????????
        mov r07,r16    ;counter for 3 times 

l10740: in r16,$16     ;1 PortB = IecPort 
        andi r16,$2a   ;1 %00101010 masks Bit 5,3,1 = DataIn ClockIn SrqIn
        add r08,r16    ;1
        
        ldi r16,$03    ;1
l10750: dec r16        ;1      3*3-1 +1 = 9 +1+1+1 + 1 + 1+2 = 16 = 2s
        brne l10750    ;2/1   

        mov r16,r08    ;1

        dec r07        ;1     reads IecBus 3 times  4s and takes average
        brne l10740    ;2                    210=bits of PortB 
                       ;      000  000  000  010
                       ;      000  000  010  010
                       ;      000  010  010  010
                       ;      ---  ---  ---  ---
                       ;      000  010  100  110



                       ;=IecPortIn read 3 times in 4s
                       ;DataIn ClockIn SrqIn
                       ;  6      4      2
        rol r16        ;  7      5      3
        rol r16        ;  c      6      4
        rol r07
        rol r16        ;         7      5
        ror r07         ;  c      7      5
        andi r16,$a0   ;%10100000 masks bit 7 and 5  (carry stays)
                   
                       ;CarryLow = DataInActive  CarryHigh = DataInInactive
                       ;Plus = ClockInActive     Minus =ClockInInactive
                       ; (SrqIn=bit 5 of r16)
        ret           
;------------------------------------------------------------------------------------------------
l10760: cli            ;disable IRQs                         reads one byte from C64  IecIn  e9c9
                       ;disadvantage: AVR-AtnAck-emulation is switched off
                       ;          ( !!!changes Z-vector!!!  if differnt timing for uni NTSC PAL)
                       ; (so far different timing isn't implemented)  
                       ;  (JD-1541 also hasn't differnt timing)
        lds r16,iccbjd ;Iec CBM / JiffyDos                      DataOut=active ClockOut=inactive
        cpi r16,$00
        breq l10770    ;=CBM-serial bus routines   (00)
        
        rjmp l10920    ;b.i.JD-serial bus routines (01-ff 1-255)
              
l10770: cli            ;disables IRQs    from l10340 => CLI=important                   CBM-IECIN

        ldi r20,$08    ;counter f. 8 bits per byte                                     
        
        ldi r25,$25    ;25--- 
        rcall l12500

l10780: rcall l10690   ;tests for AtnMode change & reads bus
        brpl l10780    ;b.i.C64 makes Clock=active / waits until C64 makes Clock=inactive
                
        ldi r25,$26    ;26---
        rcall l12500
        
        cbi $17,4      ;DataOut=inactive
l10790: rcall l10730   ;reads bus
        brcc l10790    ;b.i.C64 makes DataIn=active / waits until C64 makes DataIn=inactive
                       ;IRQ is disabled  (CLI)        
                       ;=> AtnAck-emulation is switched off
                       ;=> even if C64 makes Atn=active then the AVR shouldn't make
                       ; AVR-DataOut=active 
                       ;=>the Data-line couldn't be made to active by the AVR
                       ;=> the AVR cannot lock itself  => not dangerous?
                        
        ldi r25,$27    ;27--- 
        rcall l12500 
        
        ldi r19,$03    ;%.....011
        out $33,r19    ;starts timer0 (8bit) with 8MHz/64 = 1count per 8s for EOI-recognition
        out $32,r26    ;#$00 to timer0 counts up 32*8s=256s

l10800: rcall l10690
        brpl l10840    ;b.i.C64 makes Clock=active within 256s
        in r19,$32     ;reads timer
        cpi r19,$20
        brcs l10800    ;b.i.counter<$20 = if not yet 256s without C64 makes Clock=active
 
                       ;= 256s without C64 makes Clock=active
l10810: sbi $17,4      ;DataOut=active    =EOI received                                 EOI-begin
        
        ldi r25,$28    ;28--- 
        rcall l12500

l10820: in r19,$32
        cpi r19,$30
        brcs l10820    ;waits 128s (1541 waits 50s)
                        
        ldi r25,$29    ;29---
        rcall l12500
                
        cbi $17,4      ;DataOut=inactive
l10830: rcall l10690   ;tests for Atn-mode-change & reads IEC-port
        brmi l10830    ;b.i.C64 makes Clock=inactive / waits until C64 makes Clock=active
        lds r19,flicbb
        ori r19,$10
        sts flicbb,r19 ;sets flag for EOI                                                 EOI-end
        
l10840: ldi r19,$a0    ;160                                            =for CBM/JD-recognition   
        out $32,r19    ;from $a0 to $bb timer0 counts up $1b=27*8s=216s

l10850: rcall l10730   ;reads bus   (carry=DataIn)            
                      
        ldi r25,$2a    ;2a---
        mov r01,r25
                       ;                (jd:e9f5)           
        brmi l10900    ;b.i.C64 makes Clock=inactive / waits until C64 makes Clock=inactive
        
        lds r19,fljdal ;flag JiffyDos allowed   CBM- (00) / JiffyDos- (80) IecBusRoutines
        andi r19,$80
        breq l10850    ;b.i.only CBM allowed  / JD-serial routines not alowed 
        
        in r19,$32     ;=JD-IecBusRoutines allowed
        cpi r19,$bb
        brcs l10850    ;b.i.timer0 not counted 216s (later 1500s)
        
                       ;r17=so far read IecInByte      =C64 doesn't make Clock=inactive
                       ;           (f674)                 within 216s = JiffyDos-C64
                       ;                                  after transmission of bit 6
                       ;                                  before transmission of bit 7
        lsr r17        ;shifts so far read IecInByte into correct possition (bit7=low)
                           
        ldi r28,$a0    ;ylow   y=00a0 Vector to 00a0 (90-9f = table)
        ldi r29,$00    ;yhigh

        
l10860: ld r19,-y      ;009f-0090 predecremented
        cpi r28,$8f    ;Ylow
        breq l10890    ;b.i.end of table reached    =not Listen or Talk to this AVR

        andi r19,$df   ;%11011111 masks Listen-bit off
        cp r17,r19
        breq l10870    ;b.i.Talk to this device in table device numbers
        
        ld r19,y       ;009f-0090 (y stays unchanged)
        andi r19,$bf   ;%10111111 masks Talk-bit off
        cp r17,r19
        brne l10860    ;b.i.not Listen to this device
        
                       ;devicenumber #$00 (=AVR itself) isn't checked => speed from C64 to
                       ;AVR-itself is allways CBM, never JD. Important for calibration byte
                       ;when AVR isn't exactly running with 7.3728MHz
         
l10870: ldi r19,$01    ;=Listen or Talk to AVR  
        sts iccbjd,r19 ;sets flag f.JiffyDos            
        
        sbi $17,4      ;DataOut=active
        
l10880: ldi r24,$29    ;41
        rcall l10270   ;waits 410s
         
        cbi $17,4      ;DataOut=inactive
        
l10890: lsl r17        ;shifts so far read IecInByte into old correct value
        out $32,r26    ;#$00 starts timer0 so that it counts 160*8=1400s
        rjmp l10850
        ;-----------
                
l10900: ldi r25,$2b    ;2b---
        mov r01,r25
                       ;carry mustn't change from l10850 to here     
        ror  r17       ;shifts data-bit into r17 (not inverted at AVR)

l10910: rcall l10690   ;tests for Atn-mode-change & reads IEC-bus
        brmi l10910    ;b.i.C64 makes Clock=inactive / waits until C64 makes Clock=active                
        
                
        ldi r25,$2c    ;2c---
        mov r01,r25
        
        
        dec r20        ;decrement counter for 8 bits per byte
        brne l10840
        sbi $17,4      ;DataOut=active
        mov r16,r17
        
                
        ldi r25,$2d    ;2d---
        rcall l12500
                
        
        ret            ;r16=r17=read byte            dataOut=active  ClockOut=inactive
                       ;                             =>flag for C64 to wait
                       ;                             => unimportant that AtnAck-emulation
                       ;                                  is switched off           end CBM-IecIn

                       ;. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .    

l10920: ;andi r30,$18  ;masks bits for table for timing values                           JD-IecIn
        ;ldi r31,$ff   ;sets Z-vector  (iccbjd would contain vector to
                       ; correct timing-table in flashRom => read it with LPM-command
                       ; (so far not implemented)  

                       ;input lines aren't declicked
                       ;JD-1541 aren't declicked, too
                       ;if there should be errors then perhaps declick like at CBM-IecIn   

        sbis $10,2     ;s.i.IecAtn=inactive
l10930: rjmp l10320    ;reads byte after Atn-edge  = change from data- to Atn-mode 
            
        in r16,$16     ;reads IEC-bus                              (fbd3)

        cbi $17,4      ;DataOut=inactive                           (fbd8)

        ldi r17,$02    ;%.....010
        ldi r19,$10     

        andi r16,$08   ;masks IecClockIn                                                 before)
        brne l10950    ;b.i.C64 makes Clock=inactive (=C64error) (!AVR made AVR-DataOut=inactive
                       ;     => if C64 wants to send the next command-byte then C64 could think
                       ;         that AVR-DataOut=inactive is flag that AVR is ready 
                       ;         => C64 could begin to send next byte  = bad           

l10940: sbis $10,2     ;s.i.C64-Atn=inactive
        rjmp l10320    ;reads byte after Atn-edge  
                       ;= change from data- to Atn-mode                           uni-   
        sbis $16,3     ;s.i.C64 makes Clock=inactive                        1541 versal NTSC PAL
        rjmp l10940    ;waits until C64 makes Clock=inactive       (fdbe)
                       ;when EOI: C64 sends last byte with EOI (ed19)        0s    0s
                       ;C64-ClockOut stays active
                       ;=>1541 even after having read last EOI-byte,
                       ;it reads the next one
                       ;=>it waits at l10940
                       ;C64 makes Atn=active (when sending unlisten (after EOI))
                       ;but at 1541 the AtnAck-hardware makes
                       ;41-DataOut=active 
                       ;so 41-DataOut=active even if the direct 
                       ;DataOut-register is made
                       ;         inactive (fbd8) => 41-DataOut=active = falg for C64 to wait
                       ;the AVR hasn't got an AtnAck-hardware = problem 
                       ;JD-C64 makes 64Clock=inactive (ed49)
                       ;=>JD-1541 ends waiting-loop at l10940, but doesn't make 
                       ; AVR-DataOut=active, because there is no AtnAck-hardware and because
                       ; AtnAck-emulation is switched off and 
                       ;    if there would be no Atn-test four times while receiving one byte:                     
                       ;    AVRreads one not-existing byte from C64
                       ;    and sees at the end of this that
                       ;          C64 makes Atn=active
                       ;    and jump to the CBM routine
                       ;          (where routine after ATN-edge is made)
                       ;    Here AvrDataOut is made active (very late)
                       ;    could be perhaps too late to show C64 that AVR isn't ready
                       ;     (and C64 could perhaps begin to send command byte)
                       ;=> make test for C64-Atn=active four times



l10950: out $33,r17    ;starts timer0 (8bit) with 8MHz/8 = 1count per 1s
                       ;               7.3728MHz/8 = 1count per 1.08507s
        out $32,r19    ;$10 to timer0 counts up from $10                          (0.41-1.1s)       
        
        ldi r16,$00

l10960: in r17,$32     ;reads timer0
        cpi r17,$1f    ;$20 at 8MHz
        brne l10960    ;waits $10=16s from C64 makes Clock=inactive
                       ;  until reading first bits

        in r17,$16     ;reads IecPort Bit5=data=bit5 of port                0d-14 $10s  
                       ;   bit4=clock=bit3 of port
        
        lsl r17        ;bit5=data=bit6  bit4=clock=bit4
        lsl r17        ;bit5=data=bit7  bit4=clock=bit5
        brmi l10970    ;b.i.DataIn=inactive
        ori r16,$20
l10970: andi r17,$20        
        brne l10980    ;b.i.ClockIn=inactive
        ori r16,$10
        
l10980: sbis $10,2     ;s.i.C64-AtnIn=inactive
        rjmp l10320     

l10990: in r17,$32     ;reads timer0
        cpi r17,$2b    ;$2d at 8MHz
        brne l10990    ;waits $0d=13s from reading first bits
                       ;  until reading second bits

        in r17,$16     ;reads IecPort Bit7=data=bit5 of port                1a-21 $1ds 
                       ;   bit6=clock=bit3 of port
 
        lsl r17        ;bit5=data=bit6  bit4=clock=bit4
        lsl r17        ;bit5=data=bit7  bit4=clock=bit5
        brmi l11000    ;b.i.DataIn=inactive
        ori r16,$80
l11000: andi r17,$20        
        brne l11010    ;b.i.ClockIn=inactive
        ori r16,$40
  
l11010: sbis $10,2     ;s.i.C64-AtnIn=inactive
        rjmp l10320     

l11020: in r17,$32     ;reads timer0
        cpi r17,$35    ;$38 at 8MHz
        brne l11020    ;waits $0b=11s from reading second bits
                       ;    until reading third bits

        in r17,$16     ;reads IecPort Bit1=data=bit5 of port                25-2c $28s       
                       ;   bit3=clock=bit3 of port
        lsl r17        ;bit1=data=bit6  bit3=clock=bit4
        lsl r17        ;bit1=data=bit7  bit3=clock=bit5
        
        brmi l11030    ;b.i.DataIn=inacive
        ori r16,$02    ;sets bit1 of to received byte

l11030: andi r17,$20   ;masks bit5 = clock bit = bit 3 of to receive byte
        brne l11040    ;b.i.0-bit
        ori r16,$08    ;sets bit3 of to receive byte

l11040: sbis $10,2     ;s.i.C64-AtnIn=inactive
        rjmp l10320     

l11050: in r17,$32     ;reads timer0
        cpi r17,$41    ;$45 at 8MHz
        brne l11050    ;waits $0d=13s from reading third bits
                       ;  until reading fourth bits

        in r17,$16     ;reads IecPort Bit0=data=bit5 of port                32-39 $35s         
                       ;   bit2=clock=bit3 of port
        lsl r17        ;bit0=data=bit6  bit2=clock=bit4
        lsl r17        ;bit0=data=bit7  bit2=clock=bit5

        brmi l11060    ;b.i.DataIn=inactive
        ori r16,$01    ;sets bit0 of to received byte

l11060: andi r17,$20   ;masks bit5 = clock bit = bit2 of to receive byte
        brne l11070    ;b.i.0-bit
        ori r16,$04    ;sets bit2 of to receive byte

l11070: sbis $10,2     ;s.i.C64-AtnIn=inactive
        rjmp l10320     

l11080: in r17,$32     ;reads timer0
        cpi r17,$4d    ;$52 at 8MHz
        brne l11080    ;waits $0d=13s from reading fourth bits
                       ;  until reading EOI-bit

        in r17,$16     ;reads IecPort c64-EOI=clock=bit3 of port            3f-46 $42s   
        
        sbi $17,4      ;DataOut=active                           (fc05)
        
        sbis $10,2     ;s.i.C64-Atn=inactive                     (fc08)   
        rjmp l10320    ;reads byte after Atn-edge  = change from data- to Atn-mode
    
        andi r17,$08   ;masks bit3 =clock = EOI-bit
        breq l11090    ;b.i.noEOI
        
        lds r19,flicbb
        ori r19,$10
        sts flicbb,r19 ;sets flag for EOI
        
l11090: mov r17,r16    ;=received data-byte  (never command-byte) 
        
        ldi r25,$2f    ;2f---
        rcall l12500
        mov r25,r16    ;-----
        rcall l12500
                
        ret            ;AVR-DataOut=active        (AVR-ClockOut=inactive)
                       ;=> =flag for C64 to wait                                     end JD-IecIn
                       ;=>unimportant that AVR-AtnAck-emulation is switched off (cli) 
;================================================================================================
l11100: cli            ;IecOut IEC from AVR to C64  DataOut=inactive ClockOut=active  IecOut e916
                       ;disable IRQs                    r16             from l11830
                       ; => AtnAck-emulation is switched off (and AVR-DataOut=inactive)
                       ;   => dangerous if C64 makes C64-Atn=active

        sbis $10,2     ;s.i.C64-Atn=inactive
        rjmp l10320    ;read byte after Atn=active-edge  !doesn't close Talk-buffer!
                       ;never sends command-bytes => Atn is allways inactive

        cbi $17,4      ;DataOut=inactive (should be so even before)    

        lds r17,iccbjd ;Iec CBM JiffyDos
        cpi r17,$00
        brne l11220    ;b.i.JD
        
        ;------------                                                             

l11110:                ;ClockOut=active  DataOut=inactive                              CBM-IecOut

        ldi r25,$50    ;50--
        rcall l12490

        mov r25,r16    ;--to-send-byte--
        rcall l12490

        mov r18,r16    ;r18=r16=to sent IecOutByte  

        rcall l10690   ;test for AtnMode Change & reads IecBus
        cbi  $17,2     ;DdrB2 ClockOut=input  =inactive                      (C64:ee1e)
        brcs l11130    ;b.i.C64 makes Data=inactive (=C64 not present?)

        ldi r25,$51    ;51--
        mov r01,r25    ;faster than rcall l12490

l11120: rcall l10690
        brcc l11120    ;waits until C64 makes Data=inactive                  (C64:ee2a)

        lds r16,flicbb ;IecBusBits
        andi r16,$01   ;masks bit 0
        breq l11170    ;b.i.noEoi
                       ;                                               --------------begin of EOI 
        ;rjmp l11150   ;1541 doesn't make this / 1541 waits second time for c64 makes data=inact
                       ; this is faster                         (l11140)???  (C64:ee2a)??
l11130: ldi r25,$52    ;52--
        rcall l12490

l11140: ;rcall l10690  ;=Eoi   e937
        ;brcc l11140   ;waits until C64 makes Data=inactive                  (C64:ee2a)

l11150: ldi r25,$53    ;53--   C64 makes from ee47 to ee2a C64-DataOut to active for 84 cycles
                       ;rcall l12490 would be too long 
        mov r01,r25     ;if it hangs here then you can analyse it by r01=#$25 

                       ;before line: handshake; no waiting-loop necessary
                       ;------------------------------------------------------------------------ 
                       ;after line: timing important => waiting-loops 

l11160: rcall l10690
        brcs l11160    ;waits until C64 makes Data=active   (C64:ee47) 

        ldi r25,$54    ;54--
        rcall l12490
                       ;                                               ----------------end of EOI
        
l11170: sbi $17,2      ;e94b DdrB2 ClockOut=active  sign to C64 that transmission starts  (ee37)
        rcall l10690    
        brcc l11170    ;waits until C64 makes Data=inactive  (C64:ee2a  -first time if noEOI
                       ;                                                -second time if EOI)                                         
        ldi r25,$55    ;55--
        rcall l12490

        ldi r24,$0a
        rcall l10270   ;100s waiting loop


        ldi r17,$08    ;counter f.8 bits per byte
        ldi r24,$0e    ;=14 = 140s waiting-loop
        

l11180: rcall l10270   ;140/100s waiting-loop 
        rcall l10730   ;reads IEC-port
        brcc l11210    ;b.i.C64 makes Data=active (=error)
                                    
        lsr r18        ;to sent IecOutByte  DataOut = allways inactive here
        brcs l11190    ;b.i.1-bit  (DataOut stays inactive)
        sbi $17,4      ;DdrB4 DataOut=active =0-bit
l11190: rcall l10250   ;wait 10s
        cbi $17,2      ;DdrB2 ClockOut=inactive
        ldi r24,$07
        rcall l10270   ;wait 10s*7 70s
        sbi $17,2      ;DdrB2 ClockOut=active
        rcall l10250   ;wait 10s
        cbi $17,4      ;DdrB4 DataOut=inactive
        rcall l10250   ;waits 10s
        ldi r24,$0a    ;value for 100s waiting-loop
        dec r17        ;counter bits per byte    
        brne l11180

        ldi r25,$56    ;56--
        rcall l12490

l11200: rcall l10690   ;test if AtnModeChange & reads bus
        brcs l11200    ;b.i.DataIn=inactive   waits until C64 makes Data=active
        
        ldi r25,$57    ;57--
        rcall l12490
        
        clc            ;flag f.ok
        
        sei            ;allow IRQs important because DataOut=inactive 
                       ;if C64 sends command-byte then the serial drive must make DataOut=active
                       ;=> AtnAck-substitute-IRQ must be allowed
                       ; AtnAck-emulation is switched on                        

        ret            ;ClockOut=active  DataOut=inactive 
       ;-----------------  
l11210: ldi r25,$5e    ;5e--
        rcall l12490
        
        rjmp l13220    ;(C64 makes Data=active) to main waiting loop               end CBM-IecOut             

                       ;. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .    

l11220:                ;400s delay loop is made at L10670                             =JD-IECOUT
                        
                       ;input-lines aren't declicked
                       ;JD-1541 input-lines aren't declicked, too
                       ;perhaps declick as at CBM-IecOut if there should be errors
                      
                    
        cbi $17,2      ;ClockOut=inactive                  (ff88)
      
        ldi r17,$02    ;%.....010
        ldi r19,$10    ;startvalue counter

l11230: sbis $10,2     ;2 s.i.C64-Atn=inactive
        rjmp l10320    ;  reads byte after Atn-edge                               uni-
                       ;    = change from data- to Atn-mode                 1541 versal NTSC PAL
l11240: sbis $16,5     ;1/2  s.i.C64 makes Data=inactive
        rjmp l11230    ;2 waits until C64 makes Data=inactive     (ffbb)     0s    0s
                       ;    1 loop = 5cycles =0.68s at 7.37MHz  
  
        out $33,r17    ;1 starts timer0 (8bit) with 8MHz/8 = 1count per 1s
l11250: out $32,r19    ;1 $10 to timer0 counts up from $10                  (0s) 0.41-1.1s 
         
                       ;when C64 makes Data=inactive then the AVR needs
                       ;from l11240 to l11250 3cycles =0.41s

                       ;when the C64 makes Data=inactive 0.001s after
                       ;the AVR has read the line at l11240 then the AVR
                       ;must wait one complete loop l11230 - l11240 
                       ;=>delay is 0.41+0.68s=1.1s

               
                       ;1541 sends inverted to sent byte

        ldi r19,$18    ;$19 at 8MHz
        rcall l11290   ;sends bit 0&1                                       06-0d $09s
        
        ldi r19,$22    ;$23 at 8MHz    
        rcall l11290   ;sends bit 2&3                                       10-17 $13s 
        
        ldi r19,$2c    ;$2e at 8MHz    
        rcall l11290   ;sends bit 4&5                                       1b-22 $1es 

        ldi r19,$35    ;$38 at 8MHz    
        rcall l11290   ;sends bit 6&7                                       25-2c $28s 

        ldi r19,$3f    ;$43 at8MHz
        lds r16,flicbb ;IecBusBits
        andi r16,$01   ;masks bit 0
        breq l11260    ;b.i.noEoi     DataOut=inactive    ClockOut=active

        ldi r16,$01    ;$01=Eoi       DataOut=active  ClockOut=inactive 
                       ;                  EOI

        rcall l11290   ;sends                                          EOI: 30-37 $33s     
        ldi r19,$5d    ;$64 at 8MHz     
                       ;hold this for about 21=33s
                       ;jd41 at EOI: sets data=active Clock=inactive
                       ;doesn't wait at ffde-ffe3
                       ;rts to fb70
                       ;doesn't branch at fb72
                       ;makes data=inactive clock=active at fb74-fb78
                       ;=>holds EOI-flag for 33s to bus
                       ;if bus isn't constant within 4s then the
                       ;cmp-loop is perhaps made and it's
                       ;42s instaed of 33s
                       ;waits at ffde-ffe3 until C64 makes data=active
                       ;(C64 at receiving IECIN-byte with EOI and Untalk:
                       ;  makes data=active for 109s
                       ;  => enough time for 41 to read it)

l11260: ldi r16,$02    ;$02=noEoi                                     (EOI: 51-58 $54s)                             
                       ;                                             noEOI: 30-37 $33s 
                       ;      noEOI:  DataOut=inactive    ClockOut=active 
        rcall l11290   ;sends noEOI (or end after EOI):

        rcall l10250   ;waits 10s  (jd41 reads bus 4s after having made dataOut=inactive)
        
l11270: sbis $10,2     ;s.i.C64-Atn=inactive
        rjmp l10320    ;reads byte after Atn-edge  = change from data- to Atn-mode
        sbic $16,5     ;s.i.C64 makes Data=active
        rjmp l11270    ;waits until C64 makes Data=inactive       (ffbb)
l11280: ret            ;DataOut=inactive  ClockOut=active                           end JD-IecOut
;------------------------------------------------------------------------------------------------
l11290: in r17,$17     ;reads ddrB
        andi r17,$eb   ;%11101011  masks off bit4&2  DataOut&ClockOut
        lsr r16        ;to send IecOut-byte  bit0,2,4,6->carry
        brcs l11300    ;b.i.1-bit to send = inverted 0-bit
        ori r17,$04    ;sets clockOut bit of port
l11300: sbis $10,2     ;s.i.C64-Atn=inactive
        rjmp l10320    ;read byte after Atn=active-edge  !doesn't close Talk-buffer!
                       ;never sends command-bytes => Atn is allways inactive
        lsr r16        ;bit1,3,5,7->carry
        brcs l11310     
        ori r17,$10    ;sets DataOut bit of port

l11310: in r18,$32     ;reads timer0
        cp r18,r19
        brcs l11310    ;waits
         
        out $17,r17    ;makes bit0,2,4,6->ClockOut  bit1,3,5,7->DataOut

        ret
;------------------------------------------------------------------------------------------------
l11320:                ;r16 = actual byte                                          =JiffyDOS-LOAD
                       ;r17 = ddrB  
                       ;r18 = timer0                        AVR-DataOut=Inactive
                       ;r19 = timevalues                    AVR-ClockOut=Active            DI CA
                       ;r20 = end of load buffer            IRQ is enabled   
                       ;                                    AtnAck-emulation is switched on
                       ;r28 = Y-vector low                      =good
                       ;r29 = Y-vector high
                         
                       ;400s delay-loop is made at l10650

        lds r16,fljdal ;flag JiffyDOS allowed
        andi r16,$01   ;masks bit for way to see when C64 is ready for next block
        brne l11340    ;b.i.C64-DataOut=inactive at fb06-way 

l11330: sbis $10,2     ;s.i.C64-Atn=inactive    = waiting-loop-way
        rjmp l13220    ; main waiting looop  (!talk buffer isn't closed)       
                   
        sbis $16,5     ;s.i.C64 makes Data=Inactive (ff30)
        rjmp l11330    ;waits until C64 makes Data=Inactive (fb06)  
        
l11340: sts erbuen,r26 ;#00 clears error buffer end because it is overwritten with LOADbuffer

        ldi r25,$c0    ;c0--
        rcall l12490

        lds r16,iccode ;IEC command&devicenumber (don't close error channel)     
        lds r17,icsawo ;IEC secundary address without bits for open/close/SA
        rcall l10080   ;open talk-buffer if necessary and test if talk-byte is in buffer
                       ;equal=no byte in buffer notequal=byte in buffer (!changes Y-vector!)
        breq l11400    ;b.i.byte isn't in talk-buffer (= error)

        ldi r25,$c1    ;c1--
        rcall l12490

        lds r16,$e0    ;byte of talk-buffer
        sts $0100,r16  ;stores to $0100 

        lds r17,$d0    ;talk-SA&bits-buffer

        rcall l10220   ;close actual buffer (changes Y, Z, r16   !mustn't change r17)

        ldi r29,$01    ;Y-vector high

        ldi r28,$01    ;Y-vector low =$0101 = LOAD-buffer

        ldi r30,$80
        ldi r31,$02    ;Z-vector =$0280 (=write load-analyse-bytes into not-existing RAM)

        mov r16,r06    ;analyse buffer mode
        cpi r16,$01    ;=no analyse-write into buffer but big errorbuffer = unlogical = illegal
                       ;   =flag for save load analyse bytes

        brne l11350    ;b.i.normal analyse-bytes
        
        ldi r31,$01    ;Z-vector = $0180 =vector for load-analyse-bytes (not for load-databytes)
          
        in r16,$16     ;IEC-bus
        st z+,r16       

l11350: andi r17,$10   ;masks EOI-bit 
        breq l11370    ;b.i.noEOI
      
        ldi r25,$c2    ;c2--
        rcall l12490 
        st z+,r25

        lds r16,flicbb ;flags IeCBusBits
        ori r16,$01    ;sets flag f.EOI      
        sts flicbb,r16
        ldi r20,$00    ;set buffer end = $0100

        rjmp l11440    ;send buffer------------

l11360: ldi r28,$00    ;load write buffer = $0100  

l11370: ldi r25,$c3    ;c3--
        rcall l12490
        st z+,r25

l11380: lds r16,emumod  
        cpi r16,$00
        brne l11400    ;b.i.not IEEE

                       ;if only 1 byte is loaded from IEEE-floppy then AVR must wait
                       ;until C64 made STOP-key-routine... (use AVR-timer?)
l11390: rcall l11980   ;IeeeIn
        brcc l11410    ;b.i.ok
l11400: rjmp l13220    ;error -> close talkbuffer -> to main-waiting-loop

l11410: st y,r16       ;don't use st y+,r16 because highbyte Y-vector would be $0200

        st z+,r16
        
        lds r16,flicbb ;flags IeCBusBits
        andi r16,$01   ;masks bit for EOI
        brne l11430    ;b.i.EOI
        inc r28        ;lowbyte Y-vector
        
        mov r16,r06    ;analyse buffer mode
        andi r16,$01
        breq l11420    ;b.i.bit0=0 = small error buffer = big load buffer 0100-01ff r16=#$00
        ldi r16,$80    ;= big error buffer =small load buffer 0100-017f 
l11420: cp r28,r16
        brne l11380

        ldi r25,$c4    ;c4--
        rcall l12490
        st z+,r25

                       ;=buffer ($0100-$017f/$01ff) is full => send it to C64 
        dec r28        ;00->ff  80->7f  =position of last byte in buffer       

l11430: mov r20,r28    ;r20 = end of buffer

        ldi r25,$c5    ;c5--
        rcall l12490

        st z+,r25
        st z+,r20

l11440: ldi r28,$ff    ;read vector = $01ff                                                DI CA

        in r16,$16
        st z+,r16

l11450: ldi r24,$14    ;=20  =200s
        lds r16,fljdal ;flag JiffyDOS allowed
        andi r16,$01
        breq l11470    ;b.i.waiting-loop-way    

l11460: sbis $10,2     ;s.i.C64-Atn=inactive    = waiting-loop-way
        rjmp l13220    ;  main waiting looop       
                       
        sbis $16,5     ;s.i.C64 makes Data=Inactive
        rjmp l11460    ;waits until C64 makes Data=Inactive (fb06)  
        ldi r24,$06    ;60s waitingloop because C64 needs
                       ;from making C64-DataOut=inactive (fb06)
                       ;to reading bus (fb0c)
                       ;8 + 43 (badline) = 51s   


                       ;waits until C64 has finished stop-key-routine
                       ;and C64 is ready to receive next block


                       ; 60s  
l11470: rcall l10270   ;200s waiting loop because C64 must have enought time for STOP-key
                       ;routine (important if AVR receives only one byte from IEEE-floppy
                       ;and this would be shorter than 200s)

                       ;D=I C=A => C64 is in loop at fb0c?

        in r16,$16
        st z+,r16

        sbi $17,4      ;DataOut=Active                     (ff98)                          DA CA
        rcall l10250   ;waits 10s
        cbi $17,2      ;ClockOut=inactive                  (ff9d)                          DA CI
                       ;=> C64 leaves loop at fb0e and
                       ;branches to fb3e

        ldi r24,$08
        rcall l10270   ;80s waiting loop             (ffa0-ffb5)

        in r16,$16
        st z+,r16

l11480: inc r28        ;(at beginning: $01ff->$0100)
        ld r16,y       ;= to sent byte from load-buffer $0100-$017f/$01ff

        st z+,r28
        st z+,r16

l11490: cbi $17,4      ;  DataOut=inactive                        
        cbi $17,2      ;1 ClockOut=inactive  (important at first byte in loop)   (ffb5)    DI CI

        ldi r17,$08    ;1
l11500: dec r17        ;1
        brne l11500    ;3/2  
                       ;30cycles=4s at 7.37MHz = enought time that data-line goes inactive 
                         


        ldi r17,$02    ;1 %.....010
        ldi r19,$10    ;1 startvalue counter

        in r24,$16
        st z+,r24

l11510: sbis $10,2     ;2 s.i.C64-Atn=inactive
        rjmp l13220    ;  main waiting loop                                      uni-
                       ;                                                    1541 versal NTSC PAL
l11520: sbic $16,5     ;1/2  s.i.C64 makes Data=active
        rjmp l11510    ;2 waits until C64 makes Data=active       (ffbb)     0s    0s
                       ;    1 loop = 5cycles =0.68s at 7.37MHz  
  
        out $33,r17    ;1 starts timer0 (8bit) with 8MHz/8 = 1count per 1s
l11530: out $32,r19    ;1 $10 to timer0 counts up from $10                  (0s) 0.41-1.1s 
         
                       ;when C64 makes Data=inactive then the AVR needs
                       ;from l11520 to l11530 3cycles =0.41s

                       ;when the C64 makes Data=inactive 0.001s after
                       ;the AVR has read the line at l11520 then the AVR
                       ;must wait one complete loop l11510 - l11520 
                       ;=>delay is 0.41+0.68s=1.1s


        ldi r25,$c6
        st z+,r25
        in r25,$16
        st z+,r25
               


                       ;1541 sends inverted to sent byte

        ldi r19,$18    ;$19 at 8MHz
        rcall l11290   ;sends bit 0&1                             (ffbd)    06-0d $09s    D1 C0
        
        ldi r19,$22    ;$23 at 8MHz    
        rcall l11290   ;sends bit 2&3                             (ffc4)    10-17 $13s    D3 C2
        
        ldi r19,$2c    ;$2e at 8MHz    
        rcall l11290   ;sends bit 4&5                             (ffcc)    1b-22 $1es    D5 C4

        ldi r19,$35    ;$38 at 8MHz    
        rcall l11290   ;sends bit 6&7                             (ffd3)    25-2c $28s    D7 C6

        rcall l10250   ;waits 10s (1541 holds bit 7&6 at IECOUT 10s long
                       ;=> this must be enough also at JD-LOAD) 
          
        cp r20,r28     ;compares end of buffer with actual value
        brne l11480    ;b.i.not at end of buffer

        ldi r25,$c8    ;(c8--)
        mov r01,r25
        st z+,r25

        sbi $17,2      ;ClockOut=Active       (about 11s later than bit    30-37 $33s 
        cbi $17,4      ;DataOut=Inactive   (ffdb)    7&6 set to bus)                    
        rcall l10250   ;waits 10s                                                         DI CA
         
        ldi r25,$c9    ;(c9--)
        mov r01,r25        
        st z+,r25
        in r25,$16
        st z+,r25 
               

l11540: sbis $10,2     ;s.i.C64-Atn=inactive
        rjmp l13220    ; main waiting looop       
                        
        sbic $16,5     ;s.i.C64 makes Data=active
        rjmp l11540    ;waits until C64 makes Data=active (fb51)  

        ldi r25,$ca    ;(ca--)
        mov r01,r25        
        st z+,r25 
        in r25,$16
        st z+,r25


        lds r16,flicbb ;flags IecBusBits
        andi r16,$01   
        brne l11560    ;b.i.EOI

        ldi r25,$cb    ;cb--                                                               DI CA
        rcall l12490
        st z+,r25
        in r25,$16
        st z+,r25

        cpi r31,$04    ;highbyte Z-vector   
        brcs l11550
        
        ldi r31,$04 

l11550: rjmp l11360    ;noEOI = receive next block from IEEE-floppy

l11560: ldi r25,$cc    ;cc--
        rcall l12490
        st z+,r25
        in r16,$16
        st z+,r16

        ldi r24,$0a    ;=10                  AVR-DataOut=Inactive  AVR-ClockOut=Active
        rcall l10270   ;100s waiting loop                            (ff65)

        cbi $17,2      ;ClockOut=inactive                             (ff65)               DI CI

        ldi r24,$0a    ;=10
        rcall l10270   ;100s waiting loop                            (ff68)

        sbi $17,2      ;ClockOut=Active                               (ff6b)               DI CA

        ldi r24,$0a    ;=10
        rcall l10270   ;100s waiting loop                       (ff6e-ff71)

        cbi $17,2      ;ClockOut=inactive                             (ff73)               DI CI

        in r16,$16
        st z+,r16
        ldi r25,$cd
        st z+,r25

l11570: rjmp l13220    ;to main-waiting-loop                                          end JD-LOAD

;================================================================================================

l11580:                ;from l10640 - l10650 
                       ;action after Listen  read byte from C64                              ea2e        
                       ;   C64 made IecAtn=inactive
                       ; DataOut=active  ClockOut=inactive 
                       ;IRQ is enabled 
                       ;IRQs must be enabled because software AtnAck
 
        ldi r25,$a8    ;a8--
        rcall l12490
  
        cbi $14,3      ;DdrC3=input
        sbi $15,3      ;PortC3=PullUpOn = IeeeAtn=inactive
                       ;make IeeeAtn=inactive here (not after receiving Secaddr/Open/Close)
                       ;because it could be that there is no SecAddr (f.e. open10,10) 
 
        ldi r28,$00
        ldi r29,$01    ;Y-vector to 0100 = input buffer (important for AVRinternal)
  
l11590: rcall l10760   ;read 1 byte from C64  DataOut=active ClockOut=inactive               ea44
                       ;no return if C64 makes IecAtn=active 
        sei            ;enable IRQs  => AtnAck-emulation is switched on
                       ; (but AVR-DataOut is active anyway)  

        lds r17,emumod ;emulation mode

        mov r25,r16    ;---- 
        rcall l12490
        
        cpi r17,$00
        brne l11600    ;b.i.not IEEE

        ldi r25,$1f    ;1f--
        rcall l12490

        rcall l11900   ;IEEEOUT (at once   not bufferd  because C64 buffers)
                       ;uses same EOI from C64 
        brcc l11590    ;b.i.ok
        rjmp l13220    ;main waiting loop (make IEEE inactive???)

        
l11600: cpi r17,$20
        brne l11660    ;b.i.not Centronics
                
        lds r17,devpos ;device possibilities
        andi r17,$80
        breq l11650    ;b.i.CBM->IBM-codechange off
         
        lds r17,icsawo ;Iec secundary address withot bit for open/close/SA
        cpi r17,$07
        brne l11650    ;b.i.not secundary address 7

        cpi r16,$41
        brcs l11650    ;b.i.$00-$40  
        
        cpi r16,$5b  
        brcc l11610
        ori r16,$20    ;41-5a -> 61-7a
        rjmp l11650
        
l11610: cpi r16,$61
        brcs l11650    ;b.i.5b-60
        
        cpi r16,$7b     
        brcs l11630    ;b.i.61-7a

        cpi r16,80
        brcs l11650    ;b.i.7b-7f
        
        cpi r16,$c0
        brcs l11640    ;b.i.80-bf
        brne l11620  
        ldi r16,$60    ;c0 -> 60
        rjmp l11650

l11620: cpi r16,$db
        brcc l11640    ;b.i.db-ff
l11630: andi r16,$5f   ;c1-da -> 41-5a %110xxxxx -> %010xxxxx
        rjmp l11650    ;(61-7a-> 41-5a %011xxxxx -> %010xxxxx) 
        
l11640: ldi r16,$20    ;space

l11650: rcall l12100   ;sends byte (r16) to printer
        brcc l11590    ;b.i.carry=close = printer=present 
                       ;at end: AVR wants to read byte from C64. C64 makes Atn=active
                       ;=>AVR sees in read-byte routine that Atn changes 
                       ;goes to begin of read byte after Atn-edge               
        rjmp l13220    ;=printer not present -> mainwaitingloop = AllOut=inactive

l11660: cpi r17,$40
        brne l11680    ;b.i.not AVR-internal 
        
        cpi r28,$2a    ;                                                                     cfdf
        breq l11670
        
        sts eninbu,r28 ;stores lowbyte end input buffer
        st y+,r16      ;stores read byte to input buffer
        
l11670: lds r16,flicbb
        andi r16,$10   ;masks IecEoiReceived bit
        breq l11590    ;b.i.no EOI        
        sts avinco,r16 ;#$10  set flag f. AVR internal command present                            cfed  
        rjmp l11590
        
l11680: rjmp l13220    ;temporary  
;------------------------------------------------------------------------------------------------
l11690:                ;action after Talk from C64                                           e909
                       ;IRQ=enebaled  => AtnAck-emulation is switched on 
                       ;DataOut=inactive  ClockOut=active
                       ;                                                 C64 made IecAtn=inactive 
 
        lds r16,emumod  
        cpi r16,$00
        brne l11700    ;b.i.not IEEE

        ldi r25,$1f    ;1f--
        rcall l12490

        cbi $15,5      ;PortC5=PullUpOff
        sbi $14,5      ;DdrC5=Output = NRFD=active
        cbi $15,4      ;PortC4=PullUpOff
        sbi $14,4      ;DdrC4=Output = NDAC=active

        rcall l10250   ;10s waitingloop (necessary?)
         
l11700: cbi $14,3      ;DdrC3=input
        sbi $15,3      ;PortC3=PullUpOn = IeeeAtn=inactive
                       ;make IeeeAtn=inactive here (not after receiving Secaddr/Open/Close)
                       ;because it could be that there is no SecAddr (f.e. open10,10) 
 
l11710: lds r16,devpos ;device posibilities
        andi r16,$80   ;masks bit whether floppy
        breq l11720    ;b.i.no floppy (= channel 15 is normal data-channel)
        lds r17,icsawo ;IEC secundary address without bits for open/close/SA
        cpi r17,$0f    ;compares with command/errorchannel
        breq l11720    ;b.i.errorchannel
        lds r16,iccode ;IEC command&devicenumber  =talk to data-channel=>close talk-error-buffer
        ldi r17,$0f    ;error-channel
        rcall l10210   ;close talk-(error-)buffer if necessary

l11720: lds r16,iccbjd ;iccbjd Iec CBM/JD
        cpi r16,$60 
        brne l11730    ;b.i.not JiffyDOS-LOAD
        rjmp l11320    ;=JiffyDOS-LOAD

l11730: lds r16,iccode ;IEC command&devicenumber (don't close error channel)
        lds r17,icsawo ;IEC secundary address without bits for open/close/SA
        rcall l10080   ;open talk-buffer if necessary and test if talk-byte is in buffer
                       ;equal=no byte in buffer   notequal=byte in buffer
        breq l11750    ;b.i.byte isn't in talk-buffer (=> read new one from device)

        lds r16,$d0    ;talk-SA&bits-buffer
        andi r16,$10   ;masks EOI-bit 
        breq l11740    ;b.i.noEOI
        lds r16,flicbb ;flags IeCBusBits
        ori r16,$01    ;sets flag f.EOI      
        sts flicbb,r16

l11740: lds r16,$e0    ;byte of talk-buffer
        rjmp l11830    ;byte is in talk-buffer (=> send it   don't read new one from device)
        ;---------- 



l11750: lds r16,emumod  
        cpi r16,$00
        brne l11770    ;b.i.not IEEE
        
        ldi r25,$a9    ;a9--
        rcall l12490
        
l11760: rcall l11980   ;IeeeIn
        brcc l11800    ;b.i.ok
        rjmp l13220    ;error -> to main-waiting-loop

l11770: cpi r16,$40
        brne l11790    ;b.i.not AVR-internal
        
        lds r17,erbuen ;error buffer end    00 00 02 02 02 02      (#$00 if empty or overwritten)
        lds r16,erbuve ;errorbuffer vector  00 02 00 01 02 03
        cp r16,r17     ;                     c  c  s  s  c  c
        brcc l11780    ;b.i.all errorbytes sent = error-buffer empty
        
        ldi r17,$2a    ;isn't longer than clc sbci
        mov r30,r16
        add r30,r17    ;Z-vector = 012a-     =errorbuffer
        ldi r31,$01

        inc r16
        sts erbuve,r16

        ld r16,z       ;reads byte from errorbuffer

        rjmp l11800    ;------   
        
l11780: ldi r16,$0d    ;end-carriage return 
        lds r17,flicbb ;flag iecbus bits
        ori r17,$01    ;(sets bit f. IecEoi)
        sts flicbb,r17 ;sets bit f.IecEoi
        rjmp l11800    ;-------------------------

l11790:                ;next device  
        rjmp l13220    ;temporary
        
                
l11800: sts $e0,r16    ;stores read-byte=to-sent-IEC-OUT-byte in talk-buffer
        lds r17,$d0    ;talk-secundary-address-buffer
 
l11810: lds r18,flicbb ;flags IeCBusBits
        andi r18,$01   ;masks EOI-bit at IEC-send (from AVR to C64) (not bit4)
        breq l11820    ;b.i.noEOI
        ori r17,$10    ;sets EOI-bit in r17

l11820: ori r17,$20    ;sets bit for byte-in-talk-buffer in r17
        sts $d0,r17
        
l11830: rcall l11100   ;IecOut (from AVR to C64)
                       ; IRQ is enabled => AtnAck-emulation is switched on
                       ; = important because AVR-DataOut=inactive 
                         
                       ;if in future there should be a device where the IRQ must be disabled
                       ;because of timing, then it's perhaps necessary that AVR makes
                       ; AVR-DataOut= active while IRQ is disabled (and AtnAck-emulation 
                       ;  is switched off) 
                         
        lds r16,$d0    ;talk-secundary-address-buffer
        andi r16,$df   ;masks byte-in-buffer-bit off (bit5)
        sts $d0,r16

        brcs l11850    ;b.i.error

l11840: lds r16,$d0    ;talk-secundary address-buffer
        andi r16,$10   ;masks EOI-flag
        brne l11850    ;b.i.EOI 
        rjmp l11750    ;no EOI 

l11850: rcall l10220   ;close actual talk-buffer
;================================================================================================                
l11860: mov r08,r17    ;1 copies actual value -> old value                     reads IEEEbus-port
                       ;    (error at first time)                               (about 5s)
        ldi r17,$05    ;1                                                 
        mov r07,r17    ;1 counter 
        
l11870: in r17,$13     ;1 PortC = IeeeControlPort
        andi r17,$f0   ;1 %11110000 masks Bit 7,6,5,4 = IeeeEoi Dav Nrfd Ndac
        cpse r08,r17   ;2 compares old and actual value   =35cycles
        rjmp l11860    ;  b.i.value is not constant
        ;----------
        dec r07        ;1  7*5=35  =  4s at 8Mhz 
        brne l11870    ;2  (1541 makes 1541:lda$1800 cmp$1800 = 4s bus constant)
        ret            ;4 
;================================================================================================
l11880:                ;                                                               IeeeAtnOut

        rcall l12590   ;=====  (=write IeeePorts to analyse-bufer) 

        cbi $14,5      ;DdrC5 Nrfd=input                                               IeeeAtnOut
        sbi $15,5      ;PortC5 Nrfd=PullupOn  =Nrfd=inactive
        cbi $14,4      ;DdrC4 Ndac=input
        sbi $15,4      ;PortC4 Ndac=PullupOn  =Ndac=inactive

        rcall l12590   ;===== 

        ldi r25,$83    ;83-- 
        rcall l12490 

        rcall l12590   ;===== 

l11890: rcall l11860   ;reads IeeeControlPort
        andi r17,$40   ;masks Dav bit
        breq l11890    ;b.i.Dav=active   waits until Floppy makes Dav=inactive

        rcall l12590   ;===== 
        
        ldi r25,$84    ;84--
        rcall l12490
         
        cbi $15,3      ;PortC3 IeeeAtn=PullUpOff (->0V)
        sbi $14,3      ;DdrC3 IeeeAtn=output=0V   IeeeAtn=active

        rcall l12590   ;===== 
;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 
l11900: cbi  $14,6     ;DdrC6 = input                               r16= send Ieee-byte   IEEEOUT
        sbi  $15,6     ;PortC6 =pullUpOn =IeeeDav=inactiv                          
 
        rcall l12590   ;===== 

        cbi $14,7      ;DdrC7=input  IeeeEoi=input
        sbi $15,7      ;PortC7=PullupOn IeeeEoi=inactive
 
        rcall l12590   ;===== 

        
        ldi r25,$90    ;90--
        rcall l12490
        
        rcall l11860   ;reads IeeeControlPort
        andi r17,$30   ;00110000 masks Bit5&4 =Ndac Nrfd
        cpi  r17,$30
        sec            ;flag f. error
        breq l11950    ;b.i.Ndac and Nrfd = inactive = device not present

        rcall l12590   ;===== 

        mov  r25,r16
        rcall l12530   ;xx-- sent-byte to analysebuffer

        out  $1b,r26   ;#$00 (PullupOff)      
        out  $1a,r16   ;DdrA  0-bit=Input  1-bit=output
        com  r16
        out  $1b,r16   ;PortA  makes byte inverted to parallelport 
                       ;      0-bit=PullUpOn 1-bit=stays 0V
                       ;      0-bit=inactive (->5V)  1-bit=active (=0V) =inverted
  
        rcall l12590   ;===== 

        lds r16,flicbb ;flag f. EOI (0=no 1=yes (inverted at 1541))  
        andi r16,$10
        breq l11910    ;b.i.no EOI
        
        cbi  $15,7     ;PortC7=PullUpOff (->0V)
        sbi  $14,7     ;DdrC7=output   IeeeEoi=active
   
        rcall l12590   ;===== 

        ldi r25,$96    ;96--  (EOI)
        rcall l12530


l11910: rcall l10250   ;waits 10s

        rcall l12590   ;===== 

l11920: rcall l11860   ;reads IeeeControlPort
        andi r17,$20   ;masks Nrfd bit
        breq l11920    ;b.i=Nrfd=activ  waits until Ieee-floppy makes Nrfd=inactiv

        rcall l12590   ;===== 

        
        cbi  $15,6     ;PortC6 Dav=PullUpOff(->0V)
        sbi  $14,6     ;DdrC6  Dav=output=0V=active

        rcall l12590   ;===== 


l11930: ldi r16,$07     
l11940: rcall l11860   ;40 reads IeeeControlPort
        clc            ; 1 flag f. ok 
        andi r17,$10   ; 1 masks Ndac bit
        brne l11960    ; 1 b.i.Ndac=inactiv    waits until floppy makes Ndac = inactive       
        
        dec  r10       ; 1 wait 65120s  (64erSH10 waits 8000s CBM-Ieee 65000s)
        brne l11940    ; 2  40+1+1+1+1+2=46 46*256=10000
        dec  r16       ;    10000*7==70000cycles=70000s
        brne l11940
l11950:                ;= Ieee-Floppy doesn't make NDAC fast enough to inactive
        rcall l12590   ;===== 

        cbi  $14,3     ;DdrC3 IeeeAtn=input                             =error
        sbi  $15,3     ;PortC3 IeeeAtn=PullupOn = IeeeAtn=inactive
   
        rcall l12590   ;===== 

        ldi r25,$91    ;91--
        rcall l12490


        sec            ;error flag = time out error make all controll-lines=inactiev???

l11960: 

        rcall l12590   ;===== 

        cbi $14,6      ;DdrC6
        sbi $15,6      ;PortC6 Dav=inactive (=output&PullUpOn)

        rcall l12590   ;===== 

        cbi $14,7      ;DdrC7
        sbi $15,7      ;PortC7 IeeeEoi=inactive

        rcall l12590   ;===== 

        out $1a,r26    ;#$00 DDrA = input
        out $1b,r27    ;#$ff PortA = PullUpOn

        rcall l12590   ;===== 

        ldi r25,$94    ;94-- (=ok)
  
        brcc l11970

        ldi r25,$95    ;95-- (=error)

l11970: rcall l12490

        rcall l12590   ;===== 

        ret            ;clc=ok sec=error 
        
;================================================================================================
                       ;IEEE-routines are made similar to 
                       ;www.funet.fi\cbm\firmware\computer\pet\d\mon1.htm  f0b6-f1cb 
;================================================================================================
                       ;from l11760
l11980: cbi $15,4      ;PortC4=PullUpOff                                                   IeeeIn
        sbi $14,4      ;DdrC4=Output = NDAC=active              at beginning: NRFD=active
        cbi $14,5      ;DdrC5=Input                                           NDAC=active
        sbi $15,5      ;PortC5=PullUpOn = NRFD=inactive                       DAV=inactive
        out $1a,r26    ;DdrA=#$00=input                                       IeeeAtn=inactive
        out $1b,r27    ;PortA=#$ff PullUpOn
        
        ldi r25,$60    ;60--
        rcall l12530
                
        ldi r16,$07     

l11990: rcall l11860   ;40 reads IeeeControlPort
        andi r17,$40   ;1 masks Dav bit 
        breq l12010    ;1 b.i.one floppy makes DAV=active 

l12000:                ;  =all floppies make Dav=inactive = AVR must wait 
        dec r10        ;1   65000s = 500000cycles at 8MHz
        brne l11990    ;2    45*256=10000
        dec r16        ;     7*10000=70000 = 70ms
        brne l11990    

        ldi r25,$61    ;61--
        rcall l12530
        
        cbi $15,5      ;PortC5=PullupOff      =time-out-error
        sbi $14,5      ;DdrC5=Output = NRFD=active   (NDAC=active already)
        ldi r16,$0d    ;carriage return  (don't know why Nrfd & Ndac are active if error)
        sec            ;Flag f. error  
        ret

l12010: cbi $15,5      ;PortC5=PullupOff
        sbi $14,5      ;DdrC5=Output = NRFD=active
    
        ldi r25,$62    ;62--
        rcall l12530

        rcall l11860   ;reads IeeeControlPort
        andi r17,$80   ;masks IeeeEoi bit
        brne l12020    ;b.i. IeeeEoi=inactive
            
        lds r16,flicbb ;flag iecbus bits
        ori r16,$01    ;(sets bit f. IecEoi)
        sts flicbb,r16 ;sets bit f.IecEoi   =IeeeEoi

        ldi r25,$63    ;63--
        rcall l12530

l12020: mov r08,r16    ;1 copies actual value -> old value  reads IEEEbus-port
                       ;    (error at first time)         
        ldi r16,$06    ;1                                                 
        mov r07,r16    ;1 counter 
        
l12030: in r16,$19     ;1 PortA = IeeeParallelPort
        cpse r08,r16   ;2 compares old and actual value
        rjmp l12020    ;  b.i.value is not constant
        ;----------
        dec r07        ;1  6*6=36  =  4s at 8Mhz 
        brne l12030    ;2  (1541 makes 1541:lda$1800 cmp$1800 = 4s bus constant)

        com r16        ;inverts
        cbi $14,4      ;DdrC4=input
        sbi $15,4      ;PortC4=PullUpOn = NDAC=inactive
    
        mov r25,r16    ;--read-byte--
        rcall l12490
        
        ldi r25,$64    ;64--
        rcall l12530

l12040: rcall l11860   ;reads IeeeControlPort
        andi r17,$40   ;masks Dav bit
        breq  l12040   ;b.i.one floppy makes DAV=active 
                       ;waits until all floppies make DAV=inactive
                        
                       ;=all floppies make DAV=inactive
        ldi r25,$65    ;65--
        rcall l12530

        cbi $15,4      ;PortC4=PullUpOff
        sbi $14,4      ;DdrC4=Output = NDAC=active
        clc            ;flag f.ok
        ret
;================================================================================================
l12050: push r16       ;tests if centronic-printer is present
l12060: ldi r16,$10    ;                      (!also at debug printing => r26/r27 not #$00/#$ff)
        sbic $13,1     ;skips if centronic-printer not connected or off
        rjmp l12080    ;=printer is connected and on

l12070: sbic $13,1     ;s.i.centronic-printer is not connected or off
        rjmp l12060
        dec r16
        brne l12070     
        sec            ;=printer not connected or off  
        rjmp l12090

l12080: sbis $13,1     ;s.i.centronic-printer is connected and on
        rjmp l12060
        dec r16
        brne l12080
        clc            ;=printer is connected and present
l12090: pop r16
        ret            ;clc=ok sec=error

;------------------------------------------------------------------------------------------------
l12100: rcall l12050   ;tests if printer is present               send 1byte to centronic printer
        brcs l12160    ;printer not present   (!also at debug printing => r26/r27 not #$00/#$ff)

l12110: sbic $13,0     ;skips if Busy is 0V = ready for data
        rjmp l12100    ;jumps if Busy=5V = busy = not ready for data     
        sbic $13,0
        rjmp l12100
        sbic $13,0
        rjmp l12100

        push r16
        ldi r16,$00
        out $1a,r16    ;DDRA all=input  to prevent that port pulls with 20mA to +5V
        pop r16
        out $1b,r16    ;PortA 0-Bits=no-pullup  1-bits=pullup
        com r16
        out $1a,r16    ;DDRA  0-bits=output  1-bits=input (pullup)

        ldi r16,$1a    ;26 
l12120: dec r16        ;1
        brne l12120    ;2 wait 10s =8*10cycles at 8MHz 

        cbi  $15,2     ;PortC Bit5 of PortC=pullup-off (->0V when output) 
        sbi  $14,2     ;DdrC Bit5 of PortC=output  =  Strobe=0V=active

        ldi r16,$1a    ;26 
l12130: dec r16        ;1
        brne l12130    ;2 wait 10s =8*10cycles at 8MHz 

        cbi  $14,2     ;DdrC Bit5 of PortC=input  
        sbi  $15,2     ;PortC Bit5=pullup-on  =  strobe=inactive

        ldi r16,$1a    ;26 
l12140: dec r16        ;1
        brne l12140    ;2 wait 10s =8*10cycles at 8MHz 

l12150: clc            ;flag f. ok
        sbis $13,0     ;skips if Busy is 5V = busy = not ready for data
        rjmp l12170    ;jumps if Busy=0V = ready for data     
        rcall l12050   ;tests if printer is present
        brcc l12150    ;b.i.printer is present

l12160: sec            ;flag f. error 

l12170: ldi r16,$00    ;clc/sec
        out $1a,r16    ;DDRA=paralleport=input
        ldi r16,$ff
        out $1b,r16    ;PortA=parallelport=pullup-resistors-on
        ret            ;clc=ok  sec=error
;------------------------------------------------------------------------------------------------
l12180: mov r07,r16    ;print space + ascii (!also at debug printing => r26/r27 not #$00/#$ff)
        ldi r16,$20
        rcall l12100    
        mov r16,r07
;       ----------------
l12190: mov r07,r16    ;change hexdec->ascii (!also at debug printing => r26/r27 not #$00/#$ff)
        lsr r16
        lsr r16
        lsr r16
        lsr r16        ;00-09 0a-0f
        rcall l12200
        rcall l12100   ;print highnibble in ascii
        mov r16,r07
        andi r16,$0f   ;00-09 0a-0f
l12200: ori r16,$30    ;30-39 3a-3f
        cpi r16,$3a
        brcs l12210    ;b.i.0-9
        sbci r16,$f9   ;      41-46
l12210: rjmp l12100    ;print lownibble
;================================================================================================
l12220: andi r19,$01   ;clears bit 7-1 (4000-41ff(7fff)->0000-01ff(01ff))            EEPROM-write
        out $1e,r18    ;lowbyte address to eeprom address register low         r16=to write byte
        out $1f,r19    ;highbyte address                                         r18,r19=address
                       ;                                                             changes r17     
        out $1d,r16    ;eedr  write data (r16) to data register
        
        sbi $1c,2      ;eemwe of eecr Write logical one to EEMWE
        sbi $1c,1      ;start eeprom write by setting EEWE of eecr
                       ;if internal oscylator runs with too fast speed it must be set to 
                       ;correct speed before and to fast speed after ?????
                         
l12230: sbic $1c,1     ;eecr eeprom control register
        rjmp l12230    ;wait for completion of write
        mov r17,r16
;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - 
l12240: andi r19,$01   ;clears bit 7-1 (4000-41ff(7fff)->0000-01ff(01ff))             EEPROM-read
        out $1e,r18    ;lowbyte address to eeprom address register low           r18,r19=address
        out $1f,r19    ;highbyte address 

        sbi $1c,0      ;start eeprom read by writing EERE
        in r16,$1d     ;eedr = eeprom data register   read data from data register
        

l12250: out $1e,r26    ;clears eepromaddress 
        out $1f,r26
        out $1c,r26    ;clears eecr???
        cp r16,r17     ;only at write: compares written and read value
        
        ret
;================================================================================================
l12260:                ;analyse & execute new AVR-internal command                           c146 
                       ;print OK message to errorbuffer                                      c150 
        lds r16,$0100  ;c m m ee u u   first byte of inputbuffer
                       ;a - - ii i j
        lds r17,$0102  ;l r w +-
        lds r18,$0103  ;
        lds r19,$0104  ;     

        cpi r16,$43    ;'c'
        brne l12350

l12270: cpi r17,$4c    ;'l'  =cal calibrate
        breq l12280
        rjmp l12470    ;syntax error

l12280: cpi r18,$00    ;00 and ff isn't possible (00=use old value ff=empty or corrupted EEPROM)
        breq l12290    ;b.i. 'cal chr$(0)' = don't change value

        out $04,r18    ;calibrationbyte for internal 8MHz-oscilator   r18=hexdec

l12290: ldi r25,$f0    ;f0--
        rcall l12490
         
        ldi r19,$05    ;%.....101
        out $33,r19    ;starts timer0 (8bit) with 8MHz/1024 = 1count per 128s (if wouldbe 8MHz)
        ldi r19,$ff    ;                                    = 1count per 138.888s at 7.3728MHz      
        out $32,r19    ;$ff to timer0

l12300: in r19,$32     ;reads timer
        cpi r19,$01
        brne l12300    ;b.i.counter<>$01 = waits until counter=01  waits 35555.55s=35.555ms
                       ;                                                     for 1 halfcycle
l12310: in r19,$32     ;reads timer
        cpi r19,$00
        brne l12310    ;b.i.counter<>$00 = waits until counter0000
        
                       ;DataOut should be active?
                       ;program should be in Data- not in Command-mode              
        
l12320: inc r18
        andi r18,$01
        breq l12330    ;                = 71.111ms for 1 (complete) cycle of AVR-ClockOut-period
        sbi $17,2      ;ClockOut=active                     (=7.711s for 100cycles at7.3728MHz)
        rjmp l12340   
l12330: cbi $17,2      ;ClockOut=inactive  
l12340: rcall l10690   ;waits until C64 makes Atn=active
        rjmp l12300    ;------------------------------------------------------------------------

l12350: cpi r16,$4d    ;'m'
        brne l12440

        mov r30,r18    ;lowbyte memory to read/write     =m-w  m-r
        mov r31,r19    ;highbyte                         0000-3fff RAM
        lds r16,$0106  ;value to write                   4000-7fff EEPROM
                       ;                                 8000-ffff flashROM
        andi r31,$7f   ;8000-ffff -> 0000-7fff  (0000-3fff stays)

        cpi r19,$40
        brcc l12390    ;b.i.4000-ffff

        cpi r17,$57    ;'w'   m-r m-w RAM
        breq l12360

        ld r16,z       ;m-r RAM
        rjmp l12430    ;------

l12360: cpi r19,$00    ;m-w RAM     doesn't write to registers and i/o  (too dangerous)
        brne l12370    ;b.i.0100-03ff  
        cpi r18,$61    ;=0000-0100
        brcs l12380    ;b.i.0000-0060
l12370: st z,r16       ;=0060-3fff
l12380: rjmp l13220

l12390: cpi r19,$80
        brcc l12420    ;b.i.8000-ffff
           
l12400: cpi r17,$57    ;'w'  =m-r  m-w  EEPROM
        breq l12410
                       ;=m-r (reads allways one byte only)

        rcall l12240   ;EEPROM-read
        
        rjmp l12430    ;------

l12410:                ;=m-w (writes allways one byte only)
       
        rcall l12220   ;EEPROM-write
        rjmp l13220    ;--------------- 

l12420: lpm r16,z      ;m-r flashROM (never write)
     
l12430: sts $012a,r16  ;writes to error-buffer
        ldi r16,$01
        sts erbuen,r16 ;sets error buffer end = 1
        sts erbuve,r26 ;error buffer vector to first byte of errorbuffer    

        rjmp l13220    ;------------------------------------------------------------------------
        
l12440: cpi r16,$45    ;'e' Extra Iec (same as S-JiffyDOS)
        brne l12460 
        
        lds r16,fljdal ;flag JiffyDOS allowed
        ori r16,$80    ;sets bit7

        cpi r17,$2b    ;'+'
        breq l12450    ;b.i.ie+
        
        cpi r17,$2d    ;'-'
        brne l12470    ;b.i.not ie- =syntax error 
        
        andi r16,$7f   ;clears bit7
l12450: sts fljdal,r16
        rjmp l12480    ;-------------------         
 
l12460: cpi r16,$55    ;'u'
        brne l12470
        rjmp l12710    ;=ui uj = reset


l12470: ;nop           ;syntax error
l12480: rjmp l13220    ;temporary to main waiting loop
;================================================================================================
l12490: push r22       ;                                                 =analysebyte & IEC-ports 
        in r22,$3f     ;status register                                 to printer + LED + buffer
        push r22 
       
        mov r22,r06
        andi r22,$08

        breq l12510    ;b.i.no print analyse byte to centronics printer
        
        push r16       ;save to stack                             r25=print debugvalue as hexdec         
        mov r16,r25
        rcall l12180   ;print as hexdec on printer
        pop r16
        
        rjmp l12510
        ;----------

l12500: push r22       ;                                                 =analysebyte & IEC-ports
        in r22,$3f     ;status register                                           to LED + buffer
        push r22 
        
l12510: mov r22,r06
        andi r22,$10
        breq l12540    ;b.i.no display analyse byte to (LEDs of) parallelport

l12520: push r25
        ldi r25,$00
        out $1b,r25    ;PortA
        pop r25
        out $1a,r25    ;DdrA
        com r25        ;SEC !!! changes carry-flag 
        out $1b,r25    ;PortA gives value inverted to port as LED display
        com r25         

        rjmp l12540
        ;----------
         
l12530: push r22       ;                                                 =analysebyte & IEC-ports
        in r22,$3f     ;status register                                                 to buffer
        push r22 
       
l12540: mov r22,r06
        andi r22,$60
l12550: breq l12580    ;b.i.no save of analyse byte or of IecPort to buffer 

        sbis $13,2     ;s.i.debug-jumper is open
        rjmp l12700    ;debug-jumper is close => don't change r04 r05 (and analyse-buffer)
        
l12560: push r23

        in r22,$17     ;IecDdr (0=input=inactiv   1=output=activ)
        com r22        ;       (0=activ 1=inactiv)
        andi r22,$54   ;%01010100  masks output-bits 

        in r23,$16     ;iecPort  
        andi r23,$2a   ;%00101010  masks input-bits
 
        or r23,r22     ;(bit 7 allways low)   

        ori r23,$01    ;flag f.analyse- & Iec-byte  =>  bit0=high
                       ;=>at IEC-port bit0 (of second byte) is allways high $x1,$x3...$xf
                       ;     (at IEEE-port bit 0 of second byte is allways low ($x8 or $x0)) 
       
        in r22,$10     ;PortD (IecAtn)
        rol r22
        rol r22
        rol r22
        rol r22
        rol r22
        andi r22,$80
        or r23,r22     ;r23 Bit7=IecAtn Bit6-1=IecPort Bit0=high

        cp r00,r23     ;compares actual and old IecBus value
        brne l12570    ;b.i.change

        cp r25,r01     ;compare actual and old debug-value
        brne l12570    ;b.i.new value
        rjmp l12690    ;=no new value

l12570: mov r01,r25    ;actual analyse value -> old value 
        mov r22,r25    ;analyse byte
        mov r00,r23    ;actual IEC-bus value -> old value
            
        rjmp l12620    ;=write analyse- / IECbus-byte into analysebuffer 

l12580: rjmp l12700    ;no analyse byte wanted
;- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
l12590: push r22       ;                                       ieee-ports-analyse bytes buffering
        in r22,$3f     ;status register
        push r22 

        sbis $13,2     ;s.i.debug-jumper is open
        rjmp l12700    ;debug-jumper is close => don't change r06 r07 (and analyse-buffer)
        
        tst r06
        brpl l12700    ;b.i.no IeeePortsAnalyse 

        push r23
        push r24 
        
l12600: in r22,$19     ;Parallelport
            
        in r23,$13     ;IEEE (&printer) control-port
        andi r23,$f8   ;masks printer-bits off => bit2-0=low => $x0 or $x8
        
        in r24,$19     ;Parallelport (second time)
        cp r22,r24
        brne l12600    
        
        pop r24

        com r22        ;inverts parallelport
                 
        cp r22,r02     ;compares parallelport actual and old value
        brne l12610    ;b.i.change at parallelport

        cp r23,r03     ;compares control-port actual and old value
        breq l12690    ;b.i. no change at Ieee-controlport
        
l12610: mov r02,r22    ;actual value -> old value
        mov r03,r23
         
l12620: push r28       ;backup Ylow
        push r29       ;backup Yhigh 
        
        mov r28,r06
        rol r28        ;save-IeeePort-bit -> carry
        andi r28,$40   ;masks save-analyse-byte-bit (shifted 1 bit left) 

        mov r28,r04    ;set Y-register to analysebufferposition   
        mov r29,r05

        brcs l12630    ;b.i.IeeePorts (allways print two bytes)
        breq l12640    ;b.i.no save of AnalyseByte (=save one byte only)

l12630: st y+,r22      ;stores AnlyseByte / IeeeParallelPort to buffer 00,02,04...

l12640: mov r22,r06
        rol r22
        brcs l12650    ;b.i.IeeePorts (allways print two bytes)
        brpl l12660    ;b.i.save analys byte only (Not IecPortByte) (=save one byte only)
         
l12650: st y+,r23      ;stores IecPort / IeeeControllPort to buffer 01,03,05...
        
l12660: cpi r28,$60
        breq l12670    ;b.i.0260
        cpi r28,$61
        brne l12680    ;b.i.not 0261 

l12670: ldi r28,$00    ;=analysebuffervector is at end 
        ldi r29,$02    ;=$0200 = begin small analysebuffer (big loadbuffer)
        mov r22,r06
        andi r22,$01
        breq l12680    ;b.i.analyse buffer 0200-025f
        ldi r28,$80    ;=analyse buffer begin 0180-025f (big analyse buffer (small loadbuffer))
        ldi r29,$01
        
l12680: mov r04,r28
        mov r05,r29
        
        pop r29        ;restore Y-register      
        pop r28 


l12690: pop r23

l12700: pop r22
        out $3f,r22    ;restores status register
        pop r22
        
        ret

                       ;if IEEE and analyse+IEC is enabled then difficult to see what is what:
                       ;there are allways written two bytes into the buffer:
                       ;              analyse+IEC   IEEE
                       ;first byte    analysebyte   parallelport
                       ;second byte   IEC-port      controlport
                       ;at bit0 of second byte you can see:
                       ;if it is a odd byte (x1, x3, ... xf) then it's analyse&IEC-port
                       ;if it is even (x0 or x8) then it's IEEE-port  

;================================================================================================
l12710: cli            ;disables IRQs (= SEI at C64)                                        Reset

                       ;serial IEC-port-----------------------------------PortB------------------   
                       ;                  DDR Port
                       ;input:             0  1   = Input + 40kOhm-Pullup (0.12mA)
                       ;output-activ (0V): 1  0   = Output + push 0V
                       ;output-inactiv     0  0   = Input (=inactiv output)
                       ;IEC-pins are In- or Output (but an Input is allways an Input
                       ;                                an Output is allways an Output)
                       ;using two pins for one line is made to allow additional input- and/or
                       ;output-driver-chips (what wouldn't be possible if one line would be 
                       ;one pin) 
                       ;I2C-pins (at least data) is In- and Output
                         
        ldi r16,$10    ;%00010000 = DataDirection
                       ;7 0 I2E-Clock     SCK  (Clock In at flashing)
                       ;6 0 IEC-SRQ Out   MISO (same at flashing)
                       ;5 0 IEC-Data In   MOSI (same at flashing)  
                       ;4 1 IEC-Data Out
                       ;3 0 IEC-Clock In
                       ;2 0 IEC-Clock Out
                       ;1 0 IEC-SRQ In
                       ;0 0 I2E-Data
                       
                       ;7 isn't allways Clock In because danger of accidental flashing if C64
                       ; would make Clock=active=0V while AVR reset  
        
        ldi r17,$ab    ;%10101011 = Port
                       ;7 1 I2E-Clock     SCK  (Clock In at flashing)
                       ;6 0 IEC-SRQ Out   MISO (same at flashing)
                       ;5 1 IEC-Data In   MOSI (same at flashing)  
                       ;4 0 IEC-Data Out
                       ;3 1 IEC-Clock In
                       ;2 0 IEC-Clock Out
                       ;1 1 IEC-SRQ In
                       ;0 1 I2E-Data

        ldi r26,$00

        out $18,r26    ;PortB = all 0 to prevent that AVR pulls 20mA to 5V 
        out $17,r16    ;DDRB = serial IEC-port settings  
        out $18,r17    ;PortB
                       ;sets Data=active       
                       ; as flag that device isn't ready

        ldi r27,$ff

                       ;Parallelport--------------------------------------PortA------------------
                       ;                  DDR Port
                       ;input:             0  1   = Input + 40kOhm-Pullup (0.12mA)
                       ;output-activ (0V): 1  0   = Output + push 0V
                       ;output-inactiv     0  1   = Input (=inactiv output) ;   
                       ;each pin is In- and Output      
                       ;AVR must never pull active (with 20mA) to 5V = Bit-combination %11 
                       ;(= DDRA=1 PortA=1) is never allowed
                       ;To write a new value to the port you must change DDRA and PortA in two
                       ;steps. To prevent that accidentially a %11 is written first PortA must be
                       ;cleared
                       ;it's allways important to first clear first DdrX (or PortX) and then set
                       ;bits in PortX (or DdrX). Best is to first write #$00 (r26 later) into
                       ;DdrX or PortX and then set the bits
        out $1a,r26    ;ddra to input (#00) 
        out $1b,r27    ;PortA = PullUpOn  ParallelPort=inactiv
                
        out $14,r26    ;DdrC----------------------------------------------PortC------------------
        ldi r16,$fd    ;%11111101
        out $15,r16    ;PortC
                       ;Bit                    DDR Port
                       ;7 IEEE-EOI              0   1      end or identify 
                       ;6 IEEE-DAV              0   1      data valid
                       ;5 IEEE-NRFD             0   1      not ready for data
                       ;4 IEEE-NDAC             0   1      not data acepted
                       ;3 IEEE-ATN              0   1      attention 
                       ;2 Strobe  Out inactive  0   1  (Out active  1   0)
                       ;1 Present In (only)     0   0  no pullup because 10kOhm external 
                       ;0 Busy In & pullup      0   1                             pulldown
                        
                       ;bit 7-4 are in- and output
                       ;bit 3 is output only
                       ;bit 2 is usually output (only input when debug-jumper is read)
                       ;bit 1&0 are inputs  

        out $11,r26    ;DdrD = input--------------------------------------PortD------------------
        out $12,r27    ;PortD $ff                 (unused pins PullUpOn to prevent swinging)
                       ;                       DDR Port
                       ;7 (Data2?)              0   1
                       ;6 (Clock2?)             0   1
                       ;5 (SRQ2?)               0   1       
                       ;4 (RTS)   -             0   1
                       ;3 (CTS)   -             0   1 
                       ;2 AtnIn   In+Pullup     0   1
                       ;1 (TXD)   -             0   1
                       ;0 (RXD)   -             0   1---------------------PortD------------------
    

        out $06,r26    ;DdrE   (#$00) ------------------------------------PortE------------------
        ldi r16,$03    ;%00000011
        ldi r17,$04    ;%00000100
        out $07,r16    ;PortE 
        out $06,r17    ;DdrE PinE2=output  =  OC1B  (LED on)           atmega-only
                       ;                       DDR Port                (would be necessary at 
                       ;2 Error-LED             1   0                     AT90S8515) 
                       ;1 (ResetOut or          0   1
                       ;   datadirection of
                       ;   parallelportdriver?) 
                       ;0 (ATN2?)               0   1---------------------PortE------------------




        ldi r16,$7f
        out $3d,r16    ;stackpointerlow = 7f
        out $3e,r26    ;stackpointer high to 0 => stackpointer to 007f  stack=007f-0060 =32bytes
                
        mov r16,r06    ;analyse buffer mode
        andi r16,$02   ;masks bit1 for debug-jumper-function
        breq l12730    ;b.i.debug-printing isn't allowed
                       ;at first reset r06 contains nonsens => debug-jumper must be open.
                       ;at further resets r06 contains correct value  from Eeprom

        ldi r19,$05    ;%.....101
        out $33,r19    ;starts timer0 (8bit) with 8MHz/1024 = 1count per 128s
        out $32,r26    ;$00 to timer0 counts up 1*128s
l12720: in r19,$32     ;reads timer
        cpi r19,$01
        brcs l12720    ;b.i.counter<$01 = waits 128s
        sbic $13,2     ;b.i.centronic-Strobe-debug-jumper is on
l12730: rjmp l12850    ;=Centronics-Strobe-debug-jumper=off  = no debug-buffer-printing
                
        rcall l10050   ;LED blink                                                 =debug printing   

l12740: ldi r17,$00
l12750: in r16,$19     ;parallelport 
        cpi r16,$ff
        brne l12740    ;b.i.IeeeFloppy makes any line of IeeePort=active
        dec r17
        brne l12750    ;waits until parallelport is free=unused from Ieee-device

        rcall l10040   ;LED on

                       ;if AVR-LED blinks while debug-printin, then user must reset IeeeFloppy 
                       ;because IeeeFloppy pulls lines of parallelport to active=0V


l12760: ldi r16,$00
l12770: sbis $13,2     ;b.i.strobe-debug-jumper gets off-switched
        rjmp l12760     
        dec r16
        brne l12770     

        ldi r17,$00
l12780: ldi r16,$7f    ;del
        rcall l12100   ;sends 256 times 'del' to printer to delete earlier received wrong bytes
        dec r17        ;when debug-jumper caused wrong strobes to printer
        brne l12780

        ldi r16,$0d
        rcall l12100
        ;ldi r16,$0a
        ;rcall l12100
        

                       ;the printer must make an automatic linefeed when it receives a 
                       ;carriage-return.
                       ;the AVR cannot send an additional linefeed to the printer when the AVR
                       ;receives a CR $0d from the C64 because a $0d can also be a normal
                       ;data-character byte at printing of a bitmap
                                                    
        ldi r17,$05
l12790: ldi r16,$20
        rcall l12100   ;print 5 spaces
        dec r17
        brne l12790
        
        ldi r17,$00
l12800: mov r16,r17
        rcall l12180   ;print header '$00' - '$0f'
        inc r17
        cpi r17,$10
        brne l12800


        ldi r27,$00    ;Xhigh=0  (r26=#$00) 

l12810: ldi r16,$0d
        rcall l12100
        ;ldi r16,$0a
        ;rcall l12100
        
l12820: ldi r16,$0d
        rcall l12100
        ;ldi r16,$0a
        ;rcall l12100
        mov r16,r27    ;highbyte address
        rcall l12190   ;print as asci
        mov r16,r26    ;lowbyte address
        rcall l12190   ;print as acsii
        ldi r16,$3a    ; ':'
        rcall l12100
        
l12830: ld r16,x+        
        rcall l12180   ;print as hexdec
        mov r25,r26    ;r25=Xlow
        andi r25,$0f
        brne l12830
        cpi r26,$20
        brne l12840    ;b.i.        
        cpi r27,$00
        breq l12810    ;b.i. $0020=additional break = end of registers r00-r31
l12840: cpi r26,$60
        brne l12820    
        cpi r27,$00    ;=0060,0160,0260
        breq l12810    ;b.i.0060=additional break = end of I/O-area
        cpi r27,$02
        brne l12820    ;b.i.0160
        ldi r16,$0c    ;formfeed  =$0260=end
        rcall l12100
        
     
                       ;-------------------------------------------------------end debug printing   

l12850: ldi r26,$00    ;x low (important after debug printing)
        sbis $13,2     ;s.i.debug-jumper is open
        ldi r26,$07    ;=debug-jumper is closed => don't change r00-r06
 
        ldi r27,$00    ;x high (r26=x low =#$00/#$07)
        ldi r25,$00
l12860: st x+,r25      ;clears $00/07-$18 $1c-$23 $28-$2f $3c-$47 $50-$5c   
        cpi r26,$19    ;        00/07-24   28-35   40-47   60-71   80-92
        brne l12870
        ldi r26,$1c    ;(not $00-$06 = r00-r06)
l12870: cpi r26,$24    ; not $19-$1b = r25-r27 
        brne l12880    ; not $24-$27 = I/O-$04-$07 = calibration-byte & PortE 
        ldi r26,$28    ; not $30-$3b = I/O-$10-$1b = PortD - PortA
l12880: cpi r26,$30    ; not $48-$4f = I/O-$28-$2f = Timer1 (why)
        brne l12890    ; not $5d-$5f = I/O-$3d-$3f = stack & statusregister
        ldi r26,$3c 
l12890: cpi r26,$48
        brne l12900
        ldi r26,$50
l12900: cpi r26,$5d
        brne l12860

        ldi r26,$60
l12910: st x+,r25      ;clears 0060-015f/025f
        cpi r26,$60
        brne l12910
         
        ldi r24,$01
        sbic $13,02    ;s.i.debug-jumper is closed
        ldi r24,$02    ;debug-jumper is open

        cp r27,r24
        brne l12910    ;-------------------end initialice memory---------------------------------

        ldi r26,$00    ;must be #$00 allways because there can allways be an IRQ
        ldi r27,$ff    ;must be #$ff allways because there can allways be an IRQ  


        ldi r20,$00    ;=counter for EEPROM errors

l12920: ldi r18,$40
        ldi r19,$00    ;EEPROM-address = $0040 = entry-table0

        ldi r30,$80
        ldi r31,$00    ; z RAM-vector =$0080
 
l12930: rcall l12240   ;EEPROM read 0040-007f
        st z+,r16      ;RAM 0080-00bf

        inc r18
        brpl l12930     
 
        ldi r18,$c0
        ldi r19,$00    ;EEPROM-address = $00c0 = entry-table1

        ldi r30,$80
        ldi r31,$00    ; z RAM-vector =$0080
 
l12940: rcall l12240   ;EEPROM read 00c0-00ff
        ld r17,z+      ;RAM 0080-00bf
        cp r16,r17
        brne l12960    ;b.i.difference of EEPROM-table0 to table1
        inc r18        ;=cp r18,$00  
        brne l12940

        ldi r18,$40
        ldi r19,$01    ;EEPROM-address = $0140 = entry-table2

        ldi r30,$80
        ldi r31,$00    ; z RAM-vector =$0080
 
l12950: rcall l12240   ;EEPROM read 00c0-00ff
        ld r17,z+      ;RAM 0140-017f
        cp r16,r17
        brne l12960    ;b.i.difference of EEPROM-table0 to table2
        inc r18        ;perhaps brpl l12950 would be shorter?
        brpl l12950
        rjmp l13140    ;=no EEPROM-corruption  --------------------------------------------------

l12960: dec r20        ;counter for EEPROM errors
        brne l12970    ;b.i.1-255
        rjmp l13120    ;=256 errors (important that no hanging-loop when defectiv EEPROM)

l12970: dec r30        ;=EEPROM-corruption  

        mov r18,r30    ; RAM-vector low 80-bf   
        clc
        sbci r18,$c0   ;                c0-ff
        ldi r19,$00
        rcall l12240   ;EEPROM read 00c0-00ff
        mov r17,r16

        clc
        sbci r18,$80   ;                40-bf
        ldi r19,$01
        rcall l12240   ;EEPROM read 0140-01bf

        ld  r18,z      ;RAM =EEPROM-0040-00bf       

        cpi r30,$80    
        breq l12980    ;b.i.entry-possition00 b.i.auto-repair EEPROM-corruption
        rjmp l13090    ;=not autorepair-byte

l12980:                ;flag f.autorepair is $aa or $55, nothing else possible  
                       ;r16=$0140 r17=$00c0 r18=$0040 of EEPROM
                         
        ldi r19,$00    ;=amount of allowed values (55 or aa)

        cpi r16,$aa
        breq l12990
        cpi r16,$55
        brne l13000
l12990: inc r19

l13000: cpi r17,$aa
        breq l13010
        cpi r17,$55
        brne l13020
l13010: inc r19

l13020: cpi r18,$aa
        breq l13030
        cpi r18,$55
        brne l13040
l13030: inc r19

l13040: ;sts $0110,r16
        ;sts $0111,r17
        ;sts $0112,r18
        ;sts $0113,r19
        ;sts $0114,r20
        
        cpi r19,$00
        breq l13120    ;b.i.no tableposition00 entry is allowed  

        cpi r19,$01
        brne l13050    ;b.i.not only 1 entry is correct (2 or 3 correct entries) 

        cpi r16,$aa    ;=1 correct entry
        breq l13070    ;b.i.r16 is allowed
        cpi r16,$55
        breq l13070    ;b.i.r16 is allowed  

        cpi r17,$aa
        breq l13060    ;b.i.r17 is allowed
        cpi r17,$55
        breq l13060    ;b.i.r17 is allowed
        
        mov r16,r18    ;r16 and r17 are not allowed => r18 must be allowed 
        rjmp l13070    ;repair EEPROM-corruption   r16=correct autorepair-value


l13050: cp r16,r17     ;=2 or 3 allowed entries (but 2 or 3 allowed entries can be different
        breq l13080    ;b.i.r16 = r17                                       55 aa ff  55 55 aa)
        cp r16,r18
        breq l13070
        cp r17,r18 
        brne l13120    ;=2 allowed, but different entries

l13060: mov r16,r17
l13070: mov r17,r16
l13080: rjmp l13110    ;repair EEPROM-corruption   r16=r17=correct autorepair-value


l13090:                ; RAM-vector low 81-bf   =repair not-'auto-repair-EEPROM'-bytes
                       ;  r16=$0140 r17=$00c0 r18=$0040 of Eeprom

        cp r16,r17
        breq l13100    ;b.i.table2-value=table1-value
        cp r16,r18      
        breq l13100    ;b.i.table2-value=table0-value
        mov r16,r17
        cp r17,r18
        brne l13120    ;b.i.table1-value=table0-value

l13100: lds r17,$0080  ;      = repair EEPROM corruption   r16=correct value
l13110: cpi r17,$aa
        brne l13120    ;b.i.autorepair EEPROM is disabled

        mov r18,r30    ;lowbyte RAM vector (80-bf)   r16=correct to-write value        
        clc
        sbci r18,$40   ;->40-7f
        ldi r19,$00
        rcall l12220   ;EEPROM-write 0040-007f table0 
        mov r16,r17
        clc 
        sbci r18,$80   ;->00c0-00ff
        rcall l12220   ;EEPROM-write 00c0-00ff table1 
        mov r16,r17
        clc 
        sbci r18,$80   ;->0140-017f
        ldi r19,$01
        rcall l12220
        rjmp l12920    ;again from beginning (easier)-------------


l13120: ldi r30,$90    ;=unrepairable EEPROM-corruption or auto-repair disabled
        ldi r31,$00
          
l13130: st z+,r27      ;#$ff    clears $0090-$00bf=emulation-tables

        cpi r30,$c0
        brne l13130

        ldi r20,$ff    ;sets flag for EEPROM-error 
        ldi r30,$90    ;clears 008f-0080
        ldi r16,$ff    ;sets calibrationbyte to illegal
        rjmp l13150


l13140: ldi r30,$8f    ;=no EEPROM-corruption or repairable EEPROM-corruption
        lds r16,$0081  ;calibrationbyte from EEPROM 
        lds r06,$0082  ;analyse buffer mode
        inc r06
		breq l13150    ;b.i.had been #$ff = empty EEPRPM
		dec r06
		  
l13150: ldi r31,$00    ;z RAM vector = $008f
        
l13160: st -z,r26      ;'$00 clears 008e-0080  !!change if 8e, 8d ... should be important here!!
        
        cpi r30,$80    ;brmi l13160 doesn't work because statusreister isn't changed 
        brne l13160
                
        
        cpi r16,$ff    ;(ff=empty EEPROM or corruted EEPROM)
        brne l13170    ;b.i.EEPROM-calibratinbyte is allowed 
        ldi r16,$80    ;default for average calibrationbyte  !!! wrong timing at JiffyDOS
l13170: out 04,r16     ;calibrationbyte for internat 8MHz-oscilator

        rcall l10060   ;LED off    mustn't change r20!!!!!!!!!!!
        cpi r20,$00
        breq l13180
        rcall l10050   ;LED blink

;................................................................................................        
l13180: ldi r16,$40    ;%01000000 
        out $3b,r16    ;General IRQ mask register  allows int0 irq
        out $35,r26    ;MCU control register int0-IRQs at low level 
                       ;%00000000 low level = IRQ-trigger
                       ; good: triggers allways an IRQ
                       ;%00000010 falling edge = IRQ-trigger doesn't work because:
                       ; IEC-ATN falls so slow that it doesn't trigger reliably an IRQ 

        sbis $13,2     ;s.i.debug-jumper is open
        rjmp l13200    ;debug-jumper is closed
        
        ldi r16,$00
        ldi r17,$02
        mov r18,r06    ;analyse buffer mode
        andi r18,$01
        breq l13190    ;b.i.0200-025f
        ldi r16,$80    ;                           initialize analyse-buffer-vector 
        ldi r17,$01    ;=0180-025f  
l13190: mov r04,r16    ;X low ieee-analyse buffer
        mov r05,r17    ;X high

        rcall l12590   ;===== 

l13200: ldi r28,$2a    ;y=012a
        ldi r29,$01
        ldi r30,low(l13270<<1)
        ldi r31,high(l13270<<1)              ; Initialize Z pointer

l13210: lpm r16,z+     ;copies 73... message to errorbuffer 
        st y+,r16
        cpi r28,$44
        brne l13210
        ldi r16,$1a
        sts erbuen,r16 ;sets error buffer end
        sts erbuve,r26 ;sets error buffer vector to first byte
 
;------------------------------------------------------------------------------------------------        
l13220: ldi r16,$7f
        out $3d,r16    ;stackpointerlow = 7f
        out $3e,r26    ;stackpointer high to 0 => stackpointer to 007f    

        ldi r25,$01    ;01--
        rcall l12500

        mov r25,r26    ;----
        rcall l12500
        
        mov r25,r27    ;----
        rcall l12500 
     
                       ;                                                                   
        sts flicbb,r26 ;#$00 clears flag f. IecAtnMode   = in DataMode (important f.rcall l10690)

                       ;1541 makes all IecLines = inactive
                       ;AVR shouldn't make DataOut=active because there is no AtnAck-hardware

        lds r16,avinco ;AVR-internal command                                                 ebf0
        cpi r16,$00
        breq l13230    ;b.i.no avr-internal command
        sts avinco,r26 ;#$00 
        rcall l12260   ;analyse & execute new AVR-internal command 

l13230: rcall l10690   ;test if IecAtn change (if IecAtn=active -> 
                       ;                               l10320 serves bus after Atn-active-edge) 

;. . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . 

l13240: ldi r16,$40
        out $3b,r16    ;enable IRQ at low-level of PinD2=Int0=if AtnIn=active=0V (not inverted) 
  
        sei            ;enable IRQs
       
        ldi r25,$01    ;01--
        rcall l12500

 

l13250: cli            ;disables IRQs

        in  r16,$3b    ;reads General IRQ Mask Register                                      ec00
        andi r16,$40
        brne l13260    ;b.i.IecAtnPin IRQs still allowed
                       ;=IRQ-routine disabled Atn-line-IRQ (=Atn-active-edge received)
        rjmp l10320    ;serves bus after Atn-active-edge  

        
l13260: out $17,r26    ;DDRB ClockOut=inactive DataOut=inactive SrqOut=inactive
        ldi r16,$ab    ;%10101011         
        out $18,r16    ;PortB

        rjmp l13240

;================================================================================================
l13270: .db "73,IEC2IEEE NLQ@GMX.DE,0,0 
;================================================================================================
;                        SUBROUTINES-table
;     l10040  LED on
;     l10050  LED blink 
;     l10060  LED off


;     l10320  read byte after ATN-edge       

;     l10760  IECIN read one byte from C64 to AVR 
;     l11100  IECOUT send one byte from AVR to C64
;     l11690  Job when Talk received
;     l11320  JiffyDOS-LOAD
;     l12260  analyse & execute new AVR-internal command
