collapse

* Posts Recentes

Amplificador - Rockboard HA 1 In-Ear por almamater
[Ontem às 19:13]


O que é isto ? por KammutierSpule
[26 de Março de 2024, 19:35]


Bateria - Portátil por almamater
[25 de Março de 2024, 22:14]


Emulador NES em ESP32 por dropes
[13 de Março de 2024, 21:19]


Escolher Osciloscópio por jm_araujo
[06 de Fevereiro de 2024, 23:07]


TP4056 - Dúvida por dropes
[31 de Janeiro de 2024, 14:13]


Leitura de dados por Porta Serie por jm_araujo
[22 de Janeiro de 2024, 14:00]


Distancia Cabo por jm_araujo
[08 de Janeiro de 2024, 16:30]


Meu novo robô por josecarlos
[06 de Janeiro de 2024, 16:46]


Laser Engraver - Alguém tem? por almamater
[16 de Dezembro de 2023, 14:23]

Autor Tópico: Introdução ao avr-gcc usando o AvrStudio [Mais timers/mood light]  (Lida 115922 vezes)

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

Offline senso

  • Global Moderator
  • Mini Robot
  • *****
  • Mensagens: 9.733
  • Helpdesk do sitio
Boa noite a todos, então aqui vai uma introdução muito básica de como começar a programar em C um arduino, quem diz arduino diz qualquer outro micro-controlador atmel, mas por agora digamos que é arduino pois é para quem quiser dar o salto do ide do arduino para algo melhor.

Primeiro temos de começar por instalar o AvrStudio, que é o IDE oficial da atmel e que podem fazer o download do mesmo aqui:
Citar
http://www.atmel.com/dyn/products/tools_card.asp?tool_id=2725

Andam com a página para baixo até encontrarem a linha que diz:
Citar
AVR Studio 4.18 (build 684) (116 MB, updated 11/09)
Têm de se registar para fazer o download do mesmo, mas o registo é rápido, depois fazem o download do seguinte ficheiro(que está pouco acima do outro):
Citar
AVR Studio 4.18 SP3 (b716) (31 MB, updated 9/10)

E por fim fazem o download do WinAvr que é o compilador C para os avrs, e que se encontra aqui:
Citar
http://sourceforge.net/projects/winavr/files/WinAVR/20100110/WinAVR-20100110-install.exe/download

Depois de fazerem o download destes 3 ficheiros podem começar a instalação, primeiramente o ficheiro intitulado AVR Studio 4.18 depois o AVR Studio 4.18 SP3 e por fim do WinAvr, não mudem nenhuma das pastas de instalação quer do AvrStudio quer do WinAvr pois poderam ter problemas com a compilação pois o WinAvr espera que as bibliotecas estejam num sitio e não noutro e não querem ir editar Makefiles para o meter a funcionar.
No fim de tudo instalado recomendo que criem uma pasta onde vão guardar os programas feitos ao longo deste tutorial, aconselho a colocar a pasta logo em c:/ ou d:/ pois vamos andar na linha de comandos e quanto menos sub pastas melhor, aconselho a fazer como eu e criar uma pasta chamada AVR em c:/ e é ai que vão ficar os programas quer em C, quer todos os ficheiros gerados pelo compilador, depois o IDE encarrega-se de criar uma pasta por cada projecto que criam, por isso fica tudo separado e organizado.

Tendo tudo isto instalado podem começar por iniciar o AvrStudio e irá aparecer-vos a seguinte janela:


De seguida clicam em "New Project" e a janela passa a mostrar a seguinte informação:


Como irão notar eu já preenchi alguns dos campos e voces devem fazer tal e qual como está na imagem.
O "Project Name" neste caso é blinky, o famoso piscar um led, simples mas no entanto serve para vos iniciar neste novo mundo, quando estão a escrever blinky no "Project Name" podem notar que o programa copia automaticamente o que escrevem para o campo Initial file.
Devem tambem selecionar as caixas "Create initial file" e "Create folder", assim o programa deixa-vos tudo arrumado e pronto a programar, e por fim devem selecionar "AVR GCC" no "Project type" pois querem programar em C e não em Assembly.
Não esquecer de mudar a localização("Location") para a pasta anteriormente criada em c:/.
Tendo tudo isto feito cliquem em "Next >>", ao clicar vais-vos aparecer duas listas:


Como podem ver pela imagem selecionem "AVR Simulator 2" como a "Debug platform" e seleccionem o "ATmega328p" como o "Device" pois é esse o chip que o arduino trás, se o vosso for um dos arduinos com um ATmega168p procedam de igual modo para a "Debug platform" mas no "Device" nem precisam de andar para baixo na lista, pois o ATmega168p aparece logo no inicio da lista.
Tendo o vosso chip seleccionado cliquem em "Finish" e ai está o vosso projecto pronto para começarem a programar em C.
Eis o aspecto do IDE quando clicam em "Finish":


Agora é começar a escrever código, neste caso é algo bastante simples:
Código: [Seleccione]
Loop infinito{
Acender led;
esperar 1s;
Apagar led;
esperar 1s;
}

Primeiramente e ao contrário do IDE do arduino que faz muitas coisas sem nós saber-mos temos que dizer ao compilador para incluir alguns ficheiros, um deles é um ficheiro com as definições genéricas de registos e portos do nosso chip, outro á uma biblioteca que nos permite criar os delays que precisamos para esperar neste caso 1s.
Como podemos ter o nosso atmega328p com um grande numero de diferentes cristais de diferentes frequências temos de dizer ao compilador qual é a frequência do nosso cristal para que ele saiba gerar delays com precisão.
Assim ainda no pseudo código teremos então:
Código: [Seleccione]
Incluir os ficheiros necessários
Definir a frequência do relógio/cristal
Incluir biblioteca de delays
Loop infinito{
Acender led;
esperar 1s;
Apagar led;
esperar 1s;
}

Começando agora a passar um pouco para c:
Código: [Seleccione]
#include <avr/io.h> //Definições dos portos do m328p, assim pudemos usar os portos para controlar o led
#define F_CPU 16000000UL //F_CPU é uma constante especifica do compilador que serve para armazenar a frequencia do nosso cristal, 16000000 é os 16Mhz escritos em hz, e UL é uma indicação de que queremos o numero representado por uma variavel capaz de o armazenar para não termos problemas de overflow se o compilador usar uma variavel em que o numero não cabe
#include <util/delay.h> //Biblioteca que nos fornece o delay, tem de ser sempre declarada depois da declaração de F_CPU e não antes, se não o compilador não sabe qual é a frequencia do nosso cristal

Loop infinito{
Acender led;
esperar 1s;
Apagar led;
esperar 1s;
}

Agora que já dissemos ao compilador o que ele tem de ir buscar fora do nosso programa vamos passar para C o nosso pseudo-código:
Código: [Seleccione]
#include <avr/io.h> //Definições dos portos do m328p, assim pudemos usar os portos para controlar o led
#define F_CPU 16000000UL //F_CPU é uma constante especifica do compilador que serve para armazenar a frequencia do nosso cristal, 16000000 é os 16Mhz escritos em hz, e UL é uma indicação de que queremos o numero representado por uma variavel capaz de o armazenar para não termos problemas de overflow se o compilador usar uma variavel em que o numero não cabe
#include <util/delay.h> //Biblioteca que nos fornece o delay, tem de ser sempre declarada depois da declaração de F_CPU e não antes, se não o compilador não sabe qual é a frequencia do nosso cristal

int main(void){
while(1){ //Loop infinito{
PORTB |= (1<<PB5); //Acender led; vamos usar o led que está no pin13 do arduino
_delay_ms(1000); //esperar 1s; como são milisegundos, temos de esperar 1000ms para fazer 1s
PORTB &= ~(1<<PB5); //Apagar led;
_delay_ms(1000); //esperar 1s;
}
}

Por esta imagem podem relacionar os nomes que o arduino dá aos pinos com os nomes verdadeiros dos mesmos quando querem usar o AvrStudio.


Ainda falta uma coisa, tal como no arduino temos que definir se um pino é uma entrada ou uma saída, para isso usamos uma coisa chamada DDR, que é um registo que define se um pino é entrada ou saída, no caso do AVR 1 quer dizer saída e 0 quer dizer entrada, para isso vamos definir o nosso pino numero 5 do porto B como uma entrada assim:
Código: [Seleccione]
DDRB |= (1<<PB5);

E o nosso código final fica assim:
Código: [Seleccione]
#include <avr/io.h> //Definições dos portos do m328p, assim pudemos usar os portos para controlar o led
#define F_CPU 16000000UL //F_CPU é uma constante especifica do compilador que serve para armazenar a frequencia do nosso cristal, 16000000 é os 16Mhz escritos em hz, e UL é uma indicação de que queremos o numero representado por uma variavel capaz de o armazenar para não termos problemas de overflow se o compilador usar uma variavel em que o numero não cabe
#include <util/delay.h> //Biblioteca que nos fornece o delay, tem de ser sempre declarada depois da declaração de F_CPU e não antes, se não o compilador não sabe qual é a frequencia do nosso cristal

int main(void){

DDRB |= (1<<PB5); //Definir o pin digital 13/PORTB5 como saida para pudermos piscar o nosso led

while(1){ //Loop infinito{
PORTB |= (1<<PB5); //Acender led; vamos usar o led que está no pin13 do arduino
_delay_ms(1000); //esperar 1s; como são milisegundos, temos de esperar 1000ms para fazer 1s
PORTB &= ~(1<<PB5); //Apagar led;
_delay_ms(1000); //esperar 1s;
}
}

Basta copiar este código para a janela do IDE e carregar em F7 que é o botão para compilar e o código deve compilar sem qualquer erro e deve aparecer algo assim:


Se de erro é porque se enganaram a copiar alguma coisa, certifiquem-se que os comentários que aqui aparecem em várias linhas no IDE só estão numa linha, se andarem um pouco para cima na janela com o nome Build poderão ver que este código ocupa 172bytes de flash, muito mas muito menos que o blinky do arduino ocupa.

Sei que é neste momento que muitos de vós ficam com um nó no cérebro por causa de coisas como o "|=" o "&=" e até mesmo o "<<", isso meus caros colegas são operadores lógicos e o melhor mesmo é ler um tutorial sobre eles pois é um assunto um pouco extenso, se vocês de dão bem com inglês recomendo este aqui, pois aprendi a partir dele:
Citar
http://www.avrfreaks.net/index.php?name=PNphpBB2&file=viewtopic&t=37871

Se mesmo assim não perceberem é só dizer que eu irei fazer o meu melhor para vos ensinar.
Agora vamos passar á parte de colocar o programa no arduino, como não estamos a usar o IDE do mesmo não temos o botão mágico para fazer o upload do programa para o atmega, mas em vez de termos um botão mágico vamos fazer nós mesmo o que o IDE do arduino não mostra, primeiro vamos começar por ir á barra Iniciar do

Windows, se estiverem a usar o Vista ou superior escrevam "Executar" e carreguem no icon azul que vos aparece com o nome "Executar":


Na janela que vos aparece escrevam cmd, que quer dizer linha de comandos do windows e cliquem em ok:


Ao clicar no ok vais-vos aparecer uma janela nova, a nossa querida linha de comandos, que vai ser a vossa nova companheira, pois é por ela que vão passar a fazer o upload dos programas para o arduino:


E agora se usaram a mesma pasta que eu usei, ou seja AVR e se a meteram no mesmo sitio escrevam o seguinte na linha de comandos:
Código: [Seleccione]
cd/e carreguem no enter

Código: [Seleccione]
cd AVRE carreguem no enter

Código: [Seleccione]
cd blinkyE carreguem no enter

Código: [Seleccione]
cd defaultE carreguem no enter, eu sei que não criaram a pasta default mas é nessa pasta que está o nosso ficheiro .hex, ou seja o programa compilado pronto a enviar para o arduino, agora vem mais um pouco de magia, usando o ide do arduino vejam qual é a porta com a que o vosso arduino está associado quando o ligam ao pc.
O comando genérico para usar o avrdude é este:
Código: [Seleccione]
avrdude -p m328p -c avrisp -P com* -b 57600 -F -U flash:w:Nome do hex.hex
No meu caso a porta com é a com5 e neste exemplo o nosso programa chama-se blinky logo o hex tem o nome de blinky.hex, se não tiverem a certeza escrevam:
Código: [Seleccione]
dirE façam enter, como podem ver ali está o Blinky.hex, tenham atenção que o avrdude é sensível a letras maiúsculas e minúsculas:


Então para enviar este programa para o nosso arduino escreve-mos o seguinte na linha de comandos:
Código: [Seleccione]
avrdude -p m328p -c avrisp -P com5 -b 57600 -F -U flash:w:Blinky.hexE carreguem no enter, a única diferença aqui é que terão de carregar no botão de reset do arduino para que o upload do programa seja feito, se não irão obter um erro de "out of sync" ou algo parecido, quando o upload do programa é bem sucedido eis a mensagem que vos é apresentada:


Agora podem olhar para o vosso arduino a piscar o seu led todo contente da vida com uma tonelada de código a menos em cima, e espero que vocês tenham gostado de ler esta introdução ao avr-gcc usando o AvrStudio, se houver interesse irei continuar com uma série de tutoriais simplificados e muito explicados, estou aberto a sugestões pessoal!
« Última modificação: 02 de Fevereiro de 2012, 21:15 por senso »
Avr fanboy

Offline amando96

  • Mini Robot
  • *
  • Mensagens: 1.631
  • MAC address? But I have windows...
    • Projects, News, Blog, Tutorials
Re: Introdução ao avr-gcc usando o AvrStudio
« Responder #1 em: 28 de Setembro de 2010, 08:16 »
Bom post  ;D
Já agora esclareço aqui uma duvida,

porque
Código: [Seleccione]
DDRB |= (1<<PB5);
não dava para fazer assim?
Código: [Seleccione]
DDRB = 0x01;
tenho usado tanto de uma maneira como a outra, e ainda não vi diferenças, mas têm de haver, quais são elas?


Offline Cynary

  • Mini Robot
  • *
  • Mensagens: 182
Re: Introdução ao avr-gcc usando o AvrStudio
« Responder #2 em: 28 de Setembro de 2010, 09:28 »
Bom post  ;D
Já agora esclareço aqui uma duvida,

porque
Código: [Seleccione]
DDRB |= (1<<PB5);
não dava para fazer assim?
Código: [Seleccione]
DDRB = 0x01;
tenho usado tanto de uma maneira como a outra, e ainda não vi diferenças, mas têm de haver, quais são elas?

Primeiro, não é igual, visto que 0x01 = (1<<PB0).
Segundo, ao usares (1<<PB5), o teu código torna-se mais legível e, caso por alguma razão alterem qual o bit correspondente ao PB5 noutro AVR, tens menos trabalho a transportar o código de um AVR para outro.

Excelente tutorial senso ;)

Offline senso

  • Global Moderator
  • Mini Robot
  • *****
  • Mensagens: 9.733
  • Helpdesk do sitio
Re: Introdução ao avr-gcc usando o AvrStudio
« Responder #3 em: 28 de Setembro de 2010, 13:26 »
Tal como o cinary disse deves evitar numeros mágicos, se daqui a 6 meses olhares para o código provavelmente não te lembras por que razão está lá aquele 0x01, com 1<<PB5 sabes que é para definir o pino 5 do porto b como saida.
Já agora se vires no includes o que quer dizer o PB5 vais encontrar:
Código: [Seleccione]
#define PB0 0
#define PB1 1
#define PB2 2
#define PB3 3
#define PB4 4
#define PB5 5
#define PB6 6
#define PB7 7
Até podes usar decimais, mas ainda se torna mais confuso que usar as definições de PBx.

E como são variaveis conhecidas quando compilas o compilador optimiza tudo e não vai mandar o micro fazer shifts para calcular esse valor.
O que ainda é mais ou menos legivel é usares binário, assim tambem dá para ver visualmente qual é o pino, assim:
Código: [Seleccione]
DDRB |= 0b00100000;
Avr fanboy

Offline Njay

  • Mini Robot
  • *
  • Mensagens: 3.598
    • Tróniquices
Re: Introdução ao avr-gcc usando o AvrStudio
« Responder #4 em: 28 de Setembro de 2010, 14:05 »
porque
Código: [Seleccione]
DDRB |= (1<<PB5);
não dava para fazer assim?
Código: [Seleccione]
DDRB = 0x01;

Ambas são completamente diferentes.
A 1ª só afecta o bit 5 do porto B.
A 2ª afecta todos os bits!
Além de que convém sermpe usar nomes para as constantes, como já aqui foi referido.

Boa introdução!

Offline senso

  • Global Moderator
  • Mini Robot
  • *****
  • Mensagens: 9.733
  • Helpdesk do sitio
Re: Introdução ao avr-gcc usando o AvrStudio
« Responder #5 em: 28 de Setembro de 2010, 19:24 »
Tanta gente que quer dar o salto mas ninguem se chega á frente...
No pain no gain pessoal
Avr fanboy

Offline amando96

  • Mini Robot
  • *
  • Mensagens: 1.631
  • MAC address? But I have windows...
    • Projects, News, Blog, Tutorials
Re: Introdução ao avr-gcc usando o AvrStudio
« Responder #6 em: 28 de Setembro de 2010, 21:02 »
porque
Código: [Seleccione]
DDRB |= (1<<PB5);
não dava para fazer assim?
Código: [Seleccione]
DDRB = 0x01;

Ambas são completamente diferentes.
A 1ª só afecta o bit 5 do porto B.
A 2ª afecta todos os bits!
Além de que convém sermpe usar nomes para as constantes, como já aqui foi referido.

Boa introdução!

Sim mas, se fosse DDRB = 0x20, iria por o PB5 a 1, output, e o resto como input, se eles estão logo "default" como input, DDRB |= (1<<PB5) fará o mesmo, só que não declara o resto como input, mas como já o são, não faz falta?
Mas estou a ver que por referir logo o pino que está a ser declarado dá mais jeito para quando for rever o código, e caso o querer meter noutro AVR, passarei a fazer assim  :)

Offline senso

  • Global Moderator
  • Mini Robot
  • *****
  • Mensagens: 9.733
  • Helpdesk do sitio
Re: Introdução ao avr-gcc usando o AvrStudio
« Responder #7 em: 28 de Setembro de 2010, 21:06 »
Imagina que daqui a uns tempos te lembras e queres outro led no PB4, não te lembras que tens o DDR=0x20 e o que acontece é que o teu igual está a limpar qualquer assignação que faças antes de chegar a essa linha e isso é uma má prática de programação.
Avr fanboy

Offline Njay

  • Mini Robot
  • *
  • Mensagens: 3.598
    • Tróniquices
Re: Introdução ao avr-gcc usando o AvrStudio
« Responder #8 em: 28 de Setembro de 2010, 23:14 »
"assign" em Português é "atribuir".

Isto é um exemplo do meu tipico código de inicialização de pinos do AVR:

// Ports pin assignment.
enum {
    // Port A
    ePinStrobe  = _BV(PA0),
    ePinData    = _BV(PA1),
    ePinDClock  = _BV(PA2),
    ePinUartTx  = _BV(PA3),
    ePinUartRx  = _BV(PA4),    // input
    ePinEndX    = _BV(PA5),    // input w/ pull-up
    ePinEndY    = _BV(PA6),    // input w/ pull-up
    ePinEndZ    = _BV(PA7),    // input w/ pull-up
    // Port B
    ePinOE      = _BV(PB0),
    ePinDRLL    = _BV(PB1),
    ePinLEDa    = _BV(PB2),    // green
    ePinFTE     = _BV(PB3),
    ePinXTAL1   = _BV(PB4),    // (used by external crystal)
    ePinXTAL2   = _BV(PB5),    // (used by external crystal)
    ePinLEDb    = _BV(PB6),    // red
    ePinReset   = _BV(PB7),    // (used as the chip reset)
};

 (...)

DDRA = ePinStrobe | ePinData | ePinDClock | ePinUartTx;
PORTA = ePinEndX | ePinEndY | ePinEndX;   // pullups
DDRB = ePinOE | ePinDRLL | ePinLEDa | ePinFTE | ePinLEDb;

Offline senso

  • Global Moderator
  • Mini Robot
  • *****
  • Mensagens: 9.733
  • Helpdesk do sitio
Re: Introdução ao avr-gcc usando o AvrStudio
« Responder #9 em: 28 de Setembro de 2010, 23:44 »
Já agora, qual o uso do enum{ }; ?
Avr fanboy

Offline Cynary

  • Mini Robot
  • *
  • Mensagens: 182
Re: Introdução ao avr-gcc usando o AvrStudio
« Responder #10 em: 28 de Setembro de 2010, 23:59 »
Já agora, qual o uso do enum{ }; ?

O enum neste caso funciona como um #define.

Offline senso

  • Global Moderator
  • Mini Robot
  • *****
  • Mensagens: 9.733
  • Helpdesk do sitio
Re: Introdução ao avr-gcc usando o AvrStudio
« Responder #11 em: 29 de Setembro de 2010, 00:07 »
Isso eu percebi, mas qual a diferença de um para o outro?
Avr fanboy

Offline Njay

  • Mini Robot
  • *
  • Mensagens: 3.598
    • Tróniquices
Re: Introdução ao avr-gcc usando o AvrStudio
« Responder #12 em: 29 de Setembro de 2010, 00:20 »
Eu pessoalmente uso enums sempre que possível apenas por uma razão. É que os enums ficam registados na "informação de debug" e quando estamos a correr o programa passo a passo (em simulador ou não), são mostrados os nomes dos enums em vez do seu valor e podemos atribuir a uma variável o nome do enum em vez do valor, o que é mais útil. Isto porque os enums são processados pelo compilador e não pelo pre-processador.
Por outro lado o enum é menos flexível, pois tem um tipo, int, e o define é apenas "texto" no código fonte.

Há aqui coisas que podem não fazer sentido para vocês, porque não sabem exactamente como funciona a corrente de ferramentas do c/c++ (toolchain). Mas assim por alto, é como se o código passasse por 4 programas distintos: 1º pelo pré-processador, depois pelo compilador, depois pelo assembler e depois pelo linker. O pré-processador entende quase apenas a linguagem de macros (o que começa por #, como #include, #define, etc) e faz as suas substituições no código fonte original. Depois, o código fonte já alterado (diz-se "expandido pelo pré-processador de C/C++) é que entra no 2º programa, o compilador. O compilador gera então um programa assembly. Depois o assembler transforma o programa assembly em binário e o linker junta vários binários gerados por diferentes ficheiros C/C++ num único programa, juntando-lhe código para fazer a inicialização de acordo com o sistema operativo ou plataforma que estão a usar.

No caso do GCC, o "gcc.exe" que vocês invocam é apenas um programa que vai invocando os programas necessários para compilar o vosso programa (confuso :)?). Na directoria dos binários do GCC vocês vão encontrar todos estes programas, o cpp é o "c pre-processor", etc. O gcc.exe apaga os ficheiros intermediários, como o output do preprocessador (o vosso ficheiro C/C++ expandido), o do compilador (o programa em assembly assembly), etc e vocês só vêm os finais; mas existem opções que podem dar ao gcc para ele não os apagar e assim poderem ser inspeccionados. E para que raio haveriam vocês de querer ver esses ficheiros, para além de curiosidade? Eu por exemplo uso muito o ficheiro em assembly, uso-o para ver que optimizações o compilador está a fazer (porque eu percebo o assembly) e assim poder "orientar" o compilador a fazer melhores optimizações, ou simplesmente para saber como é que se faz ou como é que ele faz X ou Y. Estes ficheiros em assembly podem ter em comentário o código C/C++ que deu origem às sequências de instruções assembly, portanto pode-se aprender imenso a ver este ficheiro.
« Última modificação: 29 de Setembro de 2010, 00:35 por Njay »

Offline Cynary

  • Mini Robot
  • *
  • Mensagens: 182
Re: Introdução ao avr-gcc usando o AvrStudio
« Responder #13 em: 29 de Setembro de 2010, 00:24 »
Isso eu percebi, mas qual a diferença de um para o outro?

com o enum, podes criar uma espécie de tipo personalizado, em que podes corresponder palavras a certos valores.
Imagina que queres um tipo que guarde os dias da semana, podes ter algo como:

Código: (c) [Seleccione]
enum dia { segunda, terca, quarta, quinta, sexta, sabado, domingo };
...
enum dia t = terca;
...

(a necessidade de enum antes do tipo de enum depende se usas C ou C++, da mesma forma que as struct).
No entanto, não tens de obrigatoriamente ter um tipo dia para dar o valor terca à variável, pode ser um int, um char, ...
No exemplo que dei, o enum dá automaticamente valores de inteiros aos dias (segunda, terca, ...). Podes também atribuir os teus próprios valores se quiseres.
Neste caso, não há diferença entre o enum e o define.
Na prática, a maior diferença é que com o enum só podes guardar inteiros, enquanto com o #define podes guardar tudo o que quiseres (strings, funções, qualquer tipo estranho de dados, ...).

Tenho uma questão: estive a fazer um programa que altera um número num LCD. Consegui pô-lo a funcionar perfeitamente. No entanto queria que fosse mais portátil caso decidisse alterar os pinos usados. Para isso, queria guardar em três arrays os seguintes dados para cada ligação: o register de direcção de dados, o register da porta e o bit (neste momento apenas guardo os bits, usando apenas um register DDR e PORT para todos).
Alguém sabe qual o tipo de dados que uso para guardar os registers PORT e DDR num array? (será que um void * a apontar para a variável funcionaria?)
Nos includes, só encontro que são o resultado de _SFR_IO8(valor), mas não faço a mínima ideia do que essa macro faça :S

Offline senso

  • Global Moderator
  • Mini Robot
  • *****
  • Mensagens: 9.733
  • Helpdesk do sitio
Re: Introdução ao avr-gcc usando o AvrStudio
« Responder #14 em: 29 de Setembro de 2010, 00:28 »
Estou a ver a coisa.
Já agora, quanto a isso do lcd dá uma vista de olhos nisto:
http://www.jump.to/fleury
Avr fanboy