2 x BMP085 on I2C

GD,
As I am planning a project for controlling different ( delta p) pressure measured by two bmp085 with a duamilanova328
I have a question. Can I connect two bmp085 pressure sensors on a i2c bus. Then using the XCLR line to read each time sensor 1 if XCLR is high and
read sensor 2 if XCLR is low done with a digital out?
This is what I understand from the data sheet. Is this correct?

Theo

Yes, if you use an inverter on the pin controlling the XCLR line. Each BMP085 is only "awake" if its XCLR line is high. If you set it low, it ignores the I2C data. So if you want two sensors, you can either use two digital pins to connect to each XCLR line, or one digital pin which connects directly to one XCLR line and connects to the other XCLR line through an inverter.

--
The QuadRAM shield: add 512 kilobytes of external RAM to your Arduino Mega/Mega2560

Best

RuggedCircuits

Thanks for your quick anser.
So I can order a second sensor and hope the project is working.

Kind regards,

Theo

Hi there,

I am trying to do the same thing with two bmp085 connected to my i2c bus and have run into issues. When either sensor is connected to the bus alone, the readings are correct; that is a temperature of 23 deg C and a pressure of 97210 Pa.

Next, with the same code but with both sensors connected to the bus, and with xclr lines connected to digital pins 6 and 7. I add the following code to my setup():

  pinMode(6, OUTPUT);
  digitalWrite(6, LOW);

The low digital 6 pin puts one of the sensors to sleep and the rest of the code runs as it did when only one sensor was physically connected; the temperature and pressure readings are the same as above.

IF however I add the following code:

  pinMode(6, OUTPUT);
  digitalWrite(6, LOW);
  pinMode(7, OUTPUT);
  digitalWrite(7, HIGH);

The 6 pin should keep putting one sensor to sleep whilst the 7 pin should tell the other to be awake. Whilst this is the case, the high pin 7 results in the sensor returning incorrect pressure data of 122246 Pa whilst the temperature is still around the correct 23 deg C!
It does not matter which of the sensors is high/low, the return pressure is always too high.

Could this be due to the fact that I am using the sparkfun breakout of the bmp085 which has the Vddd (digital power supply) connected to the Vdda (power supply) at 3.3v whilst the digital out pin provides 5v to the XCLR?
If so, what could I do to provide either XCLR line with 3.3v using my arduino's digital pins?

Regards,
periapsis

You could use a voltage divider on the 5V XCLR output pin to reduce it to 3.3V. For example 10k and 15k resistors (or 1k/1.5k).

Also note that when you "switch on" a BMP085 (i.e., bring its XCLR line from low to high) you should wait at least 10ms or so for it to come out of reset before attempting to get data from it.

--
The Ruggeduino: compatible with Arduino UNO, 24V operation, all I/O's fused and protected

Dear RuggedCircuits,

thank you for the prompt reply. It was in fact the lack of 10ms wait time after reset which caused the erroneous pressure. How embarassing a mistake for a first post! Ah well, may this thread serve as a reminder for anyone getting strange values after a XCLR reset.

Regards,
periapsis

Best,
RuggedCircuits and periapsis,

As time passes by I recieved the 2 nd sensor.
Unfortunately the both sensors are on two different breakout boards. one on the jeelab and one on the adafuit board.
The jeelab board has the xclr via a print copper line connected to the +Vcc. So I understand this must be cut to be able to connect it to a digital out put to make high for reading. And program a small waiting time. if change to the other sensor.
This is no problem and I do understand this.
But the next question is. On both boards the SDA and SCL are on both board connected to VCC with resistors. My question is as these lines are in paralel is one resistor on each line SDA and SCL enough?

Theo

One resistor is enough on each of SCL and SDA, as long as it is sized appropriately. If this resistor is too big then the rising and falling edges can be too slow and you may have communication errors. If too small, of course, it wastes too much current when SCL/SDA are low.

--
The Gadget Shield: accelerometer, RGB LED, IR transmit/receive, speaker, microphone, light sensor, potentiometer, pushbuttons

Best RuggedCircuits,

Thanks for your reply.
So now I will connect the both sensors par. on the power supply.
Only one time a resistor at the SCA and SCL. I think to adjust the voltage level on the bus.
The XSCL I will connect to a digital out put each sensor his onw output. To change from one sensor to the other sensor I will program some time.
As the sensor data is not realy time dependable this is no problem.

Thanks so far,

Theo

i have a same project,,to controlling different pressure,,but i still confuse,,can i get the sketch and example of connecting structure?
thx

hi
plz write source bascom for 2 sensor BMP085
this only 1 sensor
tnx

'--------------------------------------------------------------------------------

'--------------------------------------------------------------------------------

$regfile = "m8def.dat"
$crystal = 1000000
$baud = 1200
$hwstack = 32
$swstack = 10
$framesize = 40


Config Scl = Portc.5
Config Sda = Portc.4

Dim Ac1 As Integer
Dim Ac1a As Long
Dim Ac2 As Integer
Dim Ac3 As Integer
Dim Ac4 As Word
Dim Ac5 As Word
Dim Ac5a As Single
Dim Ac6 As Word
Dim B1 As Integer
Dim B2 As Integer
Dim B3 As Long
Dim B3a As Long
Dim B4 As Long
Dim B5 As Long
Dim B6 As Integer
Dim B6a As Long
Dim B7 As Long
Dim Mb As Integer
Dim Mc As Integer
Dim Mc2 As Long
Dim Md As Integer
Dim Adres As Byte
Dim Wert As Byte
Dim Ut As Long
Dim X1 As Long
Dim X1t As Single
Dim X2 As Long
Dim X3 As Long
Dim T As Single
Dim T2 As Long
Dim Temperatur As String * 6
Dim Luftdruck As String * 8
Dim Druck As Single

Dim P As Long
Dim P2 As Long
Dim 2potenz15 As Long
Dim 2potenz11 As Integer
Dim 2potenz13 As Integer
Dim 2potenz8 As Integer
Dim 2potenz4 As Integer
Dim 2potenz2 As Integer
Dim 2potenz16 As Long
Dim 2potenz12 As Integer
Dim Potenz5255 As Single
Dim Altitude As Single
Dim Altitudes As String * 8
Dim Msb As Long
Dim Lsb As Long
Dim Up As Long
Dim Druckvar As Byte
Declare Sub Berechne_temp
Declare Sub Berechne_druck
Declare Sub Schreibe_bmp085(byval Adres As Byte , Byval Wert As Byte)
Declare Sub Lese_bmp085(byval Adres As Byte , Wert As Byte)
Declare Sub Lese_roh_daten
Declare Sub Messen
Declare Sub Lese_kalib_data

Const Addr_schreiben = &B11101110
Const Addr_lesen = &B11101111


Call Lese_kalib_data

Do

Call Messen
T = T / 10
Temperatur = Fusing(t , "###.##")
Potenz5255 = 1 / 5.255
Altitude = P / 101325
Altitude = Altitude ^ Potenz5255
Altitude = 1 - Altitude
Altitude = Altitude * 44330
Druck = P
Druck = Druck / 100
Luftdruck = Fusing(druck , "####.##")
Altitudes = Fusing(altitude , "#####.##")


Print "Temp " ; Temperatur ; " C," ; " Pressure " ; Luftdruck ; " Pa," ; " Altitude " ; Altitudes ; " m."

Wait 1

Loop





Sub Messen

Call Schreibe_bmp085(&Hf4 , &H2E)
Adres = &HF6
Call Lese_roh_daten
'Print "msb " ; Msb
'Print "lsb " ; Lsb
Shift Msb , Left , 8
'Print "msb shift " ; Msb
Ut = Msb + Lsb
Call Berechne_temp



Call Schreibe_bmp085(&Hf4 , &H74 )
Adres = &HF6
Call Lese_roh_daten
Shift Msb , Left , 16
Shift Lsb , Left , 8
Up = Msb + Lsb
Shift Up , Right , 6
'Print "msb " ; Msb ; "lsb " ; Lsb ; "up " ; Up
Call Berechne_druck
End Sub


Sub Berechne_temp
'X1
Ut = Ut - Ac6
2potenz15 = 2 ^ 15
Ac5a = Ac5 / 2potenz15
X1t = Ut * Ac5a
'Print "X1 " ; X1t

'X2
2potenz11 = 2 ^ 11
Mc2 = Mc * 2potenz11
X3 = X1t + Md
X2 = Mc2 / X3
'Print "X2 " ; X2
'B5

B5 = X1t + X2
'Print "B5 " ; B5
'T
2potenz4 = 2 ^ 4
T2 = B5 + 8
T = T2 / 2potenz4



End Sub


Sub Berechne_druck
'B6
B6 = B5 - 4000
'X1
2potenz12 = 2 ^ 12
B6a = B6 * B6
B6a = B6a / 2potenz12
X1 = B2 * B6a
X1 = X1 / 2potenz11
'X2
X2 = Ac2 * B6
X2 = X2 / 2potenz11
'X3
X3 = X1 + X2
'B3
Ac1a = Ac1 * 4
Ac1a = Ac1a + X3
Shift Ac1a , Left , 2
Ac1a = Ac1a + 2
B3 = Ac1a / 4
'X1 die zweite
2potenz13 = 2 ^ 13
B6a = B6 / 2potenz13
X1 = Ac3 * B6a
'X2 die zweite
B6a = B6 * B6
B6a = B6a / 2potenz12
X2 = B1 * B6a
2potenz16 = 2 ^ 16
X2 = X2 / 2potenz16
'X3 die zweite
X3 = X1 + X2
X3 = X3 + 2
2potenz2 = 2 ^ 2
X3 = X3 / 2potenz2
'B4
B4 = X3 + 32768
B4 = B4 * Ac4
B4 = B4 / 2potenz15
If B4 <= 0 Then B4 = B4 * -1

'Print B4
'B7
B7 = Up - B3
B3a = 50000
Shift B3a , Right , 2                                       '
B7 = B7 * B3a
If B7 <= 0 Then B7 = B7 * -1

'Print B7
If B7 < &H80000000 Then
P = B7 * 2
'Print "p1 " ; P
P = P / B4
'Print "p1 " ; P
Else
P = B7 / B4
'Print "p2 " ; P
P = P * 2
'Print "p2 " ; P
End If

'Print P
'nochmal X1
2potenz8 = 2 ^ 8
P2 = P / 2potenz8
X1 = P2 * P2
'Print X1

X1 = X1 * 3038
X1 = X1 / 2potenz16
'Print X1

' nochmal X2
X2 = -7357 * P
X2 = X2 / 2potenz16

'Print X2
P2 = P
P = X2 + 3791
P = P + X1
P = P / 2potenz4
P = P + P2

End Sub


Sub Lese_kalib_data
Adres = &HAA
'Ac1 lesen
Call Lese_bmp085(adres , Wert)
Msb = Wert
Adres = Adres + 1
Call Lese_bmp085(adres , Wert)
Lsb = Wert
Shift Msb , Left , 8
Ac1 = Msb + Lsb

Adres = Adres + 1
'Ac2 lesen
Call Lese_bmp085(adres , Wert)
Msb = Wert
Adres = Adres + 1
Call Lese_bmp085(adres , Wert)
Lsb = Wert
Shift Msb , Left , 8
Ac2 = Msb + Lsb

Adres = Adres + 1
'Ac3 lesen
Call Lese_bmp085(adres , Wert)
Msb = Wert
Adres = Adres + 1
Call Lese_bmp085(adres , Wert)
Lsb = Wert
Shift Msb , Left , 8
Ac3 = Msb + Lsb

Adres = Adres + 1
'Ac4 lesen
Call Lese_bmp085(adres , Wert)
Msb = Wert
Adres = Adres + 1
Call Lese_bmp085(adres , Wert)
Lsb = Wert
Shift Msb , Left , 8
Ac4 = Msb + Lsb

Adres = Adres + 1
'Ac5 lesen
Call Lese_bmp085(adres , Wert)
Msb = Wert
Adres = Adres + 1
Call Lese_bmp085(adres , Wert)
Lsb = Wert
Shift Msb , Left , 8
Ac5 = Msb + Lsb

Adres = Adres + 1
'Ac6 lesen
Call Lese_bmp085(adres , Wert)
Msb = Wert
Adres = Adres + 1
Call Lese_bmp085(adres , Wert)
Lsb = Wert
Shift Msb , Left , 8
Ac6 = Msb + Lsb

Adres = Adres + 1
'B1 lesen
Call Lese_bmp085(adres , Wert)
Msb = Wert
Adres = Adres + 1
Call Lese_bmp085(adres , Wert)
Lsb = Wert
Shift Msb , Left , 8
B1 = Msb + Lsb

Adres = Adres + 1
'B2 lesen
Call Lese_bmp085(adres , Wert)
Msb = Wert
Adres = Adres + 1
Call Lese_bmp085(adres , Wert)
Lsb = Wert
Shift Msb , Left , 8
B2 = Msb + Lsb

Adres = Adres + 1
'MB lesen
Call Lese_bmp085(adres , Wert)
Msb = Wert
Adres = Adres + 1
Call Lese_bmp085(adres , Wert)
Lsb = Wert
Shift Msb , Left , 8
Mb = Msb + Lsb

Adres = Adres + 1
'MB lesen
Call Lese_bmp085(adres , Wert)
Msb = Wert
Adres = Adres + 1
Call Lese_bmp085(adres , Wert)
Lsb = Wert
Shift Msb , Left , 8
Mc = Msb + Lsb

Adres = Adres + 1
'Md lesen
Call Lese_bmp085(adres , Wert)
Msb = Wert
Adres = Adres + 1
Call Lese_bmp085(adres , Wert)
Lsb = Wert
Shift Msb , Left , 8
Md = Msb + Lsb

Adres = Adres + 1
End Sub




Sub Lese_roh_daten
Call Lese_bmp085(adres , Wert)
Msb = Wert
Adres = Adres + 1
Call Lese_bmp085(adres , Wert)
Lsb = Wert
End Sub

Sub Schreibe_bmp085(byval Adres As Byte , Byval Wert As Byte)
I2cstart
I2cwbyte Addr_schreiben
I2cwbyte Adres
I2cwbyte Wert
I2cstop
Waitms 10
End Sub


Sub Lese_bmp085(byval Adres As Byte , Wert As Byte)
I2cstart
I2cwbyte Addr_schreiben
I2cwbyte Adres
I2cstart
I2cwbyte Addr_lesen
I2crbyte Wert , Nack
I2cstop
Waitms 10
End Sub

I know, that the original quesiton is pretty out of date, but I found this page first, and I would like to contribute the solution for the next visitor. I was able to put two BMP085 on the same bus using the following technique:

BMP085 connects an internal pull-up to the XCLR pin. This is why you can leave it unconnected and it will work.
You need to pull it down in order to disable a device.

You can pull down in case the pin is OUTPUT and you write "LOW". How to leave it alone?

You should not pull it up with Arduion pin, because it might damage your BMP085 (XCLR will get +5 V directly). (I did it once, but fortunately it survived)

So how to do it?

Turn the pin into an INPUT. In this case both pull-up and down will be turned off (tri-state):

digitalWrite( pinNumber, LOW );
pinMode( pinNumber, OUTPUT ); // now we're sourcing current, i.e. GND
pinMode( pinNumber, INPUT ); // now we're tri-stated
pinMode( pinNumber, OUTPUT ); // and back again

Another important thing is already mentioned by a previous commenter:
The delay after XCLR. According to the specs, the sensor needs 10ms to start communication (and 1us to turn off)

Cheers,

T

ps. example is from: Tri-state logic on IO pins? - #3 by Cross - Interfacing - Arduino Forum