BANCO
DE MEMÓRIA EXTERNO PARA
MICROCONTROLADORES
memo_UC
O artigo a seguir foi publicado
na revista Eletrônica Total nr126 de
Setembro/Outubro de 2007. Na época eu projetei esse
banco para ser utilizado com microcontroladores que
possuíam pouca ou nenhuma memória EEPROM como a
linha PIC16F6XX da Microchip®
e outros. Hoje em dia temos microcontroladores com
bastante memória FLASH, mas alguns deles sem nenhuma
memória EEPROM e para estes a solução é na maioria
dos casos usar parte dessa memória para dados,
"simulando" uma EEPROM. Porém isso nem sempre é o
melhor dos mundos e no meu caso, em um projeto
recente, isso mostrou-se impossível já que toda a
área da FLASH estava sendo ocupada pelo programa.
Pensando
nisso, percebi que esse antigo projeto, hoje pode se
mostrar uma "mão na roda" para o desenvolvedor. O
artigo será aqui descrito tal qual publiquei na
época, mas com pequenas adaptações você poderá usar
essa placa com um microcontrolador de 32 bits como o
STM32F103C6T8 (Blue Pill) e no banco memórias com
mais de 32kBytes.
A PROPOSTA
Quantas vezes o hobista ou estudante de eletrônica que
gosta de desenvolver suas próprias soluções não se
deparou com a necessidade de coletar alguns dados vindos
de sensores e outros através de um circuito
microcontrolado? E quantas não foram as vezes onde se
fazia necessário guardar estas informações para
posteriormente processá-las?
Pensando nisso, desenvolvi o circuito que será
apresentado neste artigo. Ele permite preparar um
pequeno banco de memória EEPROM com mais 2 kBytes! Este
tamanho pode ser estendido com a alteração de alguns
componentes e do programa de controle.
Para muitos usuários 2 kBytes de memória EEPROM pode
parecer pouco, mas se levarmos em conta que muitos
microcontroladores de 8 bits possuem memória EEPROM
interna da ordem de 128 Bytes como, por exemplo, o
PIC16F628A Microchip®, os 2 kBytes propostos são bem
mais interessantes.
As sugestões de uso para um banco externo como o
proposto neste artigo são ilimitadas. Tudo dependera da
criatividade de cada um. Como exemplo, podemos citar
algumas aplicações que podem fazer uso do banco de
memória memo_uC. São elas:
• Aplicação em um
data logger;
• Mini-servidor web (para guardar a
página e outros dados);
• Relógio de ponto eletrônico;
• Mini-terminal de dados stand
alone (operação off-line);
• etc.
Como dito
anteriormente, o limite para a aplicação do circuito
proposto depende apenas da criatividade e conhecimentos
de cada um.
COMUNICAÇÃO
I2C
O protocolo I2C (Inter-Integrated Circuit) é do
tipo serial síncrono e foi desenvolvido originalmente
pela Phillips® em meados da década de 1990. Atualmente
ele está presente em uma série de dispositivos
eletrônicos e componentes dos mais variados tipos como:
microcontroladores, controladores de LCD, memórias,
dispositivos de I/O, relógios de tempo real (RTC), entre
outros.
As vantagens deste tipo de comunicação são muitas e
dentre elas podemos citar:
• Barramento de simples controle:
mestre / escravo (Master/Slave) com endereçamento
resolvido via software ou hardware;
• Interface de comunicação interna ao
dispositivo o que facilita o uso dos dispositivos;
• Permite a ligação de dispositivos
com tensões de alimentação diferentes graças as vias de
comunicação tipo open drain;
• Excelente taxa de comunicação
(velocidade): 100 kbps no modo Standart, 400
kbps no modo Fast e até 3.4 Mbps no modo High
Speed;
• Modo de comunicação síncrono o que
permite que dispositivos de velocidades diferentes sejam
conectados ao mesmo barramento usando a taxa de
comunicação do dispositivo de menor velocidade;
• Boa imunidade a ruídos elétricos;
• Flexibilidade no barramento para
inclusão ou exclusão de um dispositivo escravo sem
afetar os demais de mesma natureza;
• etc.
Porém nem tudo “são flores” e o padrão I2C também possui
algumas desvantagens:
• Número de dispositivos ligados a um
mesmo barramento limitados a 128 dispositivos no modo
normal (7 bits para endereçamento) ou 1024 dispositivos
no modo estendido (10 bits no endereçamento);
• O barramento, devido às suas
características elétricas, não pode percorrer grandes
distâncias ficando estas limitadas ao circuito
principal. O barramento deve ser utilizado para
comunicação entre dispositivos inseridos internamente em
um equipamento e nunca externamente (em alguns casos
está regra pode ser quebrada, desde que o cabo/conexão e
a distância sejam pequenas: > 2 metros);
• Devido ao modo de comunicação
mestre / escravo a rede não pode ser compartilhada com
vários dispositivos se comunicando ao mesmo tempo. Toda
e qualquer comunicação é sempre feita entre o mestre e o
escavo, sendo está iniciada sempre pelo dispositivo
mestre
Apesar disso, o protocolo I2C
é excelente para uso na comunicação entre dispositivos
como um microcontrolador (elemento mestre) e alguns
dispositivos como: memórias, RTCs, controladores de I/O,
etc (dispositivos escravos). Fica óbvio que a realização
do projeto será simplificada pois o padrão de
comunicação entre os vários dispositivos será o mesmo e
o barramento usado também. A figura abaixo demonstra um
exemplo típico de aplicação I2C.
A comunicação I2C usa duas vias de comunicação tipo open
drain: Dados (SDA) e Clock (SCL). A via SDA é
bidirecional e serve para a troca de dados seriais entre
o dispositivo mestre e o dispositivo escravo. A via SCL
é usada para sincronismo (clock de comunicação)
entre os dispositivos mestre e escravo e é sempre
controlada pelo dispositivo mestre. A figura abaixo
mostra o diagrama de tempos padrão para a comunicação
I2C.
Observando a figura acima você pode perceber que existe
um procedimento de comunicação bastante simples no
protocolo I2C:
• O dispositivo mestre inicia a
comunicação (SDA em nível lógico “1” e SCL em nível
lógico “0”);
• O dispositivo mestre envia os bits
de endereçamento. Todos os dispositivos escravos
recebem, mas apenas o dispositivo escravo que possui o
endereço enviado responderá;
• O dispositivo mestre envia o bit de
comando – escrita ou leitura;
• O dispositivo escrava retorna
através da via SDA o sinal de ACK (Acknowledge);
• O dispositivo mestre ou escravo
(dependendo da operação – escrita ou leitura) envia
pacotes de 8 bits de dados, que serão sempre seguidos de
um sinal ACK enviado pelo dispositivo que aguarda os
dados (escravo ou master);
• O dispositivo mestre encerra a
comunicação (SDA e SCL em nível lógico “1”).
Você deve ter em mente que os dispositivos I2C possuem
funções diferentes e sendo assim, o modo de operá-los
também é diferente. O protocolo é valido apenas para a
padronização da comunicação no barramento. O uso de cada
dispositivo pode depender do acesso a registros internos
com envio de comandos específicos. A forma de
comunicação já foi demonstrada, mas cabe ao
desenvolvedor estudar cada um dos dispositivos que irá
usar. Para isso basta ler atentamente os datasheets
e notas de aplicações de cada componente. Estas
informações estão sempre presentes no site do
fabricante! Use-as sempre!
CIRCUITO E
FUNCIONAMENTO
A figura acima
traz o circuito elétrico do banco de memória externo
memo_uC. Ele apresenta oito memórias EEPROM AT24C01A
ATMEL (CI1 a CI8). Cada uma destas memórias pode
armazenar 1 kbit ou 128 bytes (1024/8). Como temos oito
memórias, podemos afirmar que o banco tem capacidade de
armazenamento igual a 1 kByte (128 x 8). Se utilizarmos
neste banco, memórias AT24C02A, também da ATMEL, teremos
um banco de memória com capacidade máxima de 2 kBytes.
Nota em 2023: Se você utilizar 8
memórias AT24C32 terá um banco com 32kBytes e se
usar 8 memórias AT24C64 o mesmo banco passará a
ter 64KBytes!!!
C1 a C8 são
capacitores de desacoplamento e ajudam a filtrar
possíveis ruídos vindos da fonte de alimentação. O
capacitor C9 aumenta o nível do filtro da fonte.
O conector JP1 serve para conectar o banco de memória ao
circuito principal e possui as duas vias de comunicação
I2C (SDA e SCL), um ponto de alimentação +5VDC e um GND
(terra).
O LED1 ajuda a demonstrar que o circuito está ligado.R1
é o resistor limitador de corrente para LED1. Esta
aparente alegoria tem um simples motivo: como a
alimentação pode ser controlada de forma externa
(através do circuito principal) e as memórias são do
tipo “não voláteis”, é possível utilizar mais de um
banco memo_uC num mesmo circuito. Se usarmos, por
exemplo, 8 bancos de 2 kBytes teremos um total de 16
kBytes de memória disponíveis.
O LED2 foi inserido no circuito para demonstrar a
presença de comunicação entre o banco de memória e o
circuito principal. Seu controle é feito através de Q1.
Sempre que houver a presença do sinal SCL no barramento
e a placa estiver devidamente alimentada (+5VDC), o LED
irá piscar a uma frequência igual a usada no
barramento. Na menor velocidade (modo standart)
o período será igual a 0,000001 s. A esta velocidade o
piscar é quase que imperceptível, e o usuário terá
apenas a impressão do LED estar simplesmente ligado. R2
é o resistor de polarização de base para Q1 (que
controla LED1). O resistor R3 mantém o transistor Q1 em
corte, e consequentemente LED2 apagado, quando o sinal
SCL não estiver presente.
Os resistores de pull-up necessários as vias de
comunicação SDA e SCL, pois estas são do tipo open
drain, não estão presentes na placa, mas são
necessários e devem ser previstos no projeto do circuito
principal que fará uso do memo_uC.
MONTAGEM
A figura acima mostra minha sugestão do lay-out
para a confecção de um circuito impresso. Este foi o
desenho usado em meu protótipo. Você se preferir poderá
montar o banco em uma placa do tipo padrão ou ainda em
uma matriz de contatos. A escolha é livre.
Comece por soldar os resistores R1, R2 e R3. Os mesmos
não são polarizados e não requerem preocupação maior ao
montá-los na placa. Apenas tome cuidado para não
trocá-los entre si, já que suas resistências são
diferentes. Caso tenha dúvida use a lista de materiais
para identificá-los.
Os capacitores C1 a C8 são cerâmicos e também não são
polarizados. Todos possuem o mesmo valor e você não terá
dificuldades em sua montagem na placa. O capacitor C9 é
do tipo eletrolítico e polarizado. Tenha cuidado para
não montá-lo invertido na placa.
O transistor Q1 também requer um maior cuidado para não
montá-lo invertido. LED1 e LED2 também precisam do mesmo
cuidado. Como sugestão é interessante que LED1 seja
vermelho e LED2 verde, por exemplo. Com cores diferentes
fica mais fácil identificar como a placa está sendo
operada.
Os CIs também são polarizados e merecem todo cuidado na
sua inserção na placa. O uso de suportes para os mesmos
é altamente recomendável, pois facilita a conexão dos
CIs de maneira segura e rápida.
O conector JP1 usado em nosso protótipo é do tipo “barra
de pinos”. Caso você não o tenha em mãos poderá usar
fios para conectar a placa ao seu circuito principal.
UM CIRCUITO
AUXILIAR PARA TESTES
Para poder testar o memo_uC eu desenvolvi um pequeno
circuito para uso com a placa, presente na figura
abaixo. A ideia é interagir com o banco de memória
memo_uC através do canal serial de um PC, usando um
microcontrolador PIC16F628A como interface entre o PC e
o memo_uC.
O circuito de teste basicamente é composto de um
microcontrolador PIC16F628A. Escolhi este
microcontrolador para os testes por acreditar (na época
- 2007) ser este um dos mais difundidos , porém nada
impede que cada um faça os seus testes utilizando seu
microcontrolador preferido.
O LED presente no circuito é apenas uma alegoria que
ajuda a informar que o circuito está em operação, pois o
mesmo pisca a uma frequência de 1 Hz. O MAX232 faz a
conversão dos níveis de tensão presentes na porta RS-232
de um PC para o padrão TTL presente nos pinos de I/O do
microcontrolador ligados a sua USART interna e
vice-versa. Aconselho a montagem do circuito em uma
matriz de contados, já que o mesmo é apenas para testes.
PROGRAMA PARA O CIRCUITO AUXILIAR
Mais abaixo em "downlods" disponibilizei o
programa original memo_crtl_24c01.c desenvolvido na
linguagem C. Utilizei para montagem e compilação deste
exemplo o compilador PICC CCS (http://www.ccsinfo.com).
A empresa CCS fornece uma versão demo que poderá ser
utilizada por você em seus testes. Esta versão possui
algumas limitações como os tipos de microcontroladores
habilitados e também no tamanho máximo do programa a ser
compilado, porém é uma boa alternativa para aqueles que
desejam “entrar” no mundo da programação na Linguagem C,
mais especificamente dedicada aos microcontroladores PIC
Microchip.
É importante compreender que você não precisa compilar o
código fornecido para realizar os seus testes, conforme
proposto. Junto ao código fonte você encontrará o
arquivo memo_crtl_24c01.hex que poderá ser utilizado
para gravar o microcontrolador de forma direta, sem a
necessidade de uma re-compilação. O uso do compilador só
será necessário se você desejar alterar o programa
fornecido.
Nota: Eu teno o hábito de
inserir linhas de comentários em meus programas no
intuito de ajudar na compreensão do mesmo. Estas
linhas devem ser lidas atentamente por quem deseja
utilizar tais códigos fontes. Elas contem
informações sobre a versão do compilador e pinos
de I/O utilizados, além de detalhes a respeito do
funcionamento das funções presentes no código,
entre outras. Ao estudar um código fonte meu, use
as linhas de comentários!
O programa foi ricamente comentado, para ajudar na sua
compreensão. Porém a seguir falareis um pouco sobre o
seu funcionamento, descrevendo as operações mais
importantes do programa.
Um detalhe a ser comentado sobre este programa é o uso
da biblioteca 24C01.c, fornecida pela CCS no pacote do
compilador (..\PICC\Drivers\24C01.c). Junto ao código
fonte fornecido mais abaixo você encontrará a mesma,
devidamente adaptada (foram inseridos cabeçalhos
explicando o funcionamento de cada função para auxiliar
o estudo das mesmas por parte de você).
Na figura abaixo temos o fluxograma que descreve a
operação do programa desenvolvido para o exemplo
proposto neste artigo.
O programa começa configurando o microcontrolador,
definindo o modo de uso dos pinos (entrada ou saída), o
tempo para o WDT (Watch Dog Timer - relógio cão de
guarda que evita que o programa se perda e assim que o
microcontrolador trave por algum motivo), a configuração
do Timer1 (interrupção responsável pelo “piscar” do LED)
e a habilitação da USART do microcontrolador (com
interrupção para recepção dos dados através da RS-232).
Após a configuração do microcontrolador, o programa
configura as portas de comunicação com as memórias
EEPROM. As funções de controle para as memórias foram
aproveitados de uma biblioteca do próprio CCS-C
(compilador selecionado para os testes). O módulo
24C01.c sofreu apenas algumas modificações para se
adequar ao funcionamento com o memo_uC e recebeu também
comentários em nossa língua para facilitar a compreensão
dvocê. O estudo deste arquivo é recomendável avocê que
quer saber como a comunicação entre o microcontrolador
em questão e as memórias é feita.
As operações mais importantes do
programa são tratadas através de interrupções. Uma
destas operações é realizada pelo Timer1 do
microcontrolador. Este temporizador gera uma interrupção
no microcontrolador a cada 0,526 segundos (com clock
operando a 4MHz). Quando isso acontece a função
trata_int_t1() é chamada. Esta função verifica quantas
interrupções aconteceram: se duas (2 x 0,526 = 1,052
segundos) a função troca o estado atual do LED,
fazendo-o piscar na freqüência de 1 Hz.
Temos no programa também a interrupção para tratamento
de um dado qualquer recebido do PC. você notará que
sempre que um dado for recebido, o microcontrolador
efetuará a leitura do mesmo e realizará uma ação. Esta
tanto pode ser imediata e ligada ao banco memo_uC como
também o envio de uma outra mensagem complementar
solicitando mais um dado. Estas mensagens basicamente
servem como ajuda para o usuário com os comandos que
podem ser utilizados.
Temos seis opções válidas:
1 – Seleciona banco (1 a 8): permite selecionar em qual
memória (CI1 a CI8) será gravado ou lido um dado;
2 – Apaga banco (1 a 8): permite apagar a memória (CI1 a
CI8) selecionada;
3 – Grava dado (endereço): permite gravar um dado no
endereço solicitado, dentro do banco previamente
selecionado;
4 – Apaga dado (endereço): permite apagar um dado no
endereço solicitado, dentro do banco previamente
selecionado.
5 – Dump da memória em ASCII: mostra o conteúdo da
memória (CI1 a CI8) previamente selecionado, no formato
ASCII.
6 - Dump da memória em HEX: mostra o conteúdo da memória
(CI1 a CI8) previamente selecionado, no formato
hexadecimal.
São duas as interrupções habilitadas
no programa. Na linha #priority RDA0, timer inserida no
começo do arquivo memo_crtl_24c01.h, definimos qual
interrupção tem maior prioridade. No caso definiu-se a
interrupção da USART.
TESTE E USO
Para que você possa realizar, com êxito, o teste proposto
neste artigo são necessários os seguintes itens:
• Circuito de testes montado;
• Microcontrolador devidamente gravado
com o programa de teste;
• Computador Pessoal (PC) com uma porta
serial RS-232 disponível;
• Um cabo de comunicação RS-232
(facilmente encontrado em lojas de informática);
• Programa Terminal instalado no PC
como, por exemplo, o Hyper Terminal do Windows,
devidamente configurado para operar com a porta COM livre
em seu PC, velocidade de 9600 bps, sem paridade, número de
bits de comunicação igual a 8, número de stop bits igual a
1 e nenhum controle de fluxo (9600, n, 8, 1).
Após a montagem de
ambos os circuitos (memo_uC e circuito de testes, este
último em uma matriz de contatos ou placa padrão), é
sempre aconselhável uma minuciosa verificação. Jamais
diga a si mesmo “tenho certeza absoluta de que tudo está
certo” sem ao menos ter feito uma boa verificação.
Cometer enganos é comum e estes podem ser corrigidos
antes de qualquer teste, evitando a perda de
componentes, tempo e dinheiro. Use o bom senso e sempre
verifique suas montagens!
A figura abaixo, mostra a montagem do
circuito de testes realizada em uma matriz de contatos,
juntamente com a placa memo_uC. Nesta montagem usei
também a placa “Conversor
RS-232/TTL duplo”, publicada na edição número 116
da revista Eletrônica Total para realizar a comunicação
entre o microcontrolador e o PC.
Conecte o cabo
descrito anteriormente entre o circuito e seu PC. Rode
um programa “terminal” como o Hyper Terminal do
Windows®, por exemplo.
Após a configuração do programa
terminal, alimente o circuito. O LED deverá piscar na
frequência descrita (1 Hz). Neste momento você poderá
ver o menu para uso da aplicação conforme descrito
anteriormente.
Um pequeno teste pode ser feita da
seguinte maneira:
- Selecione o banco 2;
- Grave um dado qualquer em
um endereço (anote onde o gravou)
- Selecione o banco 1;
- Grave um outro dado em um
endereço (anote isto também);
- Selecione novamente o
banco 2;
- Faça o dump da
memória deste banco;
- Apague o dado no endereço
usado;
- Faça um dump novamente;
- Agora selecione o banco 1
e repita as operações 6 a 8.
Se tudo correu
bem, você terá conseguido inserir um dado qualquer em um
ponto da memória e em seguida verificá-lo através do
comando dump. Em seguida o dado foi removido da
memória e isto também pôde ser verificado através do
comando dump. você também terá comprovado o uso
de mais de um banco de memória (CI).
Para aplicar o memo_uC em seus
projetos, você terá de desenvolver um programa de
controle. Para isto poderá utilizar o código fonte
fornecido realizando algumas alterações para que a
adaptação seja feita com sucesso. Deixaremos isso por
conta de cada um, já que cada um tem suas próprias
necessidades.
Apenas para exemplificar, vamos supor
que uma determinada aplicação precisar guardar dados
coletados ao longo do tempo. Estes dados terão de ser
armazenados de forma sequencial e assim, a aplicação
principal irá encarar o memo_uC como um banco de memória
único com tamanho de x Kbytes. Para que isso seja feito
este programa terá de guardar em uma memória auxiliar
qual CI foi trabalho por último e onde está o último
ponto de memória ocupada deste CI. Isto pode ser feito
de duas maneiras:
- O programa lê todos os
CIs de maneira sequencial até encontrar um byte
igual a “FFH” (byte inserido em um endereço vazio na
memória);
- O programa usa uma ou
mais posições do próprio banco memo_uC (os dois
últimos bytes do CI8, por exemplo) para guardar o
número do banco e posição de memória usados pela
última vez.
Outras formas também podem ser
experimentadas. Como dito anteriormente o uso do memo_uC
não tem limites. Tudo depende da criatividade e
conhecimentos de cada um.
CONCLUSÃO
Com algumas
memórias de custo bem acessível é possível montar um
banco de memória externo com tamanho adequado para o uso
em vários projetos. O uso de memórias seriais com um
protocolo de comunicação simples e poderoso como o I2C
favorece ainda mais o projeto final. Esperamos ter
colaborado com você desenvolvedor, seja este um
hobista/estudante ou profissional da área, pois as dicas
apresentadas neste artigo são para todos! Bons estudos e
testes! Até a próxima!
DOWNLOADS
- Circuito
eletrônico
- Lay-out
para circuito impresso (método
da transferência térmica)
-
Lay-out para circuito impresso (método
manual)
- Programa
de testes (pacote original 2006-2007)
- Lista
de materiais
Este projeto foi publicado, com minha autorização, na Revista "Eletrônica Total nr
126" de Setembro/Outubro de 2007.
Especificações:
- Cérebro - qualquer microcontrolador - Memória - até 64KBytes - Tipo - EEPROM - Programa - A sua escolha! :P
Copyright
deste conteúdo reservado para Márcio José Soares e
protegido pela Lei de Direitos Autorais LEI N° 9.610, de
19 de Fevereiro de 1998. É estritamente proibida a
reprodução total ou parcial do conteúdo desta página em
outros pontos da internet, livros ou outros tipos de
publicações comerciais ou não, sem a prévia autorização
por escrito do autor.
|