el uso de AVR Atmega32 SPI SPI sin clavijas
-
21-12-2019 - |
Pregunta
Soy bastante nuevo en la programación de los microcontroladores.Tengo algo de experiencia con el Arduino, pero después de que yo casi había terminado mi proyecto, me deceided a movido mi proyecto actual a algo más barato y más pequeño.Así que ahora estoy usando el AVR ATmega32 con Atmel studio.
Estoy tratando de utilizar el ATmega32 para comunicarse con un MAX7219 chip para la multiplexación con una matriz de led.sin embargo, tengo varios dispositivos diferentes que quiero comunicar.
¿Cómo me puedo comunicar con el dispositivo sin necesidad de utilizar los pines SPI siempre en el microcontrolador?He hecho una prueba de proyecto, pero parece ser que hay algo mal y no puedo averiguar cuál es el problema.Creo que me las arreglé para conseguir en el modo de prueba, debido a que todos los LEDs se encienden, pero no puedo llegar a hacer nada después de eso.Ni siquiera puedo borrar la pantalla/apagarlo.He comprobado el cableado a través de nuevo.Es mi codificación quizás incorrecta tan lejos como la configuración de los pines y la asignación de los pines?Hay alguna sugerencia para esto o una mejor manera de escribir mi código?
Aquí está el enlace a la MA7219 de hoja de datos
//test
#include <avr/io.h>
int main(void)
{
DDRB = 0b00000111; // pin 1(data), 2(clock) and 3(latch) are outputs
PORTB = 0 << PINB0; // data pin 1 is low
PORTB = 0 << PINB1; // clock pin 2 is low
PORTB = 0 << PINB2; // latch pin 3 is low
uint16_t data;
data = 0b0000110000000000; // data to shift out to the max7219
//read bit
uint16_t mask;
for (mask = 0b0000000000000001; mask>0; mask <<= 1)
{
//iterate through bit mask
if (data & mask)
{ // if bitwise AND resolves to true
// send one
PORTB = 1 << PINB0;
// tick
PORTB = 1 << PINB1;
// tock
PORTB = 0 << PINB1;
}
else{ //if bitwise and resolves to false
// send 0
// send one
PORTB = 0 << PINB0;
// tick
PORTB = 1 << PINB1;
// tock
PORTB = 0 << PINB1;
}
}
PORTB = 1 << PINB2; // latch all the data
PORTB = 1 << PINB0; // data pin 1 is high
PORTB = 0 << PINB1; // clock pin 2 is low
PORTB = 0 << PINB2; // latch pin 3 is low
}
Solución
Sí, su bit bang código tiene un problema en el que se asigna el valor total de la registrarse en cada momento, sin preservar el valor existente.Por lo tanto, usted borrar los datos de la señal en el instante en que usted conduce su reloj, violando el tiempo de espera del receptor, y que resulta en un funcionamiento impredecible.
En lugar de asignar los pines con =
, se debe establecer con |=
o claro con &= ~(value)
Por ejemplo:
PORTB = 1 << PINB0; //drive data
// tick
PORTB |= 1 << PINB1; //clock high PRESERVING data
// tock
PORTB &= ~(1 << PINB1); //clock low
Usted también puede necesitar para insertar un ligero retraso entre el pin de operaciones.
Técnicamente, dado que usted ya está usando un if
para el estado de los datos, también podría volver a la unidad de la señal de datos con una O en la cesión, por ejemplo
if (data & mask)
{ // if bitwise AND resolves to true
// send one
PORTB = 1 << PINB0;
// tick
PORTB = (1 << PINB1) | (1 << PINB0);
// tock
PORTB = 0 << PINB1 | (1 << PINB0);
}
else{ //if bitwise and resolves to false
// send 0
// send one
PORTB = 0 << PINB0;
// tick
PORTB = 1 << PINB1;
// tock
PORTB = 0 << PINB1;
}