I2C und Bascom

OP #2449311
Lesenswert?

Hi,

ich habe hier einen ATMega8, 16MHz Resonator, programmiert mit bewährtem 
Script für AVR-Dude.
LED, serielle Verbindung über Max202 an PC, alles funzt.
Nun will ich mit einem Gyro per I2C sprechen und mein erster Gehversuch 
mit I2C geht voll daneben.
Der Gyro ist ein Modul MinIMU-9 (L3G4200D and LSM303DLH Carrier) von 
Pololu.

Im Programm ist sonst kein Timer oder Interrupt aktiv.

Es geht alles bis in die Gosub write_byte, "i2c start" wird noch 
gesendet und dann ist schluss. Die LED bleibt an und "slaveadr" kommt 
nicht.
Klemme ich den Gyro ab (also SCL und SDA offen am Mega8) läuft es durch.
Was zum Teufel kann man da so dermassen falsch machen?
Ich mein, von mir aus stimmt was mit der Adresse nicht aber daß der 
Mega8 dann dort hängenbleibt?
1
$regfile = "M8DEF.DAT"
2

3
$hwstack = 200
4
$swstack = 32
5
$framesize = 64
6

7
$lib "i2c.lib"
8

9
$crystal = 16000000
10

11
Config Scl = Portb.4                                        'AtMega8 PDip Pin27
12
Config Sda = Portb.5                                        'AtMega8 PDip Pin28
13
I2cinit
14

15
$baud = 19200                                               'RX Pin2, TX Pin3
16

17
Ddrb.0 = 1
18
Led Alias Portb.0
19

20
Const Ctrl_reg1 = &H20
21
Const Ctrl_reg4 = &H23
22
Const Gyroadress = &HD2                                     'Gyro slave adress for write
23

24
Dim Slaveadress As Byte                                     'Adress of the slave to read or write
25
Dim Subadress As Byte                                       'the register to read or write
26
Dim Databyte As Byte                                        'Byte to read or write
27

28
'###############################################
29
Print "Gyro-test"
30
Led = 1
31
Wait 1
32
Led = 0
33

34
Waitms 100
35
Gosub Init_gyro
36

37
End
38

39
Init_gyro:
40
   Print "init-G-start"
41
   Slaveadress = Gyroadress
42
   Subadress = Ctrl_reg1
43
   Databyte = &B10001111                                    'Enable all, ODR 400kHz, LPF1 cut off 78Hz
44
   Gosub Write_byte
45
   Print "init-G-first"
46
   Slaveadress = Gyroadress
47
   Subadress = Ctrl_reg4
48
   Databyte = &B10000000                                    'Block Data Update, LSB low, Scale 250 dps
49
   Gosub Write_byte
50
   Print "init-G-finish"
51
Return
52

53
Write_byte:
54
   Print "start write"                                      'needs Slaveadress, Subadress and Databyte
55
   Led = 1
56
   Shift Slaveadress , Left                                 '8-Bit with LSB = 0, write
57
   I2cstart
58
   Print "i2c start"
59
   I2cwbyte Slaveadress
60
   Led = 0
61
   Print "slaveadr"
62
   I2cwbyte Subadress
63
    Print "subadr"
64
   I2cwbyte Databyte
65
   I2cstop
66
Return

Für sachdienliche Hinweise wäre ich dankbar.

Gruß,
Norbert
Gast #2449375
Lesenswert?

Norbert S. schrieb:
> Config Scl = Portb.4                                        'AtMega8 PDip Pin27
> Config Sda = Portb.5                                        'AtMega8 PDip Pin28

Da kollidiert die Beschreibung mit der Realität. An Pin 27/28 liegt 
PC4/5 und die HW-I2C Schnittstelle. PB4/5 geht für SW-I2C, auch die 
eingebundene Lib deutet darauf hin. Über Config I2CDelay sollte dann die 
Geschwindigkeit der Soft-I2C eingestellt werden. Es müssen externe 
Pullup-Widerstände dran, Soft-I2C geht nicht mit den internen Pullups 
des µCs.
OP #2549274
Lesenswert?

Hi,

ich bin angeschrieben worden ob ich den Code zum Lesen der Sensoren 
rausrücken würde - hier ist er:
1
'##### 7- Bit Adresses Gyro ########
2
Const Who_am_i = &H0F
3
Const Ctrl_reg1 = &H20
4
Const Ctrl_reg2 = &H21
5
Const Ctrl_reg3 = &H22
6
Const Ctrl_reg4 = &H23
7
Const Ctrl_reg5 = &H24
8
Const Out_temp = &H26
9
Const Status_reg = &H27
10
Const Out_x_l = &H28
11
Const Out_x_h = &H29
12
Const Out_y_l = &H2A
13
Const Out_y_h = &H2B
14
Const Out_z_l = &H2C
15
Const Out_z_h = &H2D
16
'##### 7-Bit Adresses Acc ########
17
Const Ctrl_reg1_a = &H20
18
Const Ctrl_reg2_a = &H21
19
Const Ctrl_reg3_a = &H22
20
Const Ctrl_reg4_a = &H23
21
Const Ctrl_reg5_a = &H24
22
Const Status_reg_a = &H27
23
Const Out_x_l_a = &H28
24
Const Out_x_h_a = &H29
25
Const Out_y_l_a = &H2A
26
Const Out_y_h_a = &H2B
27
Const Out_z_l_a = &H2C
28
Const Out_z_h_a = &H2D
29
'##### 7-Bit Adresses Mag ########
30
Const Cra_reg_m = &H00
31
Const Crb_reg_m = &H01
32
Const Mr_reg_m = &H02
33
Const Out_x_h_m = &H03
34

35
Const Gyroadress = &HD2                                     'Gyro slave adress for write
36
Const Accadress = &H30                                      'Acc slave adress for write
37
Const Magadress = &H3C                                      'Mag slave adress for write
38

39
Get_g_a_data:
40
   Slaveadress = Gyroadress
41
   Subadress = Out_x_l
42
   Gosub Read_6
43

44
   Xgyro = Dataarray(2)
45
   Shift Xgyro , Left , 8
46
   Xgyro = Xgyro + Dataarray(1)
47

48
   Ygyro = Dataarray(4)
49
   Shift Ygyro , Left , 8
50
   Ygyro = Ygyro + Dataarray(3)
51

52
   Zgyro = Dataarray(6)
53
   Shift Zgyro , Left , 8
54
   Zgyro = Zgyro + Dataarray(5)
55

56
   Slaveadress = Accadress
57
   Subadress = Out_x_l_a
58
   Gosub Read_6
59

60
   Xacc = Dataarray(2)
61
   Shift Xacc , Left , 8
62
   Xacc = Xacc + Dataarray(1)
63

64
   Yacc = Dataarray(4)
65
   Shift Yacc , Left , 8
66
   Yacc = Yacc + Dataarray(3)
67

68
   Zacc = Dataarray(6)
69
   Shift Zacc , Left , 8
70
   Zacc = Zacc + Dataarray(5)
71

72
   Xgyro = Xgyro - Xgyrooff
73
   Ygyro = Ygyro - Ygyrooff
74
   Zgyro = Zgyro - Zgyrooff
75
   Xacc = Xacc - Xaccoff
76
   Yacc = Yacc - Yaccoff
77
   Zacc = Zacc - Zaccoff
78
Return
79

80
Get_mag_data:
81
   Slaveadress = Magadress
82
   Subadress = Out_x_h_m
83
   Gosub Read_6_mag
84

85
   Xmag = Dataarray(1)
86
   Shift Xmag , Left , 8
87
   Xmag = Xmag + Dataarray(2)
88

89
   Ymag = Dataarray(3)
90
   Shift Ymag , Left , 8
91
   Ymag = Ymag + Dataarray(4)
92

93
   Zmag = Dataarray(5)
94
   Shift Zmag , Left , 8
95
   Zmag = Zmag + Dataarray(6)
96

97
   Xmag = Xmag - Xmagoff
98
   Ymag = Ymag - Ymagoff
99
Return
100

101
Init_gyro:
102
   Slaveadress = Gyroadress
103
   Subadress = Ctrl_reg1
104
   Databyte = &B10001111                                    'Enable all, ODR 400kHz, LPF1 cut off 78Hz
105
   Gosub Write_byte
106

107
   Slaveadress = Gyroadress
108
   Subadress = Ctrl_reg4
109
   Databyte = &B10000000                                    'Block Data Update, LSB low, Scale 250 dps
110
   Gosub Write_byte
111
Return
112

113
Init_acc:
114
   Slaveadress = Accadress
115
   Subadress = Ctrl_reg1_a
116
   Databyte = &B00101111                                    'normal power, 100Hz, 74Hz LPF
117
   Gosub Write_byte
118

119
   Slaveadress = Accadress
120
   Subadress = Ctrl_reg4_a
121
   Databyte = &B10000000                                    'Block Data Update, LSB low, Scale +-2g
122
   Gosub Write_byte
123
Return
124

125
Init_mag:
126
   Slaveadress = Magadress
127
   Subadress = Cra_reg_m
128
   Databyte = &B00011000                                    '75Hz Output
129
   Gosub Write_byte
130

131
   Slaveadress = Magadress
132
   Subadress = Crb_reg_m
133
   Databyte = &B01000000                                    'range +-1.9Gauss
134
   Gosub Write_byte
135

136
   Slaveadress = Magadress
137
   Subadress = Mr_reg_m
138
   Databyte = &B00000000                                    'continious mode
139
   Gosub Write_byte
140
Return
141

142
Write_byte:                                                 'needs Slaveadress, Subadress and Databyte
143
   I2cstart
144
   I2cwbyte Slaveadress
145
   I2cwbyte Subadress
146
   I2cwbyte Databyte
147
   I2cstop
148
Return
149

150
Read_byte:                                                  'needs Slaveadress, Subadress and gives Databyte
151
   I2cstart
152
   I2cwbyte Slaveadress
153
   I2cwbyte Subadress
154
   Incr Slaveadress                                         'for reading LSB=1
155
   I2crepstart
156
   I2cwbyte Slaveadress
157
   I2crbyte Databyte , Nack
158
   I2cstop
159
Return
160

161
Read_6:
162
   Subadress.7 = 1                                          'Set MSB for multiple reading
163
   I2cstart
164
   I2cwbyte Slaveadress                                     'SAD+W
165
   I2cwbyte Subadress
166
   Incr Slaveadress                                         'for reading LSB=1
167
   I2crepstart
168
   I2cwbyte Slaveadress                                     'SAD+R
169
   For J = 1 To 5
170
      I2crbyte Dataarray(j) , Ack
171
   Next
172
   I2crbyte Dataarray(6) , Nack
173
   I2cstop
174
Return
175

176
Read_6_mag:
177
   I2cstart
178
   I2cwbyte Slaveadress                                     'SAD+W
179
   I2cwbyte Subadress
180
   Incr Slaveadress                                         'for reading LSB=1
181
   I2crepstart
182
   I2cwbyte Slaveadress                                     'SAD+R
183
   For J = 1 To 5
184
      I2crbyte Dataarray(j) , Ack
185
   Next
186
   I2crbyte Dataarray(6) , Nack
187
   I2cstop
188
Return

Gruß,
Norbert
OP #3953050
Lesenswert?

Hi,

das hatte ich in dem kopierten Code vergessen.

$lib "i2c_twi.lbx"
Config Twi = 400000
Config Scl = Portc.0
Config Sda = Portc.1
I2cinit

Das sind die Hardware I2C Pins eines ATMega324, nicht wie oben noch ein 
Mega8.

Das oben sind drei verschiedene Sensoren, wobei zwei davon im gleichen 
Gehäuse sind.

Gruß,
Norbert

Antwort schreiben

Bitte melde dich an, um einen Beitrag zu schreiben.

oder

Mit Google-Account einloggen

Die Registrierung ist kostenlos und dauert nur eine Minute.

Jetzt registrieren