0
\$\begingroup\$

I need to use a tri-state buffer on a I2C bus and I have lots of 74125 (uni-directional tri-state buffers), so I'm wondering if is possible to connect two buffers back-to-back to make a bi-directional buffer.

Something like this: schematic http://www.tiago.eti.br/storage/buffer.png

Does it work?

\$\endgroup\$
  • 3
    \$\begingroup\$ I think you need separate enables for the two directions, do you not? \$\endgroup\$ – supercat Jul 16 '13 at 14:51
  • 1
    \$\begingroup\$ I2C is an open drain bus, why are you using tristate buffers for it in the first place? You're going to blow the arse out of the PMOS in the output stages sooner or later... \$\endgroup\$ – ThreePhaseEel Oct 30 '16 at 0:53
4
\$\begingroup\$

In general, it is possible and quite common to use back-to-back three-state buffers for bidirectional bridging. Such bridges, however, need something to tell them when they should conduct in each direction. For example, in many microprocessor systems, the processor will sit on a local data bus along with its memory, and that will be connected to a system data bus through such a bidirectional bridge consisting of back-to-back three-state buffers (the most commonly-used chips for such purpose would have 8 back-to-back pairs of 3-state drivers, but it would be possible to use chips with unidirectional 3-state drivers and wire them back to back). When the processor wants to write data to the external bus, the drivers are enabled in one direction. When it wants to read data, they are enabled in the other direction.

Such devices work very well in situations like microprocessor buses where there are pre-existing signals that specify which direction they should operate. They will not be sufficient for something like a full I2C implementation, in which the direction of of the clock wire may reverse without any transitions on it. To clarify, a data read or slave-acknowledge clock cycle on I2C behaves as follows:

  • Master asserts SCK (drives it low)
  • Slave sees SCK asserted, and starts driving it low as well
  • Slave determines whether it should assert or release SDA (may be instantaneous, or could take hundreds of microseconds)
  • Slave asserts or releases SDA as appropriate, and releases SCK
  • Master sees SCK released and processes data on SDA

It is imperative that the slave's SCK wire not be released until the master decides to release it, and also that the master's SCK wire not be released until the slave decides to release it. It is not possible to accomplish this with conventional logic, since there would be no way of knowing whether either side had released SCK without releasing SCK to that side. Philips in their I2C bridging chips gets around this by using chips that process multiple logic levels. Essentially, what happens is that when the SCK wire on either side is driven "hard" low, the SCK wire on the other side will be driven low, but somewhat less strongly. Strongly enough that attached devices will see the signal as a low, but weakly enough to be distinguished from an externally-driven strong low.

Note that in scenarios involving a single master and not using clock-based handshaking, it may be possible to build an I2C bridge using only conventional logic levels, since the direction of the SDA wire would be well defined at all times, but keeping track of the I2C communication state would be sufficiently complicated that using an I2C bridge chip would probably be easier.

\$\endgroup\$
2
\$\begingroup\$

I2C is an open-colletor / open-drain bus. Your drivers are push-pull, so that would not combine nicely.

But most important: where would you get the enable signal from? It would have to switch at exactly the right moment possibly (clock stretching) even while a single bit is transferred!

In practice: no, this will not work.

\$\endgroup\$
  • \$\begingroup\$ I have 4 I2C sensors in a I2C bus, and in my tests if one sensor fail it mess all the bus up making impossible to communicate with the others sensors, so the master of the bus enable/disable each sensor before sending/reading data. \$\endgroup\$ – Tiago Queiroz Jul 16 '13 at 13:17
  • \$\begingroup\$ Interesting, but that does not give you an enable signal that switches the (active) i2c lines at exactly the right moment. \$\endgroup\$ – Wouter van Ooijen Jul 16 '13 at 13:31
0
\$\begingroup\$

It is possible in general. However

  1. Your schematic has enable to both. You need two signals, one for each buffer's tri-state pin. Or find a buffer that has active-high output enable so the same signal turns one or the other off.
  2. You need to be careful with turn on and turn off. You should disable the buffer before another signal drives it. For example U1:B must be off before the Device drives a signal out.
\$\endgroup\$
0
\$\begingroup\$

Your real problem is your sensors failing and hanging SCL and/or SDA low, causing the bus to stop functioning. This is generally handled through dedicated repeater or multiplexer chips such as the LTC4307 that have internal timeout logic to detect the stuck bus state and disconnect the recalcitrant device, allowing the master to regain control of the bus.

\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.