Atualmente, a memória Flash é usada para armazenar o código do programa e a EEPROM (Memória somente leitura apagável eletricamente) é usada para armazenar dados persistentes. Há cerca de 30 anos, antes da criação do Flash, as EEPROMs eram usadas para armazenar o código do programa.
Na verdade, a ROM (memória somente leitura) veio primeiro, depois o PROM (ROM programável, apenas uma vez), EPROM (PROM apagável com luz UV), EEPROM e, finalmente, o Flash. As ROMs ainda são usadas para aplicativos de alto volume e baixo custo (por exemplo, cartões comemorativos).
A diferença importante com os microcontroladores atuais é que geralmente não é possível executar código fora da EEPROM, e é estranho os programas armazenarem dados em flash. (Os dados são armazenados em flash quando, por exemplo, você usa a palavra-chave "const" em uma declaração de dados ou define uma string, mas isso é tratado nos bastidores pelo compilador e vinculador.)
A área EEPROM pode ser usada para manter a configuração ou outros dados que você deseja disponibilizar durante as reinicializações, incluindo se o microcontrolador perdeu energia e depois é ligado novamente. Funcionalmente, você pode pensar na EEPROM como um disco rígido ou cartão SD muito pequeno.
Em microcontroladores sem EEPROM, é possível armazenar dados persistentes na memória flash, mas isso se torna difícil, uma vez que os microcontroladores não foram realmente projetados para isso, e você precisa encontrar um local especial que não interfira no código do programa e deixar isso de lado. com o vinculador. Além disso, como mencionado abaixo, você geralmente pode atualizar a EEPROM muitas vezes mais do que o flash.
Se você programar dados em flash, isso não significa que você pode acessar os dados como variáveis em seu programa C, porque não há como informar ao compilador onde essas variáveis estão no seu código (ou seja, você não pode vincular uma const variável para esta área do flash.) Portanto, a leitura deles deve ser feita através do conjunto especial de registros que são usados para escrevê-los. Observe que esta restrição também se aplica aos dados na EEPROM, portanto, não possui vantagens nesse sentido.
Para programar o flash ou a EEPROM, primeiro um bloco de memória deve ser apagado. Então é programado. Para o flash, a escrita também costuma ser feita um bloco de cada vez. Para EEPROMs, isso pode ser feito por blocos ou um byte por vez, dependendo do microcontrolador.
Para flash e EEPROMs, existe um número máximo de vezes que você pode atualizá-los antes de esgotar a memória. Esse número é fornecido na folha de dados como um valor mínimo garantido. Geralmente é muito mais alto para EEPROMs do que para memória flash. Para flash, vi números tão baixos quanto 1000. Para EEPROMs, vi números tão altos quanto 1.000.000.
Uma vantagem das EEPROMs sobre o flash é que você pode apagá-las muito mais vezes do que o flash.
"Auto-programável no sistema" significa simplesmente que o microcontrolador pode atualizar seu próprio flash durante a execução. O recurso geralmente é usado para atualizar o código no campo. O truque é que você precisa deixar algum código no sistema enquanto o programa principal está sendo atualizado, chamado de carregador de inicialização. Esse esquema é usado no sistema Arduino para programar o chip.
Acrescentarei mais algumas informações à excelente resposta de @tcrosley.
O ATmega16 implementa uma arquitetura de Harvard , isto é, uma topologia de sistema em que a memória de dados é separada da memória do programa. Citando o parágrafo relevante da folha de dados do Atmega16 (página 8):
A arquitetura de Harvard tem a vantagem de não haver contenção de barramento entre os ciclos de busca de instruções e os ciclos de acesso a dados, uma vez que dados e instruções não compartilham o mesmo barramento, como na arquitetura de PC convencional.
Portanto, a memória flash é usada como memória do programa, enquanto a memória de dados é dividida entre SRAM (para dados transitórios, como pilha de chamadas de funções e heap - se você estiver programando em C, por exemplo) e a EEPROM (para armazenamento permanente) .
fonte