Hallo!
Nachdem ich schon mehrfach was machte mit diversen I²C-Geräten (meißt auf Basis von ATmega16, 32, 644 und zuletzt vermehr mit einem NANO (ATmega328P), was bislang auch immer auf Anhieb klappte, bringt mich jetzt ein alter ATmega8-16P zur Verzweifelung.
Eine Evaluation eines QN8007B wofür ich aufgrund des Gehäuses (QFN24) eine entsprechende Platine brauchte - ein Anschluss an einen NANO o.ä. machte keinen Sinn.
Also zeichnete ich eine Platine die den QFN24 nebst Periferie trägt, sowie einen µC den ich seit Jahren noch unbenutzt liegen hatte.
Die Wahl viel auf den ATmega8-16P im DIP-28.
Platine fertig, es gelang mir auch mit SMD-Schablone und Heißluft den winzigen QFN24 ordentlich drauf zu bekommen.
Es scheitert aber nun am ATmega8:
Verwendet wird Pin 27 (PC4) als SDA und Pin 28 (PC5) als SCL - das sind die Hardware-I²C-Pins laut Datenblatt.
Das dumme ist:
Nach dem booten sind SDA und SCL korrekter weise auf High 3,3V (externe PullUps mit 4k7).
Sende ich aber einen I²C-Befehl dann wechselt wahlweise SDA oder SCL (relativ zufällig, aber immer einer von beiden) auf Low und verharrt dort.
Eben mit Oszi genau geschaut:
Bis auf diesen Wechsel einer der I²C-Leitungen von High auf Low passiert am I²C-Bus sonst gar nix:
Keine 100kHz SCL, eine Daten an SDA
Der Quelltext sieht nach etlichen Versuchen entsprechend aus - zum Teil ist an den auskommentierten Stellen aber zu erkennen was ich schon alles versucht habe.
Nur soviel:
Taste 2 führt zur Sub mit dem I²C-Adress-Scanner,
Taste 3 soll die 28 Register des QN8007b auslesen (I²C-Adresse h56 (write) / h57 (read).
Der I²C-Scanner erkennt alle 128 Readadressen die es gibt weil er angeblich jedes mal ein Ack erkennt.
Taste 3 hängt sich manchmal komplett auf (auch der Watchdog hilft da nicht), oder ließt alle Register entweder mit hFF oder h00.
Eben abhängig welche der beiden Leitungen auf GND gezogen wird.
Da die PullUps näher am QN8007B sind als am µC konnte ich eben den Spannungsabfall messen:
Die Leitung welche nach Low wechselt (entweder SDA oder SCL) hat am Portpin saubere 0V, gegenüber am QN8007B sowie am PullUp noch Restspannung von verrauschten 8-9mV.
Es ist also definitiv der µC der da unkontrolliert nach GND zieht, nicht der QN8007B!
Alles anzeigen
Im Anhang ein Bild meiner Platine.
Hat da jemand nen Tip für mich was da im ATmega8 dazwischen funkt? Im Datenblatt habe ich nix gefunden bezüglich aktivierter Zweitfunktionen an diesen Ports.
Jürgen
Nachdem ich schon mehrfach was machte mit diversen I²C-Geräten (meißt auf Basis von ATmega16, 32, 644 und zuletzt vermehr mit einem NANO (ATmega328P), was bislang auch immer auf Anhieb klappte, bringt mich jetzt ein alter ATmega8-16P zur Verzweifelung.
Eine Evaluation eines QN8007B wofür ich aufgrund des Gehäuses (QFN24) eine entsprechende Platine brauchte - ein Anschluss an einen NANO o.ä. machte keinen Sinn.
Also zeichnete ich eine Platine die den QFN24 nebst Periferie trägt, sowie einen µC den ich seit Jahren noch unbenutzt liegen hatte.
Die Wahl viel auf den ATmega8-16P im DIP-28.
Platine fertig, es gelang mir auch mit SMD-Schablone und Heißluft den winzigen QFN24 ordentlich drauf zu bekommen.
Es scheitert aber nun am ATmega8:
Verwendet wird Pin 27 (PC4) als SDA und Pin 28 (PC5) als SCL - das sind die Hardware-I²C-Pins laut Datenblatt.
Das dumme ist:
Nach dem booten sind SDA und SCL korrekter weise auf High 3,3V (externe PullUps mit 4k7).
Sende ich aber einen I²C-Befehl dann wechselt wahlweise SDA oder SCL (relativ zufällig, aber immer einer von beiden) auf Low und verharrt dort.
Eben mit Oszi genau geschaut:
Bis auf diesen Wechsel einer der I²C-Leitungen von High auf Low passiert am I²C-Bus sonst gar nix:
Keine 100kHz SCL, eine Daten an SDA
Der Quelltext sieht nach etlichen Versuchen entsprechend aus - zum Teil ist an den auskommentierten Stellen aber zu erkennen was ich schon alles versucht habe.
Nur soviel:
Taste 2 führt zur Sub mit dem I²C-Adress-Scanner,
Taste 3 soll die 28 Register des QN8007b auslesen (I²C-Adresse h56 (write) / h57 (read).
Der I²C-Scanner erkennt alle 128 Readadressen die es gibt weil er angeblich jedes mal ein Ack erkennt.
Taste 3 hängt sich manchmal komplett auf (auch der Watchdog hilft da nicht), oder ließt alle Register entweder mit hFF oder h00.
Eben abhängig welche der beiden Leitungen auf GND gezogen wird.
Da die PullUps näher am QN8007B sind als am µC konnte ich eben den Spannungsabfall messen:
Die Leitung welche nach Low wechselt (entweder SDA oder SCL) hat am Portpin saubere 0V, gegenüber am QN8007B sowie am PullUp noch Restspannung von verrauschten 8-9mV.
Es ist also definitiv der µC der da unkontrolliert nach GND zieht, nicht der QN8007B!
BASCOM-Quellcode
- 'Test V1.0 EVAL-QN8007B UKW-Transmitter.
- 'Achtung: Der 3,3V-Regler für den QN8007 fehlt noch. Auf 3,3V kann das Board nur ohne LCD betrieben werden!
- '$Regfile="m8adef.dat"
- $Regfile="m8def.dat"
- $Crystal=11059200
- $hwstack=40
- $swstack=16
- $framesize=32
- $baud=38400
- $LIB "I2C_TWI.LBX"
- DDRB=&B00001001 'MSB sind Inputs, LSB sind Outputs
- 'ddrc=&B11111111 'Alles sind Outputs
- DDRD=&B11000010 'nur drei Outputs, sonst alles Inputs
- config portb=&B11000110 'PullUps nur bei zwei MSB
- 'config portc=&B00110000 'PullUps alle aus
- config portd=&B00000000 'PullUps nur für Taster und INT
- config watchdog = 2048
- config debounce = 100
- portb.2=0
- portb.1=0
- config SDA = portc.4
- config SCL = portc.5
- config Twi = 100000
- i2cinit
- dim reg as byte
- dim i as byte
- dim Wert(29) as byte
- config base = 0
- Dim Slaveadresse As Byte 'Adressvariable für Suchlauf
- 'gosub bootmeldung
- 'config lcdpin = Pin, db4= PC.3 , db5= PC.2 , db6= PC.1 , db7= PC.0 , E= PD.7 , RS= PD.6
- 'config lcd = 16*2
- 'wait 10
- 'initlcd
- 'wait 1
- do
- waitms 250
- 'debounce pind.2 , 0 , QNint 'Auswertung QN-INT
- debounce pind.3 , 0 , S1mode 'Auswertung Taste S1 (Mode)
- debounce pind.4 , 0 , S2up 'Auswertung Taste S2 (Up)
- debounce pind.5 , 0 , S3down 'Auswertung Taste S3 (Down)
- waitms 250
- reset watchdog
- loop
- bootmeldung:
- print "EVAL-Board QN8007"
- print "V1.0 Test"
- return
- QNint:
- print "INT vom RDS-Modul QN8007"
- return
- S1mode:
- print "S1 Mode gedrückt!"
- pinb.2 = 1
- Pinb.1 = 1
- return
- S2up:
- print "S2 Up gedrückt!"
- Pinb.2 = 0
- pinb.1 = 0
- Print "I2C Slaves suchen..."
- Wait 10
- For Slaveadresse = 1 To 255 Step 2 ' für alle geraden Adressen
- I2cstart 'Startbedingung senden
- I2cwbyte Slaveadresse 'Addresse senden
- If Err = 0 Then
- Print "ACK!" 'I2C-Slave gefunden?
- Print "Slave dec: " ; Slaveadresse 'Dezimalwert ausgeben
- Print "h" ; Hex(slaveadresse) ; " b" ; Bin(slaveadresse)
- Wait 2
- End If
- I2cstop 'Bus freigeben
- Next
- 'Cls
- Print "Ende Scan"
- Wait 2
- return
- S3down:
- print "S3 Down gedrückt!"
- print "Lese QN8007 aus:"
- i2cstart
- i2cwbyte &h57
- i2cwbyte &h00
- i2crbyte wert(0) , Ack 'Lese Register h00
- i2crbyte wert(1) , Ack 'Lese Register h01
- i2crbyte wert(3) , Ack 'Lese Register h02
- i2crbyte wert(4) , Ack 'Lese Register h03
- i2crbyte wert(5) , Ack 'Lese Register h04
- i2crbyte wert(6) , Ack 'Lese Register h05
- i2crbyte wert(7) , Ack 'Lese Register h06
- i2crbyte wert(8) , Ack 'Lese Register h07
- i2crbyte wert(9) , Ack 'Lese Register h08
- i2crbyte wert(10), Ack 'Lese Register h09
- i2crbyte wert(11), Ack 'Lese Register h0A
- i2crbyte wert(12), Ack 'Lese Register h0B
- i2crbyte wert(13), Ack 'Lese Register h0C
- i2crbyte wert(14), Ack 'Lese Register h0D
- i2crbyte wert(15), Ack 'Lese Register h0E
- i2crbyte wert(16), Ack 'Lese Register h0F
- i2crbyte wert(17), Ack 'Lese Register h10
- i2crbyte wert(18), Ack 'Lese Register h11
- i2crbyte wert(19), Ack 'Lese Register h12
- i2crbyte wert(20), Ack 'Lese Register h13
- i2crbyte wert(21), Ack 'Lese Register h14
- i2crbyte wert(22), Ack 'Lese Register h15
- i2crbyte wert(23), Ack 'Lese Register h16
- i2crbyte wert(24), Ack 'Lese Register h17
- i2crbyte wert(25), Ack 'Lese Register h18
- i2crbyte wert(26), Ack 'Lese Register h19
- i2crbyte wert(27), Ack 'Lese Register h1A
- i2crbyte wert(28), Nack 'Lese Register h1B
- i2cstop
- waitms 500
- 'for i = 0 to &h28
- 'i2crbyte Wert(i) , ack
- 'next
- 'i2cstop
- print "QN8007 Register h00-h1F gelesen:"
- for i = 0 to 28
- print "Register h"; Hex(i) ; " Inhalt h"; Hex(Wert(i)); " b"; Bin(Wert(i))
- next
- return
Im Anhang ein Bild meiner Platine.
Hat da jemand nen Tip für mich was da im ATmega8 dazwischen funkt? Im Datenblatt habe ich nix gefunden bezüglich aktivierter Zweitfunktionen an diesen Ports.
Jürgen