close
Ir para o conteúdo

Cache do processador

Origem: Wikipédia, a enciclopédia livre.

Cache do processador (em inglês: CPU cache) é uma memória cache integrada ao processador ou situada muito próxima dele, usada para reduzir o tempo médio de acesso a instruções e dados. Ela mantém cópias de pequenas porções da memória principal que provavelmente serão reutilizadas. Como o acesso à cache costuma ter latência menor e maior largura de banda que o acesso à memória principal, uma alta taxa de acertos pode diminuir o tempo em que a unidade central de processamento (CPU) aguarda dados.[1]

Caches de processador são normalmente organizadas em uma hierarquia de níveis. Os níveis mais próximos dos núcleos são menores e mais rápidos, enquanto os níveis posteriores tendem a ser maiores e mais lentos. A organização exata — capacidade, número de níveis, compartilhamento entre núcleos e separação entre instruções e dados — depende da microarquitetura.[2]

Funcionamento

[editar | editar código]

Os dados são transferidos entre a memória principal e a cache em unidades de tamanho fixo chamadas linhas de cache ou blocos. Cada entrada armazena uma linha de dados e informações de controle, como a etiqueta (tag) que identifica o endereço correspondente, bits de validade e, em caches com escrita postergada, um bit que indica modificação.[3]

Quando o processador solicita um endereço, o controlador consulta a cache:

  • há um acerto (cache hit) se a linha correspondente está presente e válida; o dado pode então ser fornecido pela cache;
  • há uma falta (cache miss) se a linha não está disponível; ela precisa ser obtida de outro nível da hierarquia ou da memória principal e, em geral, é inserida na cache.

O custo de uma falta é chamado de penalidade de falta. O tempo médio de acesso depende do tempo de acerto, da taxa de faltas e dessa penalidade. A capacidade, a associatividade e o tamanho das linhas influenciam tanto a taxa de faltas quanto o custo e a complexidade do circuito.[1]

Localidade de referência

[editar | editar código]

A eficácia da cache decorre principalmente do princípio da localidade. A localidade temporal é a tendência de um dado ou uma instrução recentemente acessados serem usados novamente em pouco tempo. A localidade espacial é a tendência de endereços próximos ao endereço atual serem acessados em seguida. Por isso, ao ocorrer uma falta, transfere-se uma linha inteira, e não apenas o byte ou a palavra solicitada.[1]

Alguns processadores também empregam pré-busca (prefetching) por hardware ou por instruções de software para trazer linhas antes que sejam explicitamente solicitadas. Uma previsão correta pode ocultar parte da latência; uma pré-busca inadequada pode consumir largura de banda e expulsar dados úteis.[2]

Organização e mapeamento

[editar | editar código]

Uma cache é dividida em conjuntos. O endereço de memória determina o conjunto no qual uma linha pode ser armazenada, e a etiqueta distingue as linhas que podem ocupar esse conjunto. As organizações mais comuns são:[3]

  • mapeamento direto: cada bloco da memória pode ocupar uma única posição;
  • totalmente associativa: um bloco pode ocupar qualquer posição da cache;
  • associativa por conjuntos: cada bloco é mapeado para um conjunto e pode ocupar qualquer uma das vias desse conjunto.

O mapeamento direto exige comparação simples, mas pode sofrer mais faltas por conflito. A associação por conjuntos reduz esses conflitos ao custo de comparações adicionais. Caches totalmente associativas são mais complexas e, por isso, são mais comuns em estruturas pequenas.

Quando todas as vias de um conjunto estão ocupadas, uma política de substituição escolhe a linha a remover. Entre as políticas possíveis estão LRU (menos recentemente usada), aproximações de LRU, escolha aleatória e políticas adaptativas. A implementação adotada varia conforme os objetivos de desempenho, consumo de energia e área do circuito.[3]

Hierarquia de níveis

[editar | editar código]

Processadores modernos costumam usar vários níveis de cache. A cache L1 é a menor e de menor latência e frequentemente é separada em cache de instruções e cache de dados. Os níveis L2 e L3 são em geral maiores; podem ser privados de um núcleo ou compartilhados por vários núcleos. Nem todas as arquiteturas possuem os mesmos níveis ou as mesmas relações de inclusão entre eles.[4]

Em uma hierarquia inclusiva, as linhas de um nível superior também estão presentes em um nível inferior maior; em uma hierarquia exclusiva, procura-se evitar a duplicação entre níveis. Há ainda organizações não estritamente inclusivas nem exclusivas. Essas escolhas afetam a capacidade efetiva, a manutenção da coerência e o comportamento durante substituições.[3]

Políticas de escrita

[editar | editar código]

As duas políticas básicas para um acerto de escrita são:[1]

  • escrita simultânea (write-through): a alteração é enviada à cache e ao nível seguinte da hierarquia; um buffer de escrita pode evitar que o processador espere a conclusão de todas as operações;
  • escrita postergada (write-back): a alteração é feita inicialmente apenas na cache. A linha é marcada como modificada (dirty) e enviada ao nível seguinte quando for substituída ou explicitamente limpa.

Em uma falta de escrita, a política alocar na escrita (write-allocate) carrega a linha na cache antes de modificá-la. A política não alocar na escrita (no-write-allocate ou write-around) encaminha a escrita ao nível seguinte sem inserir a linha. Write-back é frequentemente combinado com write-allocate, e write-through com no-write-allocate, mas outras combinações são possíveis.[3]

Coerência em sistemas multinúcleo

[editar | editar código]

Em processadores com vários núcleos, o mesmo bloco pode estar replicado em caches diferentes. Um protocolo de coerência coordena essas cópias para que escritas sejam propagadas ou provoquem a invalidação de cópias incompatíveis. Protocolos desse tipo normalmente acompanham estados de cada linha e trocam mensagens pelo sistema de interconexão.[5]

Coerência de cache não é sinônimo de consistência de memória: a primeira trata da visibilidade ordenada de operações sobre uma mesma posição, enquanto a segunda estabelece regras mais amplas sobre a ordem observável de acessos a posições diferentes.[3]

O falso compartilhamento ocorre quando núcleos modificam variáveis independentes que estão na mesma linha. Embora os dados não sejam logicamente compartilhados, a linha pode alternar entre caches por causa do protocolo de coerência, reduzindo o desempenho.[6]

Desempenho

[editar | editar código]

As faltas de cache podem ser classificadas, de forma simplificada, em compulsórias (primeiro acesso a um bloco), de capacidade (o conjunto de trabalho não cabe na cache) e de conflito (linhas competem pelas mesmas posições). Em sistemas com múltiplos processadores, invalidações causadas pela coerência também podem provocar faltas.[3]

O desempenho não depende apenas da capacidade nominal. Latência, largura de banda, associatividade, tamanho da linha, políticas de pré-busca e substituição, compartilhamento entre núcleos e padrão de acesso do programa também são relevantes. Por isso, alterações que melhoram a localidade — como percorrer dados de forma contígua ou dividir um problema em blocos que caibam na cache — podem reduzir faltas, mas o efeito precisa ser medido na arquitetura e na carga de trabalho consideradas.[2]

Ver também

[editar | editar código]

Referências

  1. 1 2 3 4 Patterson, David A.; Hennessy, John L. (2021). Computer Organization and Design RISC-V Edition: The Hardware/Software Interface (em inglês) 2 ed. [S.l.]: Morgan Kaufmann. ISBN 978-0-12-820331-6
  2. 1 2 3 «Intel 64 and IA-32 Architectures Optimization» (em inglês). Intel. 31 de outubro de 2024. Consultado em 5 de agosto de 2026
  3. 1 2 3 4 5 6 7 Hennessy, John L.; Patterson, David A. (2019). Computer Architecture: A Quantitative Approach (em inglês) 6 ed. [S.l.]: Morgan Kaufmann. ISBN 978-0-12-811905-1
  4. «Intel 64 and IA-32 Architectures Software Developer Manuals» (em inglês). Intel. 22 de junho de 2026. Consultado em 5 de agosto de 2026. Cópia arquivada em 3 de agosto de 2026
  5. «Cache Coherency» (PDF) (em inglês). Arm. 6 de junho de 2011. Consultado em 5 de agosto de 2026
  6. «False Sharing» (em inglês). The Linux Kernel documentation. Consultado em 5 de agosto de 2026. Cópia arquivada em 5 de agosto de 2026