Push-pull/drenaje abierto; tirar hacia arriba/tirar hacia abajo

Estoy leyendo la ficha técnica de un chip ARM Cortex, concretamente el capítulo GPIO. En última instancia, quiero configurar varios pines GPIO para usarlos en el modo "Función alternativa" para acceso de lectura/escritura a SRAM.

De todos los registros GPIO disponibles, no entiendo dos: GPIO_PUPDRy GPIO_OTYPEcuáles son respectivamente el "registro pull-up/pull-down" y el "registro de tipo de salida".

Porque GPIO_PUPDRtengo tres opciones:

  • Sin pull-up o pull-down
  • Levantar
  • Derribar

Porque GPIO_0TYPEtengo dos opciones:

  • Salida push-pull
  • Salida de drenaje abierto

¿Cuál es la diferencia entre todas las diferentes configuraciones y cuál sería la más adecuada para la comunicación SRAM?

La documentación de la placa en la que estoy trabajando está disponible aquí (consulte la página 24 para ver los esquemas de SRAM). El manual de referencia para el chip ARM está disponible aquí (consulte las páginas 145 y 146 para los registros GPIO).

Respuestas (3)

Esta respuesta es general para procesadores y periféricos, y tiene un comentario específico de SRAM al final, que probablemente sea pertinente para su RAM y CPU específicos.

Los pines de salida se pueden controlar en tres modos diferentes:

  • drenaje abierto : un transistor se conecta a bajo y nada más
  • drenaje abierto, con pull-up : un transistor se conecta a bajo y una resistencia se conecta a alto
  • push-pull : un transistor se conecta a alto y un transistor se conecta a bajo (solo se opera uno a la vez)

Los pines de entrada pueden ser una entrada de puerta con un:

  • pull-up - una resistencia conectada a alta
  • pull-down - una resistencia conectada a baja
  • pull-up y pull-down : tanto una resistencia conectada a alto como una resistencia conectada a bajo (solo es útil en casos excepcionales).

También hay un modo de entrada activado por Schmitt donde el pin de entrada se tira con un pull-up débil a un estado inicial. Cuando se deja solo, persiste en su estado, pero puede ser llevado a un nuevo estado con un mínimo esfuerzo.

El drenaje abierto es útil cuando varias compuertas o pines están conectados entre sí con un pull-up (externo o interno). Si todos los pines están altos, todos son circuitos abiertos y el pull-up eleva los pines. Si algún pin está bajo, todos bajan cuando se unen. Esta configuración forma efectivamente una ANDpuerta.

_____________________________

Nota añadida en noviembre de 2019, más de 7 años después: la configuración de combinar múltiples salidas de drenaje/colector abierto se ha denominado tradicionalmente como una configuración de "O cableado". LLAMARLO OR (incluso tradicionalmente) no lo convierte en uno. Si usa la lógica negativa (que tradicionalmente puede haber sido el caso), las cosas serán diferentes, pero a continuación me ceñiré a la convención de lógica positiva, que es lo que se usa correctamente a menos que se indique específicamente.

El comentario anterior sobre la formación de una puerta 'Y' se ha cuestionado varias veces a lo largo de los años, y se ha sugerido que el resultado es 'realmente' una puerta 'O'. es complejo

La imagen simple es que si varias salidas de colector abierto están conectadas juntas, si cualquiera de los transistores de colector abierto está encendido, la salida común será baja. Para que la salida común sea alta, todas las salidas deben estar apagadas.

Si considera combinar 3 salidas, para que el resultado sea alto, las 3 deberían haber sido altas individualmente. 111 -> 1. Eso es un 'Y'.

Si considera cada una de las etapas de salida como un inversor, para que cada una tenga una salida alta, su entrada debe ser baja. Entonces, para obtener un alto rendimiento combinado, necesita tres 000 -> 1. Eso es un 'NOR'.

Algunos han sugerido que esto es un OR: cualquiera de XYZ con al menos 1 de estos es un 1 -> 1.
Realmente no puedo "forzar" esa idea en la situación.

_________________________________

Al conducir una SRAM, probablemente desee conducir las líneas de datos o las líneas de dirección hacia arriba o hacia abajo de la manera más sólida y rápida posible para que se necesite una unidad activa hacia arriba y hacia abajo, por lo que se indica push-pull. En algunos casos, con múltiples RAM, es posible que desee hacer algo inteligente y combinar líneas, donde otro modo puede ser más adecuado.

Con SRAM con entradas de datos desde SRAM, si el IC de RAM siempre está afirmando datos, entonces un pin sin pull-up probablemente esté bien, ya que la RAM siempre establece el nivel y esto minimiza la carga. Si las líneas de datos de la RAM a veces son de circuito abierto o triple estado, necesitará los pines de entrada para poder establecer su propio estado válido. En comunicaciones de muy alta velocidad, es posible que desee utilizar un pull-up y un pull-down para que la resistencia paralela efectiva sea la resistencia de terminación, y las dos resistencias establezcan el voltaje inactivo del bus, pero esto es algo especial.

Para que quede claro, ¿qué quiere decir con "un transistor que se conecta a bajo y nada más"? Un transistor tiene 3 pines. ¿Cómo se conecta cada pin?
@Randomblue - lo siento - colector de transistores o drenaje cuando actúa como salida
Para aclarar su respuesta sobre "bajar", ¿cuál es la diferencia entre "tierra", "bajo" y "-ve"?
Hice muchas modificaciones a su pregunta, ¿podría verificar que no haya cometido ningún error?
@Randomblue: las ediciones parecen ser buenas. Me hace preguntarme ¿qué escribí inicialmente? Parece que has dicho lo que creo que pensé :-).
Gran respuesta, Russell, realmente me ayudó. Sin embargo, en la configuración de drenaje abierto, cuando se enciende un transistor, ¿no es como tener una puerta OR?
@Dave No comenté sobre la funcionalidad lógica ya que está relacionada pero es periférica al tema principal aquí. | Es seguro decir que se pueden usar salidas de drenaje abierto, junto con otros componentes para implementar puertas OR. Un dispositivo de canal N de drenaje abierto con una resistencia a implementa un inversor. Dos de estos drenajes abiertos en común con una resistencia alta implementan una puerta NOR para lógica positiva (ya que 00 es el único estado que da salida alta. Para lógica negativa es una puerta NAND como baja = lógica_11, da salida alta = klogic_0. | SO - Se puede utilizar una compuerta de drenaje abierta para implementar una lógica de tipo RTL.
Lo siento, Russell, no estaba comentando cómo implementar la lógica con esta configuración. Cuando dijiste: "Si algún pin está bajo, todos bajan cuando se unen. Esta configuración forma efectivamente una puerta AND", pensé que era extraño porque para mí, eso describe el comportamiento OR. Probablemente estoy malinterpretando lo que está diciendo porque no sé cómo se implementan las puertas AND.
@Dave Ah -OK - Me perdí de haber dicho eso. Vamos a ver. Para lógica positiva y entrada = 1, enciende el transistor para que la salida = 0. Una dos drenajes como se indicó anteriormente. Luego in in out = 00 1, 10 0, 01 0, 11 0. Esta es una puerta NOR para lógica +ve o NAND para lógica negativa (como arriba). Entonces mi declaración fue descuidada y su declaración o mi declaración es "correcta" con suposiciones adecuadas . por ejemplo, la salida es alta si A Y B son ambos bajos. O La salida es baja si A O B son altos. Es una puerta de Fish & Fowl :-)
Yo arreglaría el comentario AND . No pensé que fuera correcto (todavía no lo creo...) en la primera lectura y creo que muchos otros podrían malinterpretar la declaración.
@RussellMcMahon ¿Qué pasa con la salida de "tótem" o es más bien una reliquia de los circuitos TTL?
@EugeniuRosca Sí, el tótem es una estructura de salida "algo diferente". La pregunta era específica de la situación del OP donde el tótem no era una opción. A efectos prácticos, el tótem y el push-pull son funcionalmente idénticos, excepto por las limitaciones basadas en TP cerca de los rieles debido a la arquitectura realmente extraña (en comparación con algo que podría hacer con componentes discretos) .
@theorifice 7 años después de mi respuesta y 3 años desde su comentario; consulte la nota agregada. No estoy de acuerdo contigo, y explica por qué. Una explicación del punto de vista opuesto sería genuinamente bienvenida.
Actualización de @Dave sobre nuestra discusión del 18 de junio: consulte la nota agregada sobre la discusión Y/O. Una explicación del punto de vista opuesto sería genuinamente bienvenida.
@RussellMcMahon Creo que lo que te estás perdiendo es que la "lógica negativa", es decir, activa-baja, es muy común. Si la documentación llama a algo un "o cableado", eso implica que es de drenaje abierto (o colector abierto, efectivamente lo mismo) activo bajo.
(Por cierto, una gran razón por la que haría que una señal en particular sea activa-baja es porque (1) querer un OR de señales es más común que querer un AND, y (2) usar un transistor para bajar una señal es un poco más barato/ más eficiente que usar un transistor para elevar una señal, al menos si está usando FET, debido a la asimetría entre P-FET y N-FET).
@GlennWillen Cuando comencé con la electrónica, casi podías comprar RTL y TTL era la nueva ola :-). es decir, no, no me lo estoy perdiendo, solo digo que durante la mayor parte de mi vida en electrónica no es a lo que la mayoría de la gente estaría acostumbrada. || Nivel de marcado RS232 = 1 = ¿qué polaridad? :-) (-12 o -15V típicamente). El bit de inicio se vuelve positivo +=0) luego .... . Dentro de los (generalmente) controladores inversores en (generalmente en ese entonces) los niveles TTL 0 eran <= +0.6V y 1 era +2.4-+5 (si la memoria antigua sirve). Así que sí, ambos tienen su lugar. Saber en qué lugar está uno trabajar con es un buen comienzo :-).
@GlennWillen Un pensamiento: tenga en cuenta lo que dije anteriormente sobre lo que constituyeron entradas y salidas para que un OR sea la respuesta correcta. Usando H para alto y L para bajo. Si L=1 y H=0 entonces: - Por ejemplo, dos dispositivos (transistores oc o lo que sea) que tienen LH HL o LL dan L es un OR con lógica negativa. Y/PERO si está manejando 2 transistores NPN, digamos con colectores abiertos o dos puertas inversoras. LL HL LH HH dará HLLL = para lógica negativa 11 01 10 00 da 0 1 1 1 que es AND . ...
| Como uno generalmente mira la entrada a las puertas o etapas o transistores (o FETS) al decidir cuál es la función lógica de entrada/salida Y es mejor que O a menos que use (y explique) el caso especial y la perspectiva involucrada. || No solo estoy tratando de ser malhumorado o de "siempre tener la razón" (es bueno cuando uno puede manejarlo :-)). - Realmente lo veo como se describe y, aunque tradicionalmente esto es "cableado O", realmente no parece tener sentido llamarlo así, con cualquier polaridad lógica, excepto cuando toma el caso especial, como arriba.
El punto de "cableado-OR" es que si toma dos (o más) salidas de drenaje abierto y las conecta directamente sin otras puertas en el medio, si L es 0V y H es VCC, entonces LL HL LH HH le da LLLH , porque el pull-up hará que la línea suba si y solo si ninguna de las salidas la está bajando. Es por eso que Active-Low Open-Drain se llama Wired-OR. (No puedo decir si por "lógica negativa" te refieres a un sistema donde la tierra es 0 y el voltaje negativo es 1; el sistema que estoy describiendo es uno en el que la tierra es 1 y el voltaje positivo es 0, como lo encontrarías en un sistema TTL para una señal baja activa).
@GlennWillen Sí. Como se señaló anteriormente, estoy al tanto del PUNTO de OR cableado y por qué se usa y qué hace. Lo que describes es un subconjunto de lo que dije anteriormente. Es un O si toma las SALIDAS de las puertas individuales y las compara con el resultado, lo que tiene bastante sentido PERO es casi único como una forma de hacer las cosas. Efectivamente, la puerta OR de lógica negativa (baja = verdadera) se forma a partir de los cables que unen las múltiples salidas. (La única resistencia que comparten es solo la combinación en paralelo de las múltiples resistencias presentes antes de la combinación).

Encontré esta respuesta de STM32 Comprender la configuración de GPIO

  • GPIO_PuPd (Pull-up / Pull-down)

En los circuitos digitales, es importante que nunca se permita que las líneas de señal "floten". Es decir, necesitan estar siempre en un estado alto o bajo. Cuando flota, el estado es indeterminado y causa algunos tipos diferentes de problemas.

La forma de corregir esto es agregar una resistencia desde la línea de señal a Vcc o Gnd. De esa manera, si la línea no está siendo impulsada activamente hacia arriba o hacia abajo, la resistencia hará que el potencial se desvíe a un nivel conocido.

El ARM (y otros microcontroladores) tienen circuitos incorporados para hacer esto. De esa manera, no necesita agregar otra parte a su circuito. Si elige "GPIO_PuPd_UP", por ejemplo, es equivalente a agregar una resistencia entre la línea de señal y Vcc.

  • GPIO_OType (Tipo de salida):

Push-Pull: este es el tipo de salida que la mayoría de la gente considera "estándar". Cuando la salida baja, se "tira" activamente a tierra. Por el contrario, cuando la salida se establece en alta, se "empuja" activamente hacia Vcc. Simplificado, se ve así:ingrese la descripción de la imagen aquí

Una salida de drenaje abierto, por otro lado, solo está activa en una dirección. Puede tirar del pasador hacia el suelo, pero no puede llevarlo alto. Imagina la imagen anterior, pero sin el MOSFET superior. Cuando no está tirando a tierra, el MOSFET (lado inferior) simplemente no es conductor, lo que hace que la salida flote.

Para este tipo de salida, se debe agregar una resistencia pull-up al circuito, lo que hará que la línea suba cuando no esté baja. Puede hacer esto con una parte externa o configurando el valor GPIO_PuPd en GPIO_PuPd_UP.

El nombre proviene del hecho de que el drenaje del MOSFET no está conectado internamente a nada. Este tipo de salida también se denomina "colector abierto" cuando se usa un BJT en lugar de un MOSFET.

  • GPIO_Velocidad

Básicamente, esto controla la velocidad de respuesta (el tiempo de subida y el tiempo de caída) de la señal de salida. Cuanto más rápida sea la velocidad de respuesta, más ruido se irradia desde el circuito. Es una buena práctica mantener la velocidad de respuesta lenta y solo aumentarla si tiene una razón específica.

Un pequeño detalle más: para los microcontroladores que no tienen un modo de "drenaje abierto" explícito, como AVR y placas basadas en Arduino ATmega328 como el Uno, este modo de "drenaje abierto" se puede simular escribiendo una función contenedora que simplemente establece un pin en "Salida BAJA" cuando lo envía 0y que configura el pin como "Entrada BAJA" (modo de alta impedancia, resistencia pullup interna NO activada) cuando lo envía 1. De esta manera se obtiene el mismo efecto. Estos modernos microcontroladores ARM-core de 32 bits tienen muchas más opciones, eso es todo.

Además, la página 146 del Manual de referencia de STM32 vinculado a lo anterior establece lo siguiente [mis adiciones están entre corchetes] :

– Modo de drenaje abierto: un “0” en el registro de salida activa el N-MOS [por lo tanto, impulsa activamente BAJO conectando el pin a GND] mientras que un “1” en el registro de salida deja el puerto en Hi-Z (el P- MOS nunca se activa) [modo de alta impedancia, igual que una entrada flotante sin resistencias pull-up o pull-down]

– Modo push-pull: un "0" en el registro de salida activa el N-MOS [controla activamente el nivel BAJO al conectar el pin a GND] mientras que un "1" en el registro de salida activa el P-MOS [controla activamente el nivel ALTO al conectar el pin a VCC]


En el código Arduino, esa "función contenedora" podría implementarse así:

digitalWriteOpenDrain(byte pin, bool state)
{
    // Actively drive LOW
    if (state==LOW)
    {
        pinMode(pin, OUTPUT);
        digitalWrite(pin, LOW);
    }
    // High impedance mode 
    // (note that an internal or external pull-up resistor can optionally be added if you like, according to your requirements)
    else //state==HIGH
    {
        pinMode(pin, INPUT);
        digitalWrite(pin, LOW);
    }
}

O simplificado:

digitalWriteOpenDrain(byte pin, bool state)
{
    digitalWrite(pin, LOW);

    // Actively drive LOW
    if (state==LOW)
    {
        pinMode(pin, OUTPUT);
    }
    // High impedance mode
    // (note that an internal or external pull-up resistor can optionally be added if you like, according to your requirements)
    else //state==HIGH
    {
        pinMode(pin, INPUT);
    }
}

Tenga en cuenta que para encender la resistencia pullup interna en un Arduino puede hacer:

pinMode(pin, INPUT_PULLUP);

O (lo mismo):

pinMode(pin, INPUT);
digitalWrite(pin, HIGH);

Lectura adicional: