Cache de Memória – Arquitetura

O funcionamento e o desempenho do cache de memória varia de acordo com o método organizacional que é utilizado pelo controlador de cache.

Existem basicamente três modelos: Cache com mapeamento direto (direct-mapped cache); Cache completamente associativo (full-associative cache);  Cache associativo por grupos (set-associative cache).

É devido ao tipo de organização utilizado pelo controlador de cache que encontramos diferenças de desempenho entre chipsets, bem como entre processadores. Não podemos nos esquecer de que os processadores a partir do 486 têm um pequeno cache de memória interno (L1). Dependendo do método utilizado pelo controlador desse cache, poderá ser mais eficiente, aumentando o desempenho do micro.

No caso dos processadores que têm o cache L2 externo, temos dois controladores de cache: controlador de cache L1, que está dentro do processador, e controlador de cache L2, que está no chipset da placa-mãe. Os dois controladores de cache podem utilizar mecanismos e arquiteturas diferentes.

Cache com mapeamento direto (direct-mapped cache)

Este é o esquema mais simples de se implementar. O controlador de cache divide o cache de memória em blocos do tamanho de uma linha, para facilitar o acesso pelo processador em seu modo burst. Normalmente cada linha do cache tem 256 bits (32 bytes), ou seja, quatro dados de 64 bits.

A memória RAM será virtualmente dividida em blocos do tamanho da memória cache. Se a memória cache secundária do micro for de 256 KB, a memória RAM será dividida em blocos de 256 KB. Um micro com 16 MB de RAM terá sua memória dividida em 64 blocos de 256 KB, por exemplo. Se esse mesmo micro tivesse 512 KB de memória cache, a memória RAM seria dividida em 32 blocos de 512 KB.

Cada linha do cache apontará a sua linha correspondente dentro do bloco — ou seja, a primeira linha do cache armazena os dados da primeira linha do bloco de memória RAM, e assim analogamente para as demais linhas.

Se o cache for de 256 KB, será dividido em 8.192 linhas (256 KB = 262.144 bytes — como cada linha armazena 32 bytes [256 bits], o cache e cada bloco de memória serão divididos em 8.192 linhas). Um cache de 512 KB será dividido em 16.384 linhas. A figura abaixo ilustra o funcionamento do cache de memória com mapeamento direto.

Funcionamento de um cache de 256 KB com mapeamento direto em um micro com 16 MB de RAM

O cache pode ser usado para acessar qualquer bloco. Entretanto, cada linha do cache aponta exclusivamente para a linha de mesmo número na memória RAM, independentemente do bloco — isto é, tanto no primeiro bloco, quanto no segundo, no terceiro ou no último, a quinta linha ocupará a quinta linha do cache.

Então é impossível ter no cache dois ou mais dados que ocupem o mesmo número de linha, independentemente do bloco que ocupam. Por exemplo, o conteúdo da décima linha do primeiro bloco e o conteúdo da décima linha do vigésimo bloco nunca poderão estar presentes simultaneamente no cache, já que serão obrigatoriamente armazenados na décima linha do cache. O último dado lido é o que prevalecerá.

Com isso, o aumento do tamanho do cache de memória torna o cache mais eficiente, aumentando o desempenho do micro. Como o cache passará a ter mais linhas (como vimos, um cache de 256 KB tem 8.192 linhas, enquanto um de 512 KB tem 16.384) e a memória será dividida em menos blocos (em um micro com 16 MB de RAM e cache de 256 KB, a memória é dividida em 64 blocos; aumentando o cache para 512 KB, a memória passa a ser dividida em 32 blocos), ocorrerão menos situações como a descrita no parágrafo anterior, ocasionando menos situações onde o processador necessite ler os dados diretamente da memória RAM porque o dado não está carregado no cache.

A organização do cache com mapeamento direto é simples. Em uma memória estática extra, armazenamos um “diretório” do conteúdo do cache. Essa memória — chamada tag — serve para o controlador de cache saber se um determinado dado já está ou não armazenado no cache. Por esse motivo, em geral, o tempo de acesso do tag é mais baixo.

No cache com mapeamento direto, o tag é muito simples de se construir, já que cada linha do cache aponta para uma posição de memória bem definida (o endereço 1 representa a linha 1, o endereço 2 representa a linha 2, e assim sucessivamente) — ou seja, para cada posição do tag (o “diretório” do cache de memória), teremos que armazenar somente a informação de qual bloco da memória RAM a linha foi copiada.

Conseqüentemente, a verificação para saber se um dado está ou não armazenado no cache é rápida, muito embora o esquema do cache em si apresente baixo desempenho, já que muitas vezes os dados solicitados não estão disponíveis.

Cache completamente associativo (full-associative cache)

No cache completamente associativo, as linhas do cache de memória poderão armazenar qualquer linha da memória RAM, independentemente de sua localização. Isto é, a memória RAM não é dividida em blocos, somente em linhas, e cada linha do cache pode armazenar qualquer linha da memória. Com isso, a probabilidade de um dado estar presente aumenta, pois não há situações “proibidas” como no cache com mapeamento direto.

Entretanto, o circuito de verificação do controlador de cache será muito mais complexo e o tag, muito maior, já que em uma linha do cache poderá estar armazenada qualquer linha da memória RAM.

Embora esse esquema em um primeiro instante pareça ser melhor do que o mapeamento direto, o controlador de cache pode demorar muito tempo verificando se um dado está ou não presente no cache, ocorrendo situações em que, paradoxalmente, seria muito mais rápido acessar o dado diretamente em memória RAM do que buscá-lo no cache.

Cache associativo por grupos (set-associative cache)

O cache associativo por grupos é atualmente a solução que apresenta melhor desempenho prático e, por isso, essa arquitetura atualmente é a mais usada. Reúne as vantagens dos dois modelos anteriores.

O controlador de cache divide o cache de memória em unidades menores. Um cache associativo de quatro vias (four-way) faria com que um cache de memória de 256 KB fosse dividido em quatro caches independentes de 64 KB. Nesse caso, a memória RAM seria igualmente dividida em blocos de 64 KB.

Esses caches independentes funcionarão no esquema de mapeamento direto. Porém, ao contrário do verdadeiro esquema de mapeamento direto, você poderá encontrar, no cache de memória, os dados de duas linhas de mesmo número de ordem, até o limite máximo do número de unidades em que o cache de memória foi dividido — ou seja, em um cache associativo de quatro vias, podem-se armazenar até quatro linhas de mesmo número de ordem.

Em outras palavras, para esse exemplo dado, é como se o micro tivesse quatro caches de 64 KB totalmente independentes um do outro, cada um funcionando no esquema de mapeamento direto.

Write Through

Embora o cache aumente muito o desempenho do micro (pois o processador é capaz de acessá-lo sem utilizar wait states e sem precisar usar a freqüência do barramento local, quando o cache é integrado ao processador), antigamente só era utilizado em operações de leitura da memória, ou seja, quando o processador buscava dados nela.

Em operações de escrita, o processador escrevia o dado diretamente na memória (utilizando wait states e a freqüência de operação externa do processador), usando o cache como um dispositivo de segurança: o controlador de cache verificava se o dado escrito em memória é exatamente igual ao dado que foi escrito simultaneamente no cache de memória.

Esse método de atualização da memória RAM é chamado Write Through (escrita direta) e é pouco utilizado hoje em dia.

Write Back

O método ideal de atualização da memória chama-se Write Back, que utiliza o cache de memória tanto para ler quanto para escrever em memória. Esse é o método atualmente utilizado pelo cache de memória. Há, no entanto, uma grande dificuldade para manter os dados da memória iguais ao do cache, pois, quando o processador escrever uma quantidade razoável de dados no cache, o conteúdo da memória RAM estará temporariamente defasado, até que o processador libere o barramento para que o controlador de cache atualize definitivamente a memória RAM. Isso pode atrapalhar operações de DMA e bus mastering, que acessam diretamente a memória RAM. Por esse motivo, o controlador de cache é bem mais complexo. Atualmente todos os controladores de cache utilizam essa arquitetura.

Observação: A expressão Write Back diz respeito à tecnologia de construção do controlador de cache do micro e não tem relação direta com os circuitos do cache de memória. Não existe a expressão memória cache Write Back, que é utilizado sem sentido em circuitos de memória cache falsificados, como veremos mais adiante.

02/11/2010