Source file: /~heha/vt/viewers/vt080.zip/src/VI²C.ASM

;Include-Datei für Videotextdekoder als TSR
;Hochoptimiert auf Geschwindigkeit und Codegröße
;Version für c't-Videotextkarte und das h#s-Derivat derselben
;API-Beschreibung:
;I2CBasis: Standard (c't): 100h, 1F0h, 200h, 220h, 300h, 3E0h
;aber:	1F0: Kollision mit Festplatte
;	200: Kollision mit Gameport
;	220: Kollision mit SoundBlaster
;	300: Kollision mit einigen Prototypen- und Netzkarten
;I2CBasis: Standard (h#s): 100h, 104h, 108h, 210h, 300h, 3e0h, 3e4h (,10ch)
;bis auf 300h keine bisher bekannten Kollisionen



;SCHNITTSTELLEN
;proc SI2C	;Sende CX Bytes zum VTD aus Puffer SI
	;PE: CX=I2CAnzahl (0 = Null Bytes)
	;    SI=Puffer im Datensegment, DS im Datensegment
	;PA: CY=1: Fehler; dann Ansprung der Critical-Error-Routine
	;    SI=SI+CX (wenn fehlerfrei)
	;VR: SI


;proc RI2C	;Empfange CX Bytes vom VTD nach Puffer DS:SI
	;PE: CX=I2CAnzahl (0 = Null Bytes)
	;    SI=Puffer im Datensegment, DS im Datensegment
	;PA: CY=1: Fehler; dann Ansprung der Critical-Error-Routine
	;    SI=SI+CX (wenn fehlerfrei)
	;VR: SI

;SStrI2C:	;PASCAL-String SI schicken

;SBufEI2C:	;Mit ein paar Steuerzeichen via STOS gefüllten Puffer ausgeben
	;PE: DI zeigt hinter das letzte aufgefüllte Zeichen im Puffer
	;PA: CX=Anzahl
	;VR: CX

;SBufI2C:	;I2CAnzahl:CX; fest aus Buf, PA:CY, VR:FLAGS

;RBufI2C:	;I2CAnzahl:CX; fest aus Buf, PA:CY, VR:FLAGS

;proc I2CInit
	;PE: -
	;PA: AL=Statusbyte
	;CY=1: I2C-Fehler (z.B. Karte nicht auf dieser Adresse)
;	call	StopI2C
;I2CStat:

;proc AddWaitI2C
	;Warte-INs hinzufügen
	;CY=1: Keine weiteren Wait-States möglich

;proc SubWaitI2C
	;Warte-INs entfernen
	;CY=1: Wait-States sind bereits Null

;proc ProgAcq
	;Programmiert VTD auf die Suche nach
	;PE: DX=Seite, Bit 15=Wildcard-Flag
	;    CX=Unterseite, Bit 15=Wildcard-Flag
	;    BH=Akquisitor-Nummer 0..3(..7)
	;PA: CY=1: Fehler auf I2C-Bus
	;VR: AX, ein paar Bytes von [Buf]

;proc GetPageInfo
	;hole aus [SI] (Abbild der Zeile 25) die Angaben über:
	;DX- Seite
	;CX- Unterseite
	;BX- C-Bits
	;AH- HamErrors
	;VR:AX,SI

;****** CCT-Hardwarezugriff-Routine (Ebene I) ******
;+++ Ebene 1a: Bitzugriff +++
INPU:	in	al,dx
adr0:	in	al,dx		;4 Waits in Form von INs
	in	al,dx
	in	al,dx
	in	al,dx
	ret

proc StartI2C		;Start für I²C-Bus
;DX ist standardmäßig bei SDAH
;(DX-2=SCLH, DX-1=SCLL, DX=SDAH, DX+1=SDAL)
	mov	dx,[I2CBasis]
	xchg	ah,al	;am Anfang: SDA=SCL=HIGH
	inc	dx
	inc	dx

	inc	dx
	call	INPU;	SDAL
	call	INPU;	SDAL	;4µs
	dec	dx
	dec	dx
	call	INPU;	SCLL	;sdal;scll am Schluß: SDA=SCL=LOW
	inc	dx
	xchg	al,ah
	ret
	endp

StopI2C:		;Ende der Übertragung
	mov	dx,[I2CBasis]
	inc	dx
	inc	dx
proc StopI2Ci		;Ende der Übertragung (intern DX=SDAH-Adr)
	inc	dx
	call	INPU;	SDAL	;Am Anfang: SDA=X, SCL=LOW
	dec	dx
	dec	dx
	dec	dx
	call	INPU;	SCLH
	call	INPU;	SCLH	;4µs
	inc	dx
	inc	dx
	call	INPU;	SDAH	;am Schluß: SDA=SCL=HlGH
	ret
	endp

;+++ Ebene 1b: Bytezugriff +++
proc SByI2C	;1 Byte senden
	;PE: AL: Zu sendendes Byte
	;    DX=SDAH-Adresse
	;PA: CY=Fehler (fehlende Empfangsquittung des SAA)
	;VR: AH
	push	cx
	mov	cx,8
	xchg	ah,al	;Datenbyte nach AH
@@l:
	rol	ah,1	;Bit7 herausshiften, ohne AH zu zerstören
	jc	@@1
	inc	dx
	call	INPU;	SDAL
	dec	dx
	jr	@@2
@@1:
	call	INPU;	SDAH
	in	al,dx	;Kontrolle, ob kein anderer stört
	shr	al,1	;(Warten hier nicht erforderlich!)
	cmc
	jc @@e
@@2:
	dec	dx
	dec	dx
	call	INPU;	SCLH	;2µs
	call	INPU;	SCLH	;4µs, Empfänger braucht Zeit zum Einsampeln
	inc	dx
	call	INPU;	SCLL
	inc	dx
	loop @@l
	call	INPU;	SDAH
	dec	dx
	dec	dx
	call	INPU;	SCLH
	inc	dx
	inc	dx
	call	INPU;	SDAH	;zum Einlesen
	shr al,1
@@e:
	dec	dx
	call	INPU;	SCLL
	inc	dx
	xchg al,ah	;unverändert
	pop cx
	ret
	endp

proc RByI2C
	;PE: Bit0(AL)=1: Letztes Byte erwartet
	;    DX: SDAH-Adresse
	;PA: AL:Datenbyte
	;    CY=1: Fehler beim Empfang (Irgendwas klemmt auf der Leitung)
	;    (tritt höchstens bei gesetztem Bit0(AL) auf!)
	;VR: AX, DX
	push	cx
	mov	cx,8
	xchg	ah,al
	call	INPU;	SDAH	;SCL ist schon Low
	dec	dx
	jr	@@l1
@@
Detected encoding: OEM (CP437)1
Wrong umlauts? - Assume file is ANSI (CP1252) encoded