collapse

* Links de Robótica

* Posts Recentes

Ajuda Projecto IR / RF por Njay
[Hoje às 00:03]


Recomendação de um opamp para um DAC r2r por jm_araujo
[Ontem às 23:05]


Ideias para construir um quadrúpede simples por dropes
[Ontem às 22:43]


Ajuda com TRIAC por senso
[17 de Novembro de 2017, 18:00]


TV LG White Screen por almamater
[15 de Novembro de 2017, 08:37]


Pergunta sobre prototipagem ( Pesquisa ) por luisjustin
[14 de Novembro de 2017, 23:22]


Medir Agua que está no Poço por Njay
[14 de Novembro de 2017, 13:28]


Amplificador audio por beirao
[12 de Novembro de 2017, 23:43]


Power_OK Enermax por edeweld
[12 de Novembro de 2017, 17:15]


Driver motor por beirao
[11 de Novembro de 2017, 17:40]

Autor Tópico: Problema na comunicação entre atmegas por SPI  (Lida 1470 vezes)

0 Membros e 1 Visitante estão a ver este tópico.

Offline vdr

  • Mini Robot
  • *
  • Mensagens: 78
Problema na comunicação entre atmegas por SPI
« em: 18 de Janeiro de 2013, 12:09 »
É o seguinte eu estou a tentar ligar dois atmegas 328p através de SPI. Mas acontece que o slave está ciclicamente a fazer reset, já li no avrfreaks que poderia ser por estar a fazer set ao pino SS depois de ter o SPI activo, mas não estou a fazer isso.

Basicamente o código abaixo deveria fazer o seguinte:

 - Master envia continuamente a cada 1s um byte
 - Slave deveria receber o byte enviado pelo interrupt e imprimi-lo no terminal.

Código: [Seleccione]
#include <asf.h>
#include "lib.h"
#include <avr/io.h>
#include <avr/interrupt.h>
#define F_CPU 16000000UL
#include <util/delay.h>
#include <stdlib.h>   

uint8_t master = 0;
uint8_t val = 10;
uint8_t res=0;
uint8_t debug = 1;

int main (void)
{
board_init();
USART_init();

if(master==1){
USART_putstring("\r\n\t************************************************ ");
USART_putstring("\r\n\t*** MASTER INIT ******************************** ");

SPI_init(1);
while(1){
res = SPI_Write(val);
USART_putstring("\r\n\t*** BYTE SENT : ");
USART_send(val);
USART_putstring("\n\r\n\t************************************************ ");
_delay_ms(1000);

}
}else{
SPI_init(0);

char string[8];

if(debug){
USART_putstring("\r\n\t* DEGUB ********");

USART_putstring("\r\n\t*** PORTB : ");
itoa(PINB, string, 10);
USART_putstring(string);

USART_putstring("\r\n\t*** SPCR : ");
itoa(SPCR, string, 10);
USART_putstring(string);

USART_putstring("\r\n\t****************");

}


USART_putstring("\r\n\t************************************************ ");
USART_putstring("\r\n\t*** SLAVE INIT ********************************* ");
        sei();
while(1);
}

}

ISR(SPI_STC_vect)
{
char ch = SPDR;
USART_putstring("\r\n\t************************************************ ");
USART_putstring("\r\n\t***SLAVE RECEIVED:  ");
USART_send(ch);
USART_putstring("\n\r\n\t************************************************ ");
}

//FUNÇÕES NA LIB.C

// SPI ------------------------------------------------------------------------------------------------------
#define MOSI PB3
#define MISO PB4
#define SCK PB5
#define SS PB2
//-----------------------------------------------------------------------------------------------------------


uint8_t SPI_Write(uint8_t data){
PORTB &= (~(1<<SS));
SPDR = data; //Start data transfer
while(!(SPSR & (1<<SPIF))); //Wait for the end of the transmission
PORTB |= (1<<SS);

return SPDR; //Return the received data
}

void SPI_init(uint8_t master){

if(master==1){
DDRB |= (1<<MOSI)|(1<<SCK)|(1<<SS); //MOSI, SCK, SS OUTPUTS
DDRB &= ~(1<<MISO); //MISO INPUT
PORTB |= (1<<SS); //SS START HIGH

//Enable SPI, Master mode
//MSB first
//CPOL=0
//CPHA=0
//SPI mode 0
//sck = F_CPU/16 = 1Mhz
//SPSR = (1<<SPI2X); //SPI clock x2
SPCR = (1<<SPE)|(1<<MSTR)|(1<<SPR0)|(0<<SPIE);
}else{

DDRB |= (1<<MISO);
DDRB &= ~(1<<MOSI);
DDRB &= ~(1<<SCK);
DDRB &= ~(1<<SS);

SPCR = (1<<SPE)|(1<<SPIE)|/*(1<<CPHA)|*/(0<<MSTR);
}
}



Offline Njay

  • Mini Robot
  • *
  • Mensagens: 3.139
    • Tróniquices
Re: Problema na comunicação entre atmegas por SPI
« Responder #1 em: 18 de Janeiro de 2013, 12:14 »
Podes invocar a USART_putstring dentro de uma interrupção? Assm à partida é a única dúvida que tenho.

Offline vdr

  • Mini Robot
  • *
  • Mensagens: 78
Re: Problema na comunicação entre atmegas por SPI
« Responder #2 em: 18 de Janeiro de 2013, 12:25 »
Podes invocar a USART_putstring dentro de uma interrupção? Assm à partida é a única dúvida que tenho.

Li algures na AVRFreaks que não haveria problema, de qualquer modo comentei todas a linhas no interrupt de USART e o problema continua. Outra coisa que me parece muito estranha é quando leio o PORTB vem sempre com valores diferentes, mas também poderá ser devido ao reset.

Offline Njay

  • Mini Robot
  • *
  • Mensagens: 3.139
    • Tróniquices
Re: Problema na comunicação entre atmegas por SPI
« Responder #3 em: 18 de Janeiro de 2013, 12:37 »
Se faz reset assim que lhe envias um byte pode ser porque não estás a usar a interrupção correcta, já verificaste isso?

Fizeste enable do PRSPI?
« Última modificação: 18 de Janeiro de 2013, 12:44 por Njay »

Offline vdr

  • Mini Robot
  • *
  • Mensagens: 78
Re: Problema na comunicação entre atmegas por SPI
« Responder #4 em: 18 de Janeiro de 2013, 15:14 »
Se faz reset assim que lhe envias um byte pode ser porque não estás a usar a interrupção correcta, já verificaste isso?

Fizeste enable do PRSPI?

Não tinha mexido nesse pino, pois ele esta por defeito a LOW logo não preciso de lhe mexer, e confirmei que o valor se mantem entre resets.

Offline Njay

  • Mini Robot
  • *
  • Mensagens: 3.139
    • Tróniquices
Re: Problema na comunicação entre atmegas por SPI
« Responder #5 em: 18 de Janeiro de 2013, 15:42 »
É por omissão e não por defeito. Então se eu fosse a ti corria o slave em simulação para ver o que acontece. É estranho estar a fazer reset nessa situação, isso parece-me problema puramente de sw, corrupção de memória ou coisa do género. Os pinos do SPI são usados para o ISP, vê lá se não estarás a ter algum conflito com isso.

Ah, também deves confirmar que tens os pinos bem ligados. Se houver um curto (2 pinos configurados como saída e ligados entre si) isso pode fazer baixar a tensão de alimentação e causar um reset no chip.
« Última modificação: 18 de Janeiro de 2013, 15:48 por Njay »

Offline vdr

  • Mini Robot
  • *
  • Mensagens: 78
Re: Problema na comunicação entre atmegas por SPI
« Responder #6 em: 18 de Janeiro de 2013, 16:02 »
Obrigado Njay.

Se eu comentar o sei(), deixa de fazer reset, penso que o problema esteja na interrupção, mas não estou a ver onde.

Offline Njay

  • Mini Robot
  • *
  • Mensagens: 3.139
    • Tróniquices
Re: Problema na comunicação entre atmegas por SPI
« Responder #7 em: 18 de Janeiro de 2013, 16:43 »
Se fizeres isso deixas de ter interrupções (o sei() habilita as interrupções).
Deve haver aí algum problema com as ints, deve estar a ser chamada alguma int que não está instalada e quqnado isso acontece o sw volta para o endereço zero (reset). Por isso logo no inicio te perguntei se estarias a usar o ISR certo. Corre isso em simulação, vai dar logo para perceber o que se passa (carrega o .ELF no AVRstudio). Tás a indicar o CPU certo ao GCC?

Offline vdr

  • Mini Robot
  • *
  • Mensagens: 78
Re: Problema na comunicação entre atmegas por SPI
« Responder #8 em: 18 de Janeiro de 2013, 17:38 »
Tás a indicar o CPU certo ao GCC?

Era aqui que estava o problema, por descuido meu tinha indicado o 329P em vez de 328..

Obrigado mais uma vez pela ajuda Njay!