Já que estamos a falar de velocidade do processador, vamos dizer algumas palavras acerca do overlocking.
Dado que quase todas as placas principais nos permitem alterar livremente a velocidade do barramento e a velocidade do relógio, em princípio, podemos aumentar a velocidade de processamento da nossa máquina, isto é, podemos configurar a nossa placa de modo que o nosso computador funcione, por exemplo, a 800 MHz, mesmo que as características de fábrica digam que ele é um 600 MHz, isto é, se ele funcionar, o que nem sempre acontece.
As frequências que podemos alterar são:
Ø A velocidade de barramento, normalmente de 100MHz ou 133 MHz, mas digamos que a queremos alterar de 100 MHz para 133 MHz.
Ø A velocidade do processador pode também ser aumentada e aqui esse aumento pode ser efectuado de dois modos: pelo aumento da velocidade do barramento e pelo aumento do seu factor multiplicativo.
O resultado de qualquer um destes processos é um processador mais rápido. No entanto, se aumentarmos a velocidade do barramento, isso vai afectar também a velocidade com que os dados são enviados e recebidos da RAM e para isso a RAM também tem de suportar esse aumento.
Por outro lado, quando aumentamos a velocidade interna do processador, temos de ver se as aplicações que utilizamos funcionam eficazmente, pois as muitas aplicações não suportam esse tipo de aventuras.
Quando fazemos o overlocking, temos de ter em atenção um factor extremamente importante nos processadores: aquecimento, já que o aumento da temperatura é um dos maiores perigos para o nosso processador.
Quanto mais aumentarmos a velocidade de processamento, maior necessidade temos de uma boa refrigeração para o processador. Os processadores são construídos com tecnologia CMOS, a qual funciona melhor a baixas temperaturas. Assim, com o aumento da temperatura, podemos ter o resultado oposto ao desejado, isto é, uma drástica diminuição da performance.
Por isso, se está a pensar fazer o overlocking à sua máquina, primeiro veja se o processador o permite, procure saber qual a performance máxima que poderia tirar dele e, muito importante, não se esqueça de reforçar o dissipador de calor do processador. Tente documentar-se o melhor possível acerca do assunto e a Internet é uma óptima fonte de informação.
3.4.8 Cache Interna
A cache interna apareceu pela primeira vez no processador Intel 80486DX e denominou-se L1 (Level 1). Desde esse momento, a cache teve o seu desenvolvimento natural, principalmente em tamanho, como podemos ver na tabela 3.5.
Nesta tabela podemos ver que alguns processadores têm também uma cache L2, o equivalente À cache externa situada nas placas principais, que posteriormente começou a ser parte integrante do processador, mas vamos abordar este assunto posteriormente.
| CPU | Tamanho da Cache |
| 80486DX e DX2 | 8KB L1 |
| Pentium | 16 KB L1 |
| Pentium Pro | 16 KB + 256 KB L2 |
| Pentium MMX | 32 KB L1 |
| AMD K6 e K6-2 | 64 KB L1 |
| Pentium II e Pentium III | 32 KB L1 |
| Celeron | 32 KB + 128 KB L2 |
| Pentium II CuMine | 32 KB L1+ 256 KB L2 |
| AMD K6-3 | 64 KB L1 + 256 KB L2 |
| AMD K7 Athlon | 128 KB L1 |
| AMD Duron | 128 KB L1 + 64 KB L2 |
| AMD Athlon Thunderbird | 128 KB L1 + 256 KB L2 |
Tabela 3.5 – Tabelada memória cache
Vejamos agora qual a sua função e com funciona.
O processador tem de receber e entregar os dados a alta velocidade. A memória RAM não consegue acompanhar essa necessidade de velocidade, pelo que foi criada uma memória RAM especial, a que se chamou cache, a qual é utilizada como área de armazenamento temporário. Para se tirar a máxima performance do CPU, o número de transacções para o exterior deve ser minimizado. Quanto mais dados puderem ser mantidos dentro do CPU, melhor será a performance. Tomemos como exemplo os processadores 486, equipados com uma unidade de vírgula flutuante e uma cache interna de 8 KB. Estes dois elementos ajudam a minimizar o fluxo de dados que entra e sai do CPU, aumentando a sua performance.
Como já vimos, a cache funciona como armazenamento temporário para instruções frequentemente utilizadas, reduzindo assim a busca de dados na memória principal do sistema.
Apesar da cache L1 aparecer inicialmente no 486, a partir do Pentium ela passou a ter um refinamento. O 486 tem uma cache unificada de 8KB, que era usada para o código e para instruções. A partir do Pentium, os processadores passaram a ter a cache L1 dividida em duas partes, sendo uma delas reservada para dados e outra reservada para código. Retomando o exemplo do Pentium, temos uma cache L1 com 16 KB, sendo 8 KB para código e 8 KB para dados. Vejamos as características de cada um destes tipos de cache.
Temos as seguintes características da cache única:
Ø Para um dado tamanho de cache, uma cache única apresenta uma taxa de acerto maior do que caches separadas.
Ø Apenas é necessário projectar uma cache.
Ø A manipulação do código é mais simples.
Vejamos agora as caches separadas:
Ø Reduzem os conflitos de barramento.
Ø Aumentam a disponibilidade da cache quando necessário.
A opção do uso de caches separadas para o Pentium foi devida à necessidade de uma maior largura debanda do que a que era proporcionada pela cache única.
A memória cache torna-se especialmente importante nos processadores em que a frequência interna é multiplicada, o que a torna muito superior à externa. Assim, a cache permite uma recepção e entrega de dados muito mais rápida.
Como já foi referido e podemos ver na figura 3.19, os computadores têm dois níveis de memória cache, a L1 interna e a L2 externa, mas que posteriormente passou também a ser colocada no próprio chip do processador, com notórias vantagens a nível de performance global, como veremos mais à frente.
Fig. 3.19 – Processador Pentium
3.4.9 Arquitectura Superescalar
O termo superescalar refere-se a uma arquitectura de processador que tenha mais de uma unidade de execução ou pipelines. Estas unidades são nada mais nada menos que os locais do processador onde são processados os dados e as instruções.
Na figura 3.20 podemos ver um exemplo de uma arquitectura simples e de uma arquitectura superescalar. No caso de uma arquitectura simples, as instruções são executadas numa só pipeline, enquanto que numa arquitectura superescalar as instruções são executadas em duas ou mais pipelines.
Fig. 3.20 – Tipos de execução
Vamos ver com um pequeno exemplo como isso se processa, tomando o caso dos processadores i486 e Pentium, sendo o primeiro um processador convencional e o segundo um superescalar de grau dois, isto é, capaz de executar duas instruções simultaneamente.
Imaginemos um programa com duas instruções seguidas: A+B e C+D. Como as instruções não têm qualquer dependência entre elas, C+D antes de A+B não tem qualquer interferência no resultado final. Assim sendo, o processador pode executá-las simultaneamente, isto é, podem ser executadas paralelamente, uma em cada canal ou pipeline. Com isto podemos obter o dobro do desempenho em relação a outros processadores anteriores ao Pentium, já que foi o primeiro superescalar da Intel (fig. 3.21)
Pipeline Única Pipeline U Pipeline V
| | | | |
| A+B | | A+B | C+D |
| C+D | | Processador Pentium | |
Processador 486
Fig. 3.21 – Tipos de pipelines
No entanto, se o nosso programa tiver instruções dependentes, isto é, a continuação de uma dependa do resultado da outra, a operação já se processa de outro modo.
Se tivermos a instrução A+B e (A+B)+C, podemos ver que esta segunda instrução não pode ser executada sem que a primeira forneça um resultado, pelo que cada instrução será executada pela sua ordem lógica, coo aconteceria em qualquer processador convencional anterior ao Pentium (fig. 3.22).
Pipeline U Pipeline V
| A+B | Vazia |
| (A+B)+C | Vazia |
Fig. 3.22 – Tipos de pipelines
Comparativamente com a execução simples, ou sequencial, o pipelining leva-nos a um aumento da performance do processador. Teoricamente, quantos mais estágios tivermos numa pipeline, maior será a velocidade que podemos tirar dela. Por exemplo, supúnhamos que são necessários 12 ciclos de relógio para processar todos os passos necessários de uma instrução; se usarmos uma pipeline de quatro estágios, o máximo que ela consegue processar será uma instrução por cada três ciclos, mas se usarmos uma pipeline de seis estágios, já conseguimos uma instrução em cada dois ciclos. Como élógico, isto é somente um exemplo muito simplificado.
3.4.10 Processadores RISC e Processadores CISC
Os processadores obedecem a uma de duas tecnologias, a RISC (Reduced Instruction Set Computer) e a CISC (Complex Instruction Set Computer). Até ao aparecimento do Pentium Pro, todos os processadores, para PC é claro, eram baseados na tecnologia CISC. Esta classe de processadores possui u grande conjunto de instruções em código máquina. Essas instruções necessitam de ser descodificadas de modo a poderem ser executadas. Para isso, os processadores CISC socorrem-se de um microcódigo interno que indica ao processador como deve manipular cada instrução individualmente. No entanto, à medida que são acrescentadas novas instruções ao processador, o descodificador de instruções torna-se mais complexo, o que o torna mais lento (fig. 3.23).
Fig. 3.23 – Tecnologia CISC
A solução para construir processadores mais rápidos é a utilização da tecnologia RISC. Ao contrário da CISC, os processadores com tecnologia RISC são de fabrico mais simples, pois não necessitam de um descodificador de instruções. Cada bit de uma instrução abre ou fecha directamente um determinado circuito biológico do processador, o que o torna bastante mais rápido. (fig. 3.24).
Fig. 3.24 – Tecnologia RISC
O seria que todos os processadores fossem baseados na tecnologia RISC, mas, há sempre um “mas”, as duas tecnologias são perfeitamente incompatíveis. Assim, se a Intel decidisse acabar com os processadores CISC e fabricar somente processadores RISC, não seríamos capazes de correr nenhum dos programas já existentes, o que nenhum de nós iria gostar particularmente.
A solução para o problema foi a apresentação de um processador híbrido, isto é, um processador RISC, mas capaz de correr instruções CISC. Assim nasceu o Pentium Pro, de que iremos falar mais à frente. No entanto, podemos adiantar que se trata de um processador RISC com um emulador CISC. Para executar instruções CISC, ele tem um descodificador interno que transforma essas instruções CISC em tantas instruções RISC quantas as necessárias, de modo a poder executar aquilo que lhe é solicitado. Esta opção da Intel mantém-se em todos os processadores seguintes ao Pentium Pro.
3.4.11 Passos da Execução Nativa
Os processadores de execução nativa são aqueles que correm directamente o código x86, sem tradução para RISC. Os passos necessários à execução das instruções varia conforme o processador. No entanto, na generalidade, são os que vamos ver em seguida e em processadores mais recentes estas instruções correm em pipelines:
Ø Fetch – O primeiro passo é carregar a instrução na unidade de execução. Dado que a memória é muito lenta comparada com o processador, este passo não envolve uma leitura directa da memória. Em vez disso, um circuito de controlo carrega blocos de 16 ou 32 bits de instruções ou dados, da memória directamente para uma cache primária de instruções. Estes dados estão assim disponíveis para as unidades de execução, conforme forem solicitados. Alguns processadores têm unidades de prefetch para executar esta operação.
Ø Decode – A descodificação é usada para examinar a instrução carregada e determinar o seu tamanho, se requer um acesso à memória para ler dados, etc. Alguns processadores empregam múltiplos descodificadores, de modo a aumentar a sua performance.
Ø Adress Generate – Enquanto algumas instruções operam em localizações de memória, outras não. Para aquelas que acedem à memória, neste estágio é gerado o endereço da localização baseado na informação dada como parte da instrução.
Ø Execute – É aqui que a instrução é executada, de acordo com a informação processada nos passos anteriores.
Ø Write-Back – Após a execução da instrução, é produzido um resultado que é escrito num registo interno da memória de sistema. Mas como a memória de sistema é muito lenta, na realidade esse resultado é escrito num write buffer, onde é mantido até que possa ser finalmente escrito na memória de sistema ou na cache.
3.4.12 Passos da Execução por Tradução x86
Os processadores em tradução x86 são aqueles que correm instruções x86 standard, traduzindo-as em micro-instruções RISC. Este tipo de processador é muito mais complexo devido ao trabalho extra de tradução e gestão destas micro-instruções. De certo modo funciona como pequenos computadores com multiprocessamento dentro do CPU, com código especial para gerir a alocação de tarefas às diferentes unidades de execução, mais ou menos como faz um sistema operativo de multiprocessamento quando usa mais de um processador.
Tal como na execução nativa, os passos necessários à execução das instruções varia conforme o processador. No entanto, na generalidade são os que vamos ver em seguida e é de notar que estas instruções correm sempre em pipelines:
Ø Fetch – O primeiro passo é carregar a instrução na unidade de execução. Dado que a memória é muito lenta comparada com o processador, este passo não envolve uma leitura directa da memória. Em vez disso, um circuito de controlo carrega blocos de 16 ou 32 bits de instruções ou dados, da memória directamente para uma cache primária de instruções. Estes dados estão assim disponíveis para as unidades de execução, conforme forem solicitados. Alguns processadores têm unidades de prefetch para executar esta operação.
Ø Decode – Estes processadores empregam descodificadores múltiplos, sendo cada um deles capaz de pegar nas instruções e descodificá-las em micro-instruções. Como nenhuma das instruções x86 é executada directamente, faz sentido usar descodificadores múltiplos de modo a aumentar a performance. O tempo necessário à descodificação de uma instrução depende da sua complexidade. Instruções simples podem ser descodificadas a uma média de várias por ciclo de relógio, enquanto que outras mais complexas necessitam de mais de um ciclo cada. Qualquer endereço de memória que seja necessário é igualmente gerado nesta altura.
Ø Issue/Schedule – As micro-instruções são atribuídas a uma unidade de execução. Um circuito interno optimiza esta tarefa e controla quais e para onde vão as instruções. Por vezes, esta operação denomina-se “instruction scheduling”, dado que, basicamente, é uma tarefa de agendamento de instruções, de acordo com os recursos disponíveis (unidades de execução).
Ø Execute – É aqui que as micro-instruções são executadas. Normalmente são usadas múltiplas unidades de execução para aumentar a performance, onde algumas são dedicadas somente para certas instruções. Por exemplo, operações complexas de vírgula flutuante são executadas na unidade de execução de vírgula flutuante.
Ø Retire – Dado que as micro-instruções podem ser executadas independentemente umas das outras e fora da sua ordem normal, temos que assegurar que não haverá problemas e que os resultados da execução são primeiro armazenados em locações temporárias. Uma unidade reúne os resultados das micro-instruções e assegura-se que o output é produzido correctamente, de acordo com as instruções x86 originais. A isso chama-se “retiring” as instruções.
Ø Write-back – Após a execução da instrução, é produzido um resultado, o qual é escrito num registo interno da memória de sistema. Mas como a memória de sistema é muito lenta, na realidade esse resultado é escrito num write buffer, onde é mantido até que possa ser finalmente escrito na memória de sistema ou na cache.
3.4.13 Speculative Execution e Branch Prediction
Como já vimos anteriormente, alguns processadores podem executar múltiplas instruções simultaneamente. Por vezes nem todos os resultados das execuções serão usados, devido a alterações no fluxo do programa. Isto pode ocorrer particularmente na vizinhança de branches ou ramificações, onde uma condição é testada e a sequência do programa é alterada dependendo do resultado dessa análise.
Branches são muito comuns no código x86 e poderão ser um sério problema para o pipeling, porque não podemos ter a certeza que as instruções serão executadas numa sequência linear. Pipelining é sinónimo de executar a instrução seguinte antes que a primeira esteja completa. Quando se trata de instruções de teste condicional, isto é, uma instrução tipo “if…then”, não sabemos qual é a instrução seguinte até que a instrução de teste condicional seja totalmente executada, pelo que não se sabe que instrução deverá ir em seguida para a pipeline.
Num processador menos actual, acontece parar a pipeline até que os resultados sejam totalmente conhecidos, tendo como consequência um decréscimo de performance. Processadores mais recentes tratam esse problema de um modo diferente, ou seja, executam especulativamente a instrução seguinte, com a esperança de poder usar os resultados se o branch for para o lado que ele julga que vai, daí a expressão speculative execution. Mas os processadores actuais combinam o speculative execution com uma outra técnica, o branch prediction, a qual permite ao processador, baseado no fluxo do programa e em instruções anteriores, prever com alguma precisão para que lado irá o branch.
Tomemos o seguinte exemplo:
IF A = B THEN
C = C + 1
ELSE
C = C - 1
END IF
A instrução “IF THEN” é um branch ou, melhor dizendo, uma ramificação. Até que esteja completamente executada, não sabemos se a próxima instrução será uma adição ou uma subtracção. Um processador que execute especulativamente pode arrancar tanto a adição como a subtracção simultaneamente, e pura e simplesmente esquece aquela que não interessar. Ou pode fazer uso do branch prediction para arrancar somente uma delas, aquela que ele considerar ser a mais indicada para se o resultado da instrução “IF”.
O branch prediction aperfeiçoa o manuseamento dos branches fazendo uso de uma pequena cache chamada branch target buffer ou BTB. Sempre que o processador executa um branch, ele armazena informações acerca do branch nessa área. Quando o processador encontra novamente o mesmo branch, ele é capaz de saber qual a melhor solução. Isto ajuda a manter o fluxo de instruções na pipeline e aumenta a performance. Quanto maior for o BTB, mais informação acerca dos branches é capaz de manter.
3.4.14 Tecnologia MMX
MMX é a abreviatura de MULTIMÉDIA Extensions, uma tecnologia adicionada aos processadores que tem por fim simplificar o uso do multimédia. Essa tecnologia foi usada inicialmente nos processadores Pentium MMX, sendo utilizada em todos ao processadores fabricados desde então.
Em termos práticos, a extensão MMX é composta por 57 novas instruções de software e algumas alterações em termos de hardware interno do processador.
No que respeita às 57 novas instruções, elas são capazes de lidar com dados agrupados de 64 bits, que podem tomar 3 formas:
- 64 bits de uma só vez:
- dois pacotes de 32 bits
- oito pacotes de 8 bits.
A manipulação de dados de áudio é geralmente de 16 bits. No entanto, alguns recursos de vídeo trabalham com sequências de 8 bits. Deste modo, as instruções MMX podem processar sons e imagens com bastante velocidade sem a necessidade de periféricos, além de poder trabalhar sons e vídeo simultaneamente.
No entanto, e como já foi referido, também há grandes diferenças a nível do hardware, já que a arquitectura interna também foi dimensionada para aumentar a performance na execução de instruções multimédia.
O barramento interno permite que várias operações de I/O possam ser executadas muito mais rapidamente. A cache interna do processador passou de 16 KB para 32 KB, sendo 16KB de cache de dados e os restantes 16 KB de cache de instruções.
Vamos ver de um modo simplificado as diferenças de operação em multimédia de um Pentium e do Pentium MMX.
Observemos a figura 3.25 que exemplifica o funcionamento de um programa de videoconferência num Pentium normal.
Figura 3.25 – Videoconferência em Pentium
A aplicação envia um comando de exibição de imagem no monitor ao sistema operativo. Esse comando é transferido pelo driver de vídeo à respectiva placa controladora, onde um circuito integrado acelerador faz o processamento da imagem. Posteriormente, este mesmo integrado faz a distribuição dos sinais para as placas de interface respectivas, isto é, fax/modem, placa de som e placa de vídeo, que por sua vez apresenta a imagem no monitor.
Vejamos, na figura 3.26, como funciona a mesma aplicação num processador MMX.
Figura 3.26 – Videoconferência em processador MMXPentium
A aplicação envia um comando de exibição de imagem no monitor ao sistema operativo. O comando é processado pelo processador MMX, já sem o uso do integrado acelerador. Dado que o processador já incorpora as instruções multimédia necessárias, ele executa muitas das funções inerentes ao fax/modem e á placa de som e vídeo, aumentando substancialmente a qualidade e performance da imagem e do som.
Como é lógico, isto representa uma imagem muito simplista da realidade, mas permite-nos ter uma ideia da diferença entre um processador MMX e um não MMX. Não podemos também esquecer que as aplicações têm de tirar partido das instruções MMX, existentes no processador, porque, caso não o façam, o seu comportamento é idêntico à de um processador sem MMX.
Sem comentários:
Enviar um comentário