Portal - FPGA para Todos

Cronômetro - Placa DE0

Cronômetro - Placa DE0®

 

 

O projeto apresenta a implementação de um cronômetro de minutos e segundos na placa DE0®, utilizando os displays de 7 degmentos para a vizualização. O cronômetro também utilizará três botões, um de pausa, um de reset e um para parar a contagem.

Esse artigo demonstra a implementação de um projeto em VHDL, o qual foi simulado com o Modelsim-Altera® utilizando a simulação por testbench

Equipamento utilizado: Placa DE0®.

Descrição do Funcionamento

O projeto gerará um clock de 1Hz para incrementar os valores dos segundos. Quando a contagem chegar a 60, é necessário "zerar" a contagem de segundos incrementar o contador de  minutos.

Para o display de 7 segmentos será necessário um decodificador para mostrar os valores na saída. O botão de pausa congelará o valor mostrado nos displays de 7 segmentos, porém a contagem continuará. O botão stop interromperá a contagem, a qual pode ser retomada pressionando novamente este botão. O botão de reset reinicia a contagem.

Descrição em VHDL

Para a implementação do projeto, precisa-se de quatro entradas e 28 saídas, destinadas aos 4 displays de 7 segmentos e uma para o ponto do display central, o qual sempre estará em nível lógico baixo, pois os displays são do tipo anodo comum. O clock interno de 1Hz é gerado por um preescaler de 50M, pois a placa DE0® possui um clock de 50MHz.

O projeto possui 4 entradas e 29 saídas, declaradas na entidade:

entity cronometro is
port
(
    clock: std_logic;
    resetn, pausa, stop: in std_logic;
    seg_7_1, seg_7_2, seg_7_3, seg_7_4: out STD_LOGIC_vector(0 to 6);
    H : out std_logic
);
end entity;

O primeiro bloco do código tem como função implementar a lógica do comando de parada. Quando o botão é pressionado a variável flag muda o seu valor: se estava contando para de contar; se estava parado retorna a contar. O processo principal depende da variável flag para contar ou não.

if stop'event and stop = '0' and flag ='0' then
    flag := '1';
elsif stop'event and stop = '0' and flag = '1' then
    flag := '0';
end if;

elsif clock'event and clock = '1' then 
    if flag = '0' then

O processo principal utiliza as variáveis apresentadas abaixo, sendo os 4 bits menos significativos dos vetores destinados as unidades e os 3 bits mais significativos destinados as dezenas. A flag funciona como registrador de estado, indicando se está contando ou está parado. A variável cont funciona como preescaler.

process(clock, resetn, pausa, stop)
variable cont : integer range 0 to 50000000 :=0;
variable var_min : std_logic_vector(6 downto 0) := "0000000";
variable var_seg : std_logic_vector(6 downto 0) := "0000000";
variable flag : std_logic := '0';

O bloco seguinte do código é reponsavél pelo comportamento quando o botão de reset está pressionado. São atriubuido os valores iniciais das varáveis

if resetn = '0' then
    var_min := "0000000";
    var_seg := "0000000";
    cont := 0;
    flag := '0';

Quando o reset não está pressionado, o programa entra na rotina principal. Primeiramente é implementado o presescaler para a incrementar os segundos. O passo seguinte é verificar o estouro de contagem, neste caso 10 nas unidades e 6 nas dezenas. 

cont := cont + 1; 
    if cont = 50000000 then 
        cont :=0; 
        var_seg := var_seg + "0000001"; 
        if var_seg (3 downto 0) = "1010" then 
            var_seg (6 downto 4) := var_seg(6 downto 4) + "001"; 
            var_seg (3 downto 0) := "0000"; 
            if var_seg(6 downto 4) = "110" then 
                var_min := var_min + "0000001"; 
                var_seg (6 downto 4) := "000"; 
                if var_min (3 downto 0) = "1010" then 
                    var_min(6 downto 4) := var_min(6 downto 4) + "001"; 
                    var_min(3 downto 0) := "0000"; 
                    if var_min(6 downto 0) = "110" then 
                        var_min(6 downto 0) := "000"; 
                    end if; 
                end if; 
            end if; 
        end if; 
    end if;

Ao final do processo, se o botão de pausa não está pressionado, atualiza-se os valores dos sinais.

if pausa /= '0' then
    min <= var_min;
    seg <= var_seg;

No final do código é implementado um contador para os displays de 7 segmentos. O decodificador tem como entrada o valor númerico e traduz para os segmentos que precisam ser acendidos no display. Como o display é de anodo comum, os segmentos acesos são os que estão em nível lógico baixo.

with min (3 downto 0) select
    seg_7_1 <= "0000001" when "0000",
        "1001111" when "0001",
        "0010010" when "0010",
        "0000110" when "0011",
        "1001100" when "0100",
        "0100100" when "0101",
        "0100000" when "0110",
        "0001111" when "0111",
        "0000000" when "1000",
        "0000100" when "1001",
        "1111111" when others;
with min (6 downto 4) select
    seg_7_2 <= "0000001" when "000",
        "1001111" when "001",
        "0010010" when "010",
        "0000110" when "011",
        "1001100" when "100",
        "0100100" when "101",
        "0100000" when "110",
        "0001111" when "111",
        "1111111" when others;
with seg (6 downto 4) select
    seg_7_3 <= "0000001" when "000",
        "1001111" when "001",
        "0010010" when "010",
        "0000110" when "011",
        "1001100" when "100",
        "0100100" when "101",
        "0100000" when "110",
        "0001111" when "111",
        "1111111" when others;
with seg (3 downto 0) select
    seg_7_4 <= "0000001" when "0000",
        "1001111" when "0001",
        "0010010" when "0010",
        "0000110" when "0011",
        "1001100" when "0100",
        "0100100" when "0101",
        "0100000" when "0110",
        "0001111" when "0111",
        "0000000" when "1000",
        "0000100" when "1001",
        "1111111" when others;

Simulação

Para simular o funcionamento do código fonte é necessário gerar os pulsos de clock e emular o pressionamento dos botões utilizados no projeto. Para que a simulação ocorra mais rapidamente pode diminuir o preescaler do código fonte. Neste teste será diminuido para 20 ms.

Primeiramente declare-se o port map.

port map
(
    clock, resetn, pausa, stop,
    min2, min1, seg2, seg1, H
);

O primeiro bloco emula o clock.

gera_clock: process 
    begin 
    for cont in 0 to 20000000 loop 
        CLOCK <= '0'; 
        wait for 1 ns; 
        CLOCK <= '1'; 
        wait for 1 ns; 
    end loop; 
    wait; 
end process;
 

O segundo bloco tem por funcionalidade emular o pressionamento dos botões.

simulacao: process
    begin
    resetn <= '1';
    pausa <= '1';
    stop <= '1';
    -- simulando reset
    resetn <= '0';
    wait for 100ns;
    resetn <='1';
    wait for 2 ms;
    -- simulando pausa
    pausa <= '0';
    wait for 1ms;
    pausa <='1';
    wait for 1 ms;
    --simulando stop
    stop <= '0';
    wait for 1 ms;
    stop <= '1';
    wait for 1 ms;
    wait for 1 ms;
    stop <= '1';
    wait for 1 ms;
    resetn <= '0';
    wait for 10ns;
    resetn <= '1';
    wait for 5ms;
    wait;

Abaixo estão apresentadas as formas de onda obtidas na simulação.

 sim_1

Figura 2: Instante do incrmento na dezena dos segundos.

sim_2

Figura 3: Instante do pressionamento do botão de pausa.

sim_3

Figura 4: Instante em que o botão de pausa é solto.

sim_4

Figura 5: Instante em que é pressionado o botão de stop..

sim_5

Figura 6: Instante em que o botão de stop é solto.

sim_6

Figura 7: Instante em que o botão de reset é pressionado.

Montagem e Roteamento

O único equipamento necessário para a implementação do projeto é a placa DE0®. Os recursos utilizados são os 4 displays de 7 segmento e os 3 push bottons. A figura abaixo apresenta a distribuição de pinos, utilizando como base o manual da placa. O FPGA presente na placa é o EP3C16F484 da família Cyclone III.

Cronometro_DE0

Figura 8: Cronômetro implementado na placa DE0®

 pinagem

Figura 9: Atribuição de pinos

Teste e Gravação

A gravação pode ser feita seguindo os procedimentos indicados no manual da placa DE0® ou seguindo o tópico de gravação no tutorial. O teste de funcionamento é mostrado no início do artigo.

Arquivos de Projeto

Links Externos

Quem está Online

Temos 99 visitantes e Nenhum membro online

Apoio

Login Form