En Arduino Uno, noté que cuando configuro un PIN para la salida, el estado inicial predeterminado es bajo. ¿Hay alguna manera de establecer el estado de salida inicial en alto?
La documentación de pinmode solo admite input
, input_pullup
y output
. Me gustaría que hubiera una opción para output_pullup
. Si coloco una resistencia pull-up externa de 10k Ohm alrededor del PIN de salida, ayuda un poco a empujar el estado inicial hacia lo alto.
Aún así, si hay una solución basada en software (es decir, flashear el Arduino Uno para que la salida predeterminada sea alta), sería muy apreciada.
No hay nada que le impida escribir los registros de salida (PORTx) antes de escribir los registros de dirección (DDRx). Desafortunadamente, las funciones de la biblioteca Arduino ( pinMode
y digitalWrite
) tienen una serie de efectos secundarios y pueden o no funcionar. (Quizás alguien más familiarizado que yo con las bibliotecas de Arduino pueda aconsejarme si un digitalWrite
seguido de un pinMode
funcionará.
Por lo tanto, la manipulación directa del registro puede lograr lo que desea, si la solución de @Tom es insuficiente (la solución de Tom debería funcionar en casi todos los casos). Primero, consulte la página 77 de la hoja de datos del ATmega328 y observe la tabla 14-1.
Suponiendo que un pin comience con los bits DDR y PORT limpios: es un pin de entrada Hi-z. Establezca el bit PORT, el pin ahora es una entrada con un pullup. Ahora, cuando configura el bit DDR, el pin pasa de una entrada con pullup directamente a una salida alta.
Editar: tratando de comprender mejor lo que sucedería con el siguiente código leyendo wiring_digital.c
:
// where p is an Arduino pin, x is the corresponding port,
// and n is the corresponding bit
// pin starts with DDRxn == 0, PORTxn == 0
digitalWrite(PINp, HIGH);
// PORTx |= 1<<n, from line 159
// PORTxn == 1, DDRxn == 0: input pullup
pinMode(PINp, OUTPUT)
// DDRx |= 1<<n, from line 56
// PORTxn == 1, DDRxn == 1: output high
Entonces, parece que llamar digitalWrite
antes pinMode
hará exactamente lo que quieres. Ignore el lío sobre la manipulación directa del registro anterior.
No puede cambiar el valor predeterminado del hardware. Hay un código que se ejecuta al inicio que usted no controla (hay al menos algún código de inicio en la ROM dentro del procesador, y también puede haber un gestor de arranque que se puede cambiar pero que es difícil de modificar para usted). A veces, este código puede alternar los pines de formas inesperadas mientras busca dispositivos de arranque alternativos o lo que sea. Esto me ha causado muchos problemas en varios momentos de mi carrera, porque no siempre está bien documentado por los proveedores de silicio (proveedores de segundo nivel de bajo costo).
A partir de su pregunta, no está claro si el procesador está bajando activamente el pin que desea usar, o si solo tiene un pulldown débil. Si es solo un pulldown débil, puedes dominarlo con un pullup de 1k. Además, puedes probar las ideas mencionadas anteriormente. Básicamente, debe asegurarse de alguna manera de que los datos estén configurados en alto ANTES de que la dirección se configure para generar en el código sobre el que tiene control. No sé mucho sobre arduino, pero me he ocupado de este tipo de cosas en varios microprocesadores y normalmente es posible establecer datos antes de establecer la dirección de un pin IO. A veces, el mismo bit que habilita el pullup interno también establece los datos en 1 para la salida.
Si el pin está bajando activamente por el código que no tiene la capacidad de modificar, un pullup no solucionará el problema. Pero es posible que pueda consultar la documentación (o experimentar) y encontrar otro pin que no se agote después del reinicio.
Buena suerte.
Si bien no es exactamente lo que estaba buscando, agregar un código adicional setup()
debería funcionar:
void setup() {
pinMode(PINx, OUTPUT); // replace PINx with the pin number
digitalWrite(PINx, HIGH); //makes PINx high almost immediately (few uS)
// rest of code
}
No hay problema con realizar escrituras digitales o lecturas digitales en void setup(), puede hacer cualquier cosa en setup()
, pero solo se ejecuta una vez. A menos que quiera decir 'ir alto en el instante en que se aplica la energía' porque, aparte de una resistencia pullup, creo que no tendrá suerte
setup();
está en la función principal al principio (mucho después de una init()
llamada oculta).setup()
que se llamara
crasico
setup()
. Si el cargador de arranque configura el pin, la solución no funcionará por cierto.