MSP430f23x0 + SHT21 und I2C

Gast #2118989
Lesenswert?

Hallo,

ich versuche mit Hilfe eines MSP430f2370 einen Temperatur- und 
Feuchtigkeitssensor (SHT21 von Sensirion) auszulesen.
Das komische ist das mal eine I2C-Kommunikation stattfindet und ein 
anderes mal funktionierts wieder nicht. Der Fehler lässt sich auch nicht 
reproduzieren. Nach langem hin und her rätseln/versuchen wollte ich euch 
mal fragen ob ihr durch Zufall einen Fehler im Code entdeckt.

10k Ohm PullUps sind an SDA und SCL dran.

PS: Da der Code noch in der Entwurfsphase ist, schaut er an manchen 
Stellen noch etwas komisch aus.

Ich danke schon mal für jeden kleinen Hinweis.

1
#include  "msp430x23x0.h"
2

3

4
//Funktionsdeklaration
5
void warte_ms(unsigned int i);
6
void ausgeben(unsigned char c[], unsigned char len);
7
void Reset();
8
void I2C_schreiben_byte(unsigned char cmd);
9
void I2C_lesen();
10

11
int main(void)
12
{
13
  
14
  unsigned char Ende[2]="00";
15
  unsigned char Test[5]="TEST-";
16
  int a=0;
17

18
// ---Initialisierung-Start---
19
  WDTCTL = WDTPW + WDTHOLD;  // Watchdog aus
20
  BCSCTL3 = XCAP1;      // Clock
21

22
  P4DIR = BIT5;               // P4.5 als Ausgang
23

24
// UART init
25
  UCA0CTL1 = UCSWRST;
26
  UCA0CTL1 |= UCSSEL0;                       // UCLK = ACLK
27
  UCA0BR0 = 0x03;                            // 32k/2400 - 13.65
28
  UCA0BR1 = 0x00;
29
  UCA0MCTL = 0x06;                           // Modulation
30
  P3SEL |= 0x30;  
31
  P3DIR |= 0x10;
32
  P3OUT |= 0x10;
33
  UCA0CTL1 &= ~(UCSWRST);                    // Initalize USART state machine
34

35
// I2C init
36
  P3SEL |= 0x06;                            // Assign I2C pins to USCI_B0
37
  UCB0CTL1 |= UCSWRST;                      // Enable SW reset
38
  UCB0CTL0 = UCMST + UCMODE_3 + UCSYNC;     // I2C Master, synchronous mode
39
  UCB0CTL1 = UCSSEL_2 + UCSWRST;            // Use SMCLK, keep SW reset  
40
  UCB0BR0 = 12;                             // fSCL = ACLK/12 = ~100kHz
41
  UCB0BR1 = 0;
42
  UCB0I2CSA = 0x40;                         // Set slave address
43
  UCB0CTL1 &= ~UCSWRST;                     // Clear SW reset, resume operation
44
 
45
// TIMER init
46
  TACCTL0 = CCIE;
47
  TACTL = TASSEL0 + ID0 + ID1;
48

49
  _BIS_SR(GIE);              // Interrupts ein
50
// ---Initialisierung-Ende---
51

52
for (a=0;a<20000;a++)            // Delay fuer Hardwarekonfigurierung
53
{;}
54

55
Ende[0] = '\r';
56
Ende[1] = '\n';
57

58
//ausgeben(Test,5);
59

60
//Reset();
61
//warte_ms(20);  
62
//
63
//ausgeben(Test,5);
64

65
  while(1)  // Hauptschleife
66
  {
67
//    ausgeben(Test,5);
68
    
69
    P4OUT &= ~BIT5;        // gelbe LED an
70
//    I2C_schreiben_byte(0xF3);  // Temp noHOLD-MASTER
71
    I2C_schreiben_byte(0xE3);  // Temp HOLD-MASTER
72
    I2C_lesen();
73
    P4OUT |= BIT5;        // gelbe LED aus
74
    
75
//    ausgeben(Test,5);
76
    
77
    warte_ms(50);
78
    
79
    P4OUT &= ~BIT5;        // gelbe LED an
80
//    I2C_schreiben_byte(0xF5);  // RH noHold-Master
81
    I2C_schreiben_byte(0xE5);  // RH Hold-Master  
82
    I2C_lesen();
83
    P4OUT |= BIT5;        // gelbe LED aus
84
    
85
    ausgeben(Ende,2);
86

87
  }
88

89
}
90

91
#pragma vector = TIMERA0_VECTOR    // ISR-TIMERA0
92
__interrupt void Timer_A (void)
93
{
94
  TACTL &= ~(MC0);
95
  TAR=0;
96
  TAIV = 0;
97
  LPM0_EXIT;                // Exit LPM0 um mit Programmausführung fortzufahren
98
}
99

100
//---------------------------------------------------------------------------------
101
// ausgelagerte Funktionen
102

103
void warte_ms(unsigned int i)
104
{
105
  if(i>=4)
106
  {
107
  TACCR0 = (i<<2);
108
  TACTL |= MC0;
109
  _BIS_SR(LPM0);
110
  }
111
  else
112
  {
113
    TACCR0 = (4<<2);
114
    TACTL |= MC0;
115
    _BIS_SR(LPM0);
116
  }
117
}
118

119
void ausgeben(unsigned char c[], unsigned char len)
120
{
121
  unsigned char i=0;
122
  while(i<len)
123
  {
124
    while (!(IFG2 & UCA0TXIFG));  // USART0 TX buffer ready?
125
      UCA0TXBUF = c[i];
126
    i++;
127
    while(UCBUSY & UCA0STAT);
128
  }
129
}
130

131
void Reset()  // Sensor Reset
132
{
133
  UCB0I2CSA = 0x40;                   // Slave Address 
134
  UCB0CTL1 |= UCTR + UCTXSTT;         // I2C TX, Start senden
135
  UCB0TXBUF = 0xFE;
136
  
137
  while((UCB0CTL1 & UCTXSTT) && !(UCB0STAT & UCNACKIFG));      // Warten bis Start und Adresse gesendet  
138

139
  UCB0CTL1 |= UCTXSTP;              // Stop senden
140
  while(UCB0CTL1 & UCTXSTP);          // Warten bis Stop gesendet  
141
}
142

143
void I2C_schreiben_byte(unsigned char cmd)
144
{
145

146
  UCB0I2CSA = 0x40;                   // Slave Address 
147
  UCB0CTL1 |= UCTR + UCTXSTT;         // I2C TX, Start senden
148
  UCB0TXBUF = cmd;
149
  
150
  while((UCB0CTL1 & UCTXSTT) && !(UCB0STAT & UCNACKIFG));      // Warten bis Start und Adresse gesendet  
151
  
152
  // Kein stop senden
153
}
154

155
// Temperatur oder RH lesen
156
void I2C_lesen()
157
{
158
  unsigned int i=0;
159
  unsigned char j=0;
160
  unsigned char Daten[3] = "000";
161
  
162
  UCB0I2CSA = 0x40;                    // Slave Address 
163
  
164
  UCB0CTL1 &=~UCTR;                   // I2C RX
165
  UCB0CTL1 |= UCTXSTT;                // Start senden
166
  while((UCB0CTL1 & UCTXSTT) && !(UCB0STAT & UCNACKIFG));      // Warten bis Start und Adresse gesendet  
167
  
168
  for (i=0; i<3; i++)
169
  {
170
      while (!(IFG2 & UCB0RXIFG));      // Buffer bereit?
171
//    Daten[i] = UCB0RXBUF;
172
     
173
      if(i==0)            // erstmal ohne Schleifenindex + Array-Index
174
      {Daten[0] = UCB0RXBUF;}
175
      if(i==1)
176
      {Daten[1] = UCB0RXBUF;
177
      UCB0CTL1 |= UCTXSTP;    // beim vorletzten Byte stop senden
178
      }
179
      if(i==2)
180
      {Daten[2] = UCB0RXBUF;}
181
   }
182
  
183
//  UCB0CTL1 |= UCTXSTP;            // Stop senden
184
  while(UCB0CTL1 & UCTXSTP);                    // Warten bis Stop gesendet
185
  
186
  // gleich Daten uebertragen
187
  while(j<3)
188
  {
189
    while (!(IFG2 & UCA0TXIFG));  // USART0 TX buffer ready?
190
      UCA0TXBUF = Daten[j];
191
    j++;
192
    while(UCBUSY & UCA0STAT);
193
  }
194
  
195
//  IFG2 &= ~UCB0RXIFG;    // Clear receive interruptflag
196
}

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