Implementação do Codificador de Fala G.729 em FPGA
Full text
IMPLEMENTAÇÃO DO COD IFICADOR DE FALA G.729 EM FPGA CARLA SOFIA INÁCIO B RITO DISSERTAÇÃO DE MESTRADO APRESENTADA À FACULDADE DE ENGENHARIA DA UNIVERSIDADE DO PORTO EM MIEEC – MESTRADO INTEGRADO EM ENGENHARIA ELETROTÉCNICA E DE COMPUTADORES 4 2014
FACULDADE DE ENGENHARIA DA UNIVERSIDADE DO PORTO Implementação do Codificador de Fala G.729 em FPGA Carla Sofia Inácio Brito Mestrado Integrado em Engenharia Electrotécnica e de Computadores Orientador: João Canas Ferreira (Prof. Dr.) Co-orientador: José Carlos Alves (Prof. Dr.) 15 de Abril de 2014
c Carla Brito, 2014
Resumo O objectivo do projecto consiste na implementação do codificador de fala G.729 em FPGA e, usando as características dessa plataforma reconfigurável, melhorar o desempenho do codificador. O projecto teve como ponto de partida a aplicação em C do codificador e um estudo feito sobre o mesmo. O profiling da aplicação foi efectuado para determinar as etapas de codificação com tempos de execução mais elevadas. As duas funções com maior tempo de execução foram seleccionadas para serem implementadas em Hardware: a função Residue eLag Max. Foram exploradas diferentes estratégias de implementação em Hardware de cada uma das funções, explorando técnicas tais como o pipelining e paralelismo, por forma a obter melhores desempenhos. Para além disso, o Software foi modificado substituindo a função em C por um device driver que permitia a comunicação com os módulos em Hardware. A placa de desenvolvimento ML507 da Xilinx é utilizada no projecto. Esta plataforma contém um Virtex-5 com PowerPC. i
ii
Abstract The aim of the project is the implementation of the G.729 speech coder in FPGA, using the features of this reconfigurable platform, to improve its performance. The starting point of this project was the application in C of the encoder and its study. The application profiling was performed to determine the encoding steps with highest execution times. The two functions with highest execution time were selected for implementation in Hardware: Residue and Lag Max. Different strategies were explored for implementation in hardware of each function, exploring techniques such as pipelining and parallelism in order to obtain better performances. In addition, the Software was modified by replacing the C function by a device driver that allowed communication with the modules in hardware. The Xilinx Ml507 development board was used in the project. This platform contains a Virtex5 with PowerPC. iii
iv
Agradecimentos Agradeço ao Prof. João Canas Ferreira pelo suporte e orientação ao longo do desenvolvimento da minha tese. Agradeço aos meus colegas que, com o espírito de entreajuda e muita amizade, ajudaram a atravessar dificuldades encontradas. Agradeço a todos aqueles que me ajudaram ao longo desses anos do meu curso, que me ajudaram a adaptar a vivência num país distante do meu e que sempre me deram forças para continuar na linha luta pelo conhecimento. Carla Brito v
xii LISTA DE FIGURAS
Lista de Tabelas 2.1 Recursos da Virtex-5 XC5VFX70T [4] ...................... 8 2.2 G.729 original e anexos [2] ............................ 9 3.1 Tempo de codificação de um segmento de fala . . . . . . . . . . . . . . . . . . . 18 3.2 Resultados do Profiling para nível de optimização 1 . . . . . . . . . . . . . . . . 18 3.3 Resultados do Profiling para nível de optimização 2 . . . . . . . . . . . . . . . . 18 3.4 Resultados do Profiling para nível de optimização 3 . . . . . . . . . . . . . . . . 19 5.1 Sinais do módulo multiplier ............................ 34 5.2 Sinais do módulo adder ............................... 35 5.3 Sinais dos módulos Residue10 eResidue30 .................... 38 5.4 Descrição dos parâmetros dos três módulos . . . . . . . . . . . . . . . . . . . . 38 5.5 ........................................... 39 5.6 ........................................... 42 5.7 Mapeamento das entradas e saídas dos módulos nos registos acessíveis por Software 50 5.8 Sinais do módulo Residue .............................. 51 5.9 Descrição dos parâmetros do módulo . . . . . . . . . . . . . . . . . . . . . . . . 51 5.10 Mapeamento das entradas e saídas do módulo Residue nos registos acessíveis por Software....................................... 52 7.1 Tempo total de execução da aplicação . . . . . . . . . . . . . . . . . . . . . . . 58 7.2 Percentagens de melhorias no Teste 1 . . . . . . . . . . . . . . . . . . . . . . . 59 7.3 Percentagens de melhorias no Teste 2 . . . . . . . . . . . . . . . . . . . . . . . 59 7.4 Percentagens de melhorias no Teste 3 . . . . . . . . . . . . . . . . . . . . . . . 59 7.5 Tempo de processamento de um segmento de fala . . . . . . . . . . . . . . . . . 59 7.6 Tempo de escrita dos vectores nas BRAMs . . . . . . . . . . . . . . . . . . . . . 60 7.7 Tempo de leitura dos vectores nas BRAMs . . . . . . . . . . . . . . . . . . . . . 60 7.8 Resumo dos resultados obtidos . . . . . . . . . . . . . . . . . . . . . . . . . . . 60 xiii
xiv LISTA DE TABELAS
Abreviaturas e Símbolos ASIC Application-Specific Integrated Circuit BRAM Block Random Access Memory CLB Configurable Logic Block DPBRAM Dual Port Block Random Access Memory DSP Digital Signal Processor DTX Discontinuous Transmission EDK Embedded Development Kit FPGA Field-Programmable Gate Array HDL Hardware Description Language ISE Integrated Software Environment ITU-T International Telecommunication Union - Telecommunication Standardization Sector LP Linear Prediction LSP Line Spectrum Pairs RAM Random Access Memory REFLECT Rendering FPGA to Multi-Core Embedded computing Voip Voice over Internet Protocol Kb Kilo bits Kbps Kilo bits per second ms mili second xv
Capítulo 1 Introdução Esta dissertação descreve o trabalho desenvolvido ao longo da tese sobre o tema "Implementação do codificador de fala G.729 em FPGA". Os Sistemas Embarcados estão presentes nas mais diversas áreas de aplicação. Todos os dias estamos em contacto com vários sistemas embarcados, tendo um grande impacto sobre a nossa vida quotidiana e uma grande importância económica na nossa sociedade. As suas áreas de aplicação inclui eletrónica automóvel, eletrónica aeronautica, comboios, telecomunicações, sistemas de autenticação, aplicações médicas, aplicações militares, eletrónica de consumo, robótica, equipamentos de fabricação, energia. A nova Era de explosão de troca de informações e do aumento extraordinário e diversificado do mercado de consumo eletrónico trouxe grandes desafios aos Sistemas Embarcados. Cada vez mais os produtos são mais complexos, verificando um exigente aumento de funcionalidades nesses produtos.Para lidar com isso, os Sistemas Embarcados devem ser cada vez mais eficientes, mais seguros e mais inovadores, trazendo benefícios tais como aumento do desempenho, redução dos recursos, energia consumida e preço e maior gestão da informação para garantir a sua segurança. Muitas das funcionalidades dos Sistemas Embarcados são e irão ser implementadas em Software. A implementação em Software oferece grande flexibilidade de implementação mas o aumento da dimensão dos códigos fonte e da necessidade do aumento do desempenho faz com que a implementação em Hardware assume uma importância nos Sistemas Embarcados. A implementação em Hardware permite lidar com situações das quais é difícil de garantir em Software, tais como, a gestão da potência e o desempenho em tempo real. As FPGAs são uma excelente escolha para implementação eficiente e heterogênea dos Sistemas Embarcados. A reconfigurabilidade é a principal carecterística que permite distinguir esta tecnologia de outras tecnologias usadas na implementação dos Sistemas Embarcados. Em vez de usar tecnologias construídas à medida, as FPGAs permitem configurar o comportamento de qualquer circuito especificado. 1
2Introdução 1.1 Objectivos O objectivo do projecto consiste na implementação de partes do codificador de fala G.729 em FPGA e, usando as características dessa plataforma reconfigurável, melhorar o desempenho do codificador. As principais características do codificador G.729 são alto desempenho e alta qualidade de codificação. Para tornar o codificador validável, o sinal de voz deve ser codificado em tempo real e a correcção da saída deve ser garantida. Para melhorar o desempenho, optou-se por uma implementação heterogênea (Software e Hardware). Enquanto que a implementação em Software fornece a flexibilidade necessária de implementação, a aceleração de partes do codificador em Hardware permite atinguir melhores desempenhos, com a exploração de duas importantes técnicas, o Paralelismo e o Pipelining. Outro aspecto a ter em conta para melhorar o desempenho é a transferência de dados entre Software/Hardware, que consume uma grande parcela de tempo. Minimizando ao máximo a transferência de dados, melhores resultados temporais são obtidos. O codificador encontra-se já implementado em Software na linguagem C. Na análise da aplicação foram identificadas um conjunto de funções com tempos de execução elevadas e candidatas a aceleração em Hardware. Dessas funções duas foram escolhidas para implementação em Hardware. Alguns modelos de Hardware das funções críticas foram fornecidos e o trabalho centra-se no estudo e implementação desses e outros modelos em Hardware bem como na exploração do tradeoff entre aumentar o desempenho e reduzir os recursos consumidos, e na análise do impacto da generalização e especialização em Hardware. A plataforma de desenvolvimento ML507 da Xilinx é utilizada. Esta plataforma contém um Virtex-5 XC5VFX70T com PowerPC 440 incorporado, de onde se escolheu correr o kernel Linux. A aplicação em C é executada no PowerPC e a comunicação entre Software e Hardware é feito com recurso a um device driver. 1.2 Estrutura da Dissertação Para além deste capítulo de Introdução, esta dissertação contém mais 7 capítulos: •Capítulo 2 - Neste capítulo faz-se a revisão da literatura e levantamento do Estado da Arte. •Capítulo 3 - Neste capítulo faz-se uma análise da aplicação em C e das funções a serem implementadas. •Capítulo 4 - Neste capítulo são apresentados aspectos gerais de implementação, bem como os ambientes de verificação e validação. •Capítulo 5 - Neste capítulo descreve-se as estratégias utilizadas na implementação das funções em Hardware.
1.2 Estrutura da Dissertação 3 •Capítulo 6 - Neste capítulo descrevem-se as modificações efectuadas em Software e a transferência de dados entre Software e Hardware. •Capítulo 7 - Neste capítulo são apresentados e analisados os resultados obtidos. •Capítulo 8 - Neste capítulo conclui-se o projecto desenvolvido e são apresentados possíveis trabalhos futuros.
4Introdução
Capítulo 2 Estado da Arte Neste capítulo, é apresentada a arquitectura da tecnologia FPGA, com ênfase na arquitectura da família Virtex-5 que inclui a FPGA utilizada no desenvolvimento deste trabalho; é descrito a norma do Codec G.729 e por último é apresentado o fluxo de projecto para aplicações audio que foi usada na implementação do G.729 em FPGA e as ferramentas usadas no desenvolvimento do projecto. 2.1 FPGA Field Programmable Gate Array (FPGA) [5] é um dispositivo semicondutor, desenvolvido pela Xilinx em 1985, com capacidade para ser reconfigurado pelo utilizador para uma determinada aplicação ou determinada funcionalidade, após o seu fabrico. O processo de reconfiguração é o que distingue os FPGAs de outras tecnologias, por exemplo, ASICs que são construídas sob medida para um fim específico. Em comparação com tecnologias ASIC, os FPGAs apresentam várias vantagens [6] , por exemplo: •Rápida prototipagem; •Capacidade de reprogramado das aplicações no FPGA para verificação e validação; •Rápida saída para o mercado. Os FPGAs apresentam 2 mecanismo de reconfiguração [7] : •Dinâmica - A reconfiguração Dinâmica permite que o processo de configuração seja feito durante o tempo de execução do sistema. •Estática - A reconfiguração Estática, por outro lado, só permite a reconfiguração quando o sistema estiver inactivo. A reconfiguração Dinâmica e Estática podem ser: •Parcial - A reconfiguração Parcial permite que apenas uma parte da FPGA seja modificado durante o processo de reconfiguração. 5
12 Estado da Arte •A excitação do filtro de síntese u(n)é construida; •Atualiza-se o dicionário adaptativo com a incorporação de u(n); •O sinal de fala é reconstruído, filtrando o sinal de excitação pelo filtro de síntese; •E por último, o sinal reconstruído passa por um pós-processamento, que inclui um pós-filtro, seguido de um filtro passa-alto e por uma operação de escalamento. 2.3 Fluxo de Projeto para Aplicações Audio A figura 2.3 mostra o fluxo de projeto tipicamente utilizado na implementação heterogénea de aplicações audio [3]. O fluxo de projeto foi proposto pelo projecto REFLECT e utilizado nesta implementação do codificador G.729 em FPGA. Este fluxo de projeto tem por base os códigos fontes da aplicação implementada, geralmente, em linguagem C. Um conjunto de ficheiros contendo amostras de audio são utilizados para extrair os valores da entrada da aplicação, com o objectivo de executar a aplicação e colher resultados para validar o sistema desenvolvido. A otimização da representação dos dados permite não só a simplificação do Software mas também a simplificação na implementação em Hardware. Consiste na redução do número de bits das variáveis ou na conversão para tipos de dados mais simples. O teste de validação de precisão é efectuado comparando os resultados obtidos com e sem optimização. Uma margem de erro aceitável e que permite manter o sistema validável é definida e, uma vez que, o erro entre as duas implementações se mantém dentro da margem, a nova aplicação deve ser considerada para as etapas seguintes. Oprofiling da aplicação permite determinar as funções críticas, isto é, as funções com tempos de execução muito elevados. Muitas aplicações audio têm de operar em tempo real. Sendo assim, as funções críticas tornam-se candidatas a aceleração em Hardware. Após determinar quais são as funções críticas, decide-se quais as funções a serem implementadas em Hardware, fazendo, assim, a partição entre Hardware e Software. A implementação em Hardware é feita através de uma linguagem de descrição de Hardware, por exemplo, Verilog, e através de exploração de técnicas, tais como, o Paralelismo e o Pipelining, pode-se alcançar melhores desempenhos que em Software. A aplicação é modificada, substituindo as funções críticas por um mecanismo que permita a comunicação com o Hardware. Na plataforma de desenvolvimento, a aplicação é executada num processador e os módulos das funções mapeadas na FPGA e, com o auxílio de um device driver, a comunicação entre eles é efectuada. Uma vez implementados na plataforma, a depuração do sistema é efectuada para identificar e posteriormente serem corrigidos eventuais erros na implementação, tanto em Hardware como nas modificações em Software. Após a depuração, procede-se à validação, colheita e análise dos resultados. Nesta etapa, fazse a validação final da correcção dos valores produzidos na saída, é medida a aceleração (ou não)
2.3 Fluxo de Projeto para Aplicações Audio 13 Figura 2.3: Fluxo de projecto para aplicações audio segundo [3]
14 Estado da Arte obtida face a implementação só em Software e verifica-se se a aplicação é executada em tempo real. Caso não se verifique a execução da aplicação em tempo real, mais funções críticas podem ser seleccionadas para serem implementadas em Hardware. Na implementação em FPGA do G.729 foi seguido esse fluxo de projeto com excepção das etapas de otimização da representação dos dados e teste de validação de precisão porque já foi fornecido o código fonte, em linguagem C, da aplicação, com otimização das variavéis em pontofixo. As funções críticas foram implementadas em Verilog. 2.3.1 Plataforma de desenvolvimento A plataforma de desenvolvimento utilizada é o ML507 [8] . A plataforma é utilizada, como descrito anteriormente, para implementação, validação final e extração de resultados do sistema implementado. Esta plataforma contém um FPGA Virtex-5 [4] da Xilinx (XC5VFX70T-1FFG1136) que contém um processador PowerPC 440. Para além disso, a plataforma contém um conjunto de outros periféricos [8] importantes no auxílio da implementação, tais como: •Porta série RS232, •Porta de configuração JTAG, •Transceptor PHY Ethernet de três velocidades, •DDR2 de 256MB e 16 bit de largura. 2.3.2 Ferramentas As seguintes ferramentas foram utilizadas no desenvolvimento do projecto: •GNU Gprof [9] - É uma ferramenta de análise de programas escritos em linguagens de programação tal como o C. O seu principal propósito é a análise computacional de partes de código, permitindo obter quanto tempo uma parte do programa ou uma função gasta na execução. Com esta informação, pode-se saber que partes do programa são muito lentos ou gastam muito tempo e, assim, tomar uma ação para obter o tempo de execução desejado. No projecto, foi utilizado no profiling da aplicação do G.729, permitindo determinar quais as funções a serem implementadas em Hardware. •ModelSim [10] - É um simulador e ambiente de depuração para as linguagens de descrição de Hardware Verilog e VHDL e para SystemC, muito utilizado no design de projectos para FPGA e ASIC. Fornece um ambiente gráfico amigável, permitindo visualizar as entradas e saídas dos módulos em formato de ondas. Neste projecto foi utilizado na simulação e análise dos módulos Verilog desenvolvidos. •Xilinx ISE Design Suite 12.3
2.3 Fluxo de Projeto para Aplicações Audio 15 –Xilinx Platform Studio (XPS) [11] - É a ferramenta do Xilinx ISE que permite construir o sistema base de Hardware, criar e acrescentar ao sistema base os nossos próprios IP Cores, e gerar e descarregar o bitstream para a placa de desenvolvimento. Apresenta um sofisticado ambiente gráfico que auxilia e guia o desenvolvedor ao longo de todos os passos para a criação do seu sistema. –Project Navigator [12] - É a ferramenta do Xilinx ISE que permite a gestão dos ficheiros HDL que compõe o design desenvolvido e a sintetização do design na plataforma alvo. –Xilinx Software Development Kit (XSDK) [13] - É um ambiente gráfico de desenvolvimento de software embarcado que suporta várias funcionalidades: profiling e optimização de software, depuração de software, drives e bibliotecas de suporte de comunicação com o Hardware, interpretação do sistema criado em XPS, configuração de vários parâmetros e criação do pacote de suporte a implementação na placa de desenvolvimento. •Embedded Linux Development Kit (ELDK) [14] - Inclui as ferramentas de desenvolvimento em ambiente GNU, tais como compiladores, para além bibliotecas e ferramentas de suporte ao funcionamento em sistemas alvos que correm Linux.
16 Estado da Arte
Capítulo 3 Análise da Aplicação O trabalho desenvolvido tem por base a aplicação em linguagem C do codificador de fala G.729. É utilizado o ITU-T G.729 Annex I Software Package Release 2, versão 1.2, última modificação em Outubro de 2006, que implementa o algoritmo de compressão em ponto-fixo segundo o anexo I. A aplicação recebe um ficheiro que contém dados de fala e de onde são extraídos os valores da entrada do algoritmo. Para além disso, a aplicação permite seleccionar o bit rate pretendido, 6.4kbit/s, 8.0kbit/s ou 11.8kbit/s, e activar ou desactivar a flag DTX. Em caso de não ser especificado o bit rate e/ou a flag DTX são assumidos, por omissão, o bit rate 8.0kbit/s e DTX desativado. Quando especificado, a aplicação também permite a variação embarcada do bit rate (dentro dos três valores possíveis), isto é, permite que cada segmento de fala tenha um bit rate de saída diferente. O bitstream da saída é guardado num ficheiro binário. É de salientar que o uso de ficheiros para ler os valores de entrada e escrever os valores de saída é para fins de análise. Em caso de codificação em tempo real seria necessário uma interface de comunicação com o sistema que fornece os dados de entrada e com o sistema para onde a aplicação fornece os dados. A aplicação foi executada na plataforma de desenvolvimento ML507 que corre Linux e duas importantes análises foram efectuadas: •Profiling da aplicação. •Determinação do tempo de codificação de um segmento de fala. Dado que a codificação tem de ser efectuada em tempo real, o atraso de codificação não deve exceder os 15 ms por segmento de fala, 10 ms de dados de entrada e mais 5 ms para execução do algoritmo. A tabela 3.1 contém os tempos que a aplicação demora a processar um segmento de fala (tempo de codificação) para os diferentes valores de bit rate e configuração DTX. A aplicação foi compilada para nível de optimização 2, os dados de entrada foram extraídos do ficheiro speech e foi utilizado um temporizador para medir os tempos. A estratégia usada para medir o tempo de codificação será apresentada com mais detalhe no capítulo 7. 17
18 Análise da Aplicação Pela análise dos resultados, verifica-se que estes valores encontram-se abaixo do limite máximo de 5 ms para a execução do algoritmo. DTX Bitrate(kbit/s) tempo (us) activo 6.4 1067 activo 8.0 1092 activo 11.8 3942 não activo 6.4 2666 não activo 8.0 3228 não activo 11.8 3874 Tabela 3.1: Tempo de codificação de um segmento de fala A ferramenta Gprof foi utilizada para o Profiling da aplicação. Nesta análise, os valores de entrada foram extraidos dos ficheiros speech edm19.8. A aplicação foi executada 5 vezes para cada uma das 8 combinações de ficheiro de entrada, bit rate, DTX e variação embarcada de bit rate. Para além de outras informações, a ferramenta dá-nos 4 informações importantes: o número de chamadas, o tempo de execução por chamada, o tempo total de execução, a percentagem do tempo de execução de cada função. As tabelas 3.2,3.3 e3.4 mostram o resultado do Profiling para as quatro funções com maiores percentagens de execução, para os três níveis de compilação O1, O2 e O3. Função Número de Tempo de execução tempo total Tempo total Chamadas por chamada(us) de execução(s) (percentagem) Lag-Max 67380 178.84 12.05 8.87 Residue 295050 37.65 11.11 8.18 Syn-filte 366480 27.56 10.10 7.43 cor-h-vec 918240 9.26 8.50 6.25 Tabela 3.2: Resultados do Profiling para nível de optimização 1 Função Número de Tempo de execução tempo total Tempo total Chamadas por chamada(us) de execução(s) (percentagem) Residue 295050 29.01 8.56 7.46 Lag-Max 67380 124.37 8.38 7.31 Syn-filte 366480 21.58 7.91 6.9 cor-h-vec 918240 7.39 6.79 5.92 Tabela 3.3: Resultados do Profiling para nível de optimização 2 Pelas tabelas, verifica-se que as funções Lag_max eResidue apresentam as piores percentagens de tempos de execução. No total, as duas funções somam 17.05%, 14.77% e 16.70% do tempo total de execução da aplicação, para os três níveis de optimização O1, O2 e O3 respectivamente. Por serem as funções com maior consumo de tempo, foram escolhidas para serem implementadas em Hardware. Nas duas secções seguintes, é feita a análise detalhada dessas funções.
3.1 Descrição Detalhada das Funções 19 Função Número de Tempo de execução tempo total Tempo total Chamadas por chamada(us) de execução(s) (percentagem) Lag_Max 67380 154.94 10.44 8.99 Residue 295050 30.3 8.95 7.71 ACELP_10i40_35bits 38260 223.21 8.54 7.35 Syn-filte 366480 21.64 7.93 6.83 Tabela 3.4: Resultados do Profiling para nível de optimização 3 3.1 Descrição Detalhada das Funções 3.1.1 Residue A função Residue calcula a convolução de ordem M e lg posições, entre os vectores x(n)e a(n), tal como apresentado na seguinte equação y(k) = M ∑ n=0 a(n)x(k−n)(3.1) com 0 <=k<lg A função recebe na entrada os dois vectores x(n)ea(n), os dois valores limite Melg, escreve os resultados no vector y(n)e não retorna nenhum valor. No texto seguinte são mostrados os argumentos da função. A expressão Word16 indica que o tamanho é de 16 bits e que o tipo de dados é Integer com sinal. Texto 3.1: Argumentos da função Residue void Residue ( Word16 m, Word16 a [] , Word16 x [ ] , Word16 y [ ] , Word16 lg ) A função contém dois ciclos for, um externo com um total de lg repetições em que cada repetição desloca uma posição no vector x(n)e no vector de saida y(n), e um ciclo interno que faz M+1 multiplicações e acumulações. O resultado final das multiplicações e acumulações é de 32 bits, mas é truncado e arredondado para o resultado de 16 bits. De seguida é guardada na posição do vector y(n)definido pelo ciclo externo. O texto mostra o segmento de código que implementa a função Residue. fo r ( i = 0; i < lg ; i ++) { s = L_mult ( x [ i ] , a [ 0 ] ) ; fo r ( j = 1; j <= m; j ++) s = L_mac ( s , a [ j ] , x [ i−j ] ) ; s = L_shl ( s , 3) ; y [ i ] = round ( s ) ; }
20 Análise da Aplicação Figura 3.1: Vector global de fala speech A função Residue é chamada nove vezes ao longo da aplicação, cinco vezes dentro da função set_lpc_mode e as restantes dentro da função principal de codificação Coder_ld8c. A função set_lpc_mode é chamada uma única vez dentro de Coder_ld8c. A função set_lpc_mode contém os argumentos signal_ptr,a_fwd ea_bwd e outros, e quando é chamada recebe o vector de fala global speech, a janela A_t_fwd_q e a janela A_t_bwd respectivamente nestes três argumentos. O vector de fala speech tem uma dimensão total de 240 valores, sendo 80 valores actuais dividido em dois segmentos de 40 valores, 40 valores futuros e 120 valores passados. A figura 3.1 mostra esse vector. Nas cinco chamadas à função, em três delas M assume o valor 30 e nas outras duas, o valor 10. Em todas as cinco chamadas o vector x(n)aponta para o vector speech. Para M igual a 30, a janela a(n)é um apontador para o vector A_t_bwd que tem um total de 62 valores. Para M igual a 10, a janela a(n)aponta para o vector A_t_fwd_q que tem um total de 22 valores. A figura 3.2 mostra o alcance ao vector speech para cada uma das 3 chamadas com M igual a 30. Na primeira chamada a função trabalha sobre os 80 valores presentes, na segunda chama trabalha sobre o primeiro sub-segmento e na terceira chamada sobre o segundo sub-segmento. Em todos os três casos são necessários mais 30 valores anteriores. Relativamente ao vector A_t_bwd, a segunda chamada à função trabalha sobre os primeiros 31 valores desse vector e nas outras chamadas trabalha sobre os restantes 31 valores. O valor de lg é L_FRAME (80) na primeira chamada à função. Isto é, são calculadas 80 convoluções; na segunda e terceira chamada à função são calculadas L_SUBFR (40) convoluções. Para M igual a 10, a primeira e segunda chamada à função trabalha sobre o primeiro e segundo sub-segmento, respectivamente, tal como é mostrado na figura 3.3. São necessários mais 10 valores anteriores. De forma semelhante, a primeira chamada à função trabalha sobre os primeiros 11 valores do vector A_t_fwd_q e a segunda chamada à função trabalha sobre os restantes 11 valores desse vector. Em ambas as chamadas à função são calculadas L_SUBFR(40) convoluções. Dentro da função Coder_ld8c, a função é chamada em quatro locais, sendo eles dentro de ciclos for. Em dois locais, o vector x(n)aponta para o vector speech e nos outros dois restantes aponta para o vector error que é calculado antes da chamada à função. O valor de M varia (10 ou 30) conforme um conjunto de condições verificadas antes da chamada à função e a janela a(n)
3.1 Descrição Detalhada das Funções 21 Figura 3.2: Acesso ao vector speech nas três chamadas de Residue para M igual a 30 Figura 3.3: Acesso ao vector speech nas três chamadas de Residue para M igual a 10
28 Aspectos Gerais •Residue - É um módulo genérico que implementa a função Residue para lg variável e tanto para M igual a 10 como para M igual a 30, com um total de 11 multiplicadores. O funcionamente para M igual a 10 ou M igual a 30 é definido através de uma entrada do módulo. Apresenta um funcionamente semelhante ao Residue10 eResidue30_10. Com estes quatro módulos da função Residue, três casos de teste na placa de desenvolvimento são possíveis: •1oteste - Com os módulos Residue10 eResidue30. •2oteste - Com os módulos Residue10 eResidue30_10. •3oteste - Com o módulo Residue. Para a função Lag-Max, quatro módulos foram implementados: •Lag_max_sp1 - Este módulo implementa a função Lag-Max para L_FRAME igual a 80 e os limites lag_max igual a 143 e lag_min igual a 80. Utiliza um total de 20 multiplicadores e cada resultado é colocado à saída a cada 8 ciclos de relógio. •Lag_max_sp2 - Este módulo implementa a função Lag-Max para L_FRAME igual a 80 e os limites lag_max igual a 79 e lag_min igual a 40. Utiliza um total de 20 multiplicadores e cada resultado é colocado à saída a cada 8 ciclos de relógio. •Lag_max_sp3 - Este módulo implementa a função Lag-Max para L_FRAME igual a 80 e os limites lag_max igual a 39 e lag_min igual a 20. Utiliza um total de 20 multiplicadores e cada resultado é colocado à saída a cada 8 ciclos de relógio. •Lag_max - Este módulo implementa a função Lag-Max para L_FRAME igual a 80 e para cada uma das três regiões de cálculo, sendo que, os valores de lag_max elag_min são entradas do módulo. Utiliza um total de 40 multiplicadores e cada resultado é colocado à saída a cada 4 ciclos de relógio. Com estes quatro módulos da função Lag-Max, dois casos de teste na placa de desenvolvimento são possíveis: •1oteste - Com os módulos Lag_max_sp1,Lag_max_sp2 eLag_max_sp3 . •2oteste - Com o módulo Lag_max. Para a implementação dos módulos, foi utilizada a linguagem de descrição de Hardware Verilog na versão mais recente verilog-2001. Esta versão do Verilog trouxe muitas vantagens e simplificações ao projecto face à utilização de outras versões mais antigas do Verilog, por exemplo, Verilog-1995. Destaque-se duas principais vantagens:
4.2 Ambiente de Verificação 29 Figura 4.1: Ambiente de Verificação •O Verilog-2001 permite definir variáveis do tipo "signed"que são interpretadas pelas ferramentas de simulação e de síntese como contendo números com sinal em complemento para dois. •O Verilog-2001 permite fazer a comparação de números com sinais em complemento para dois através dos operadores «"e »". No capítulo 5 é descrita, detalhadamente, a implementação de cada módulo em Verilog, a criação do correspondente IP Core e intregração dos módulos no user logic, e cada um dos casos de teste. 4.2 Ambiente de Verificação A figura 4.1 mostra o ambiente de verificação dos módulos desenvolvidos em Verilog. A verificação consiste, no sentido geral, na comparação entre os resultados de simulação dos módulos desenvolvidos e os resultados obtidos após execução da correspondente função em C. Um conjunto de ficheiros contendo dados de simulação foi usado na verificação sendo que cada teste de verificação incide sobre um ficheiro. Estes ficheiros contêm, na sua maioria, dados aleatórios, excepto em alguns casos cujos dados foram escolhidos para simular casos específicos e críticos. Na simulação do DUT (Device Under Test), os dados são guardados em memória RAM, de onde o DUT lerá esses dados e um conjunto de outros parâmetros são passados ao DUT conforme for o módulo a testar. Após a simulação os resultados são guardados noutro ficheiro. A ferramenta ModelSim foi usada na simulação dos módulos. Numa fase inicial foi necessário também a análise das formas de onda para uma melhor verificação do DUT. A função em C correspondente ao DUT foi separada da aplicação do G.729 e foi criada uma nova aplicação contendo apenas a função e outras funções que esta herda. A função é executada e os resultados guardados num ficheiro. Os ficheiros contendo resultados da simulação do DUT e
30 Aspectos Gerais da execução da função são comparados e caso houver diferenças entre elas, procede-se à análise detalhada do Verilog e à análise das formas de onda, para encontrar o problema e assim corrigi-lo. Após verificar-se que os resultados da simulação do DUT e da execução da função são iguais para todos os diferentes ficheiros de entrada, a próxima etapa é a implementação na placa de desenvolvimento. 4.3 Implementação na placa de desenvolvimento Para a construção do sistema base de Hardware e integração dos módulos desenvolvidos, foi utilizada a ferramenta XPS do ISE Design Suite 12.3 da Xilinx. Com essa ferramenta não só se escolheram os periféricos auxiliares e se criou e integrou ao sistema base o meu próprio IPCORE, como também atráves dela se fez o place and route, geração do bitstream e descarregamento para a placa ML507 da mesma. Para síntese dos módulos do IPCORE usou-se a ferramenta Project Navigator também contida na ISE Design Suite 12.3. A figura 4.2 mostra o sistema base usado na implementação em Hardware. Todos esses periféricos estão ligados ao barramento PLB e, através dele, os periféricos comunicam-se entre si. A aplicação e os ficheiros de entrada são transferidos do computador para a placa através da Hard Ethernet. Esses são guardados na DDR2 e posteriormente executados no PowerPC, que opera a uma frequência de 400MHZ. Durante a execução da aplicação, no momento de execução da função, que foi substituida pelo driver, os dados são transferidos para as RAMs do módulo, são processados pelo módulo e quando este terminar, a aplicação lê os dados da RAM e continua o processamento. Após o término da execução da aplicação, o ficheiro de saída é guardado na DDR2. 4.4 Ambiente de Validação A estratégia usada para verificação da correcção dos dados e validação do sistema na placa de desenvolvimento é mostrada na figura 4.3. O mesmo ficheiro é aplicado à entrada da aplicação somente em Software e da aplicação em Software modificada para aceder a Hardware. Cada uma das aplicações é executadaa na placa de desenvolvimento e os resultados guardados em ficheiros. Posteriormente, esses dois ficheiros de saída foram comparados, usando o comando diff do linux, que compara dois ficheiros especificados e caso haja diferenças entre os dois ficheiros indica onde se verificou a diferença. Ambos os ficheiros contendo dados de fala fornecido pela REFLECT, speech edm19.8, foram usados neste processo. Para maior segurança, não só foram comparados os dados obtidos à saída da aplicação, isto é, os dados finais, mais também foram comparados os dados obtidos logo à saída das funções implementadas em Hardware. No processo final de validação dos dados verificou-se a total correcção dos dados obtidos pelo processamento em Hardware.
4.4 Ambiente de Validação 31 Figura 4.2: Sistema base Figura 4.3: Ambiente de validação
32 Aspectos Gerais
Capítulo 5 Implementação em Hardware Neste capítulo é descrita a implementação em Verilog dos diferentes módulos para as funções Residue e Lag-Max. Para além disso, é descrita a integração desses módulos ao user logic, mostrando as ligações entre os módulos aos blocos BRAM e aos registos acessíveis por Software. 5.1 Sub-Módulos Nesta secção é descrita a implementação em Verilog de dois módulos importantes incluídos nos módulos principais, multiplier eadder. Os módulos multiplier eadder implementam, respectivamente, um multiplicador de variáveis de 16 bits e um somador de variáveis de 32 bits com sinal em complemento para 2. Estes módulos poderiam ser usados para implementar em Hardware outras funções do codificador em C para além das implementadas nesta dissertação. 5.1.1 Multiplicador O módulo multiplier calcula o dobro da multiplicação de duas variáveis de 16 bits. É constituido por duas partes: na 1aparte é efectuado a multiplicação das duas variáveis e na 2aparte é calculado o dobro do resultado obtido na primeira parte. Para implementar a 1aparte do multiplier optou-se por inferir blocos DSP já contidos na Virtex-5. A Virtex-5 contém slices DSP com blocos multiplicadores de variáveis de 25x18 bits em complemento para 2. Estes blocos multiplicadores foram usados na implementação dada a sua baixa latência e elevada frequência. Para tornar o módulo mais portável, optou-se por inferir os blocos DSP em vez de instanciar. A tabela 5.1 mostra os sinais de entrada e saída do módulo multiplier: Os sinais de entrada A e B são aplicadas a entrada do módulo que infere o DSP48. Visto que o DSP calcula a multiplicação de variáveis de 25x18, é importante fazer a extensão do sinal das duas entradas A e B, para garantir o resultado correcto. A figura 5.1 mostra como foi inferido o bloco multiplicador DSP48. Foi necessária uma implementação rigorosa por forma a que o bloco DSP48 fosse correctamente inferido. As duas entradas A e B, de 25 e 18 bits respectivamente, são guardadas em dois registos A1 e B1. O valor 33
34 Implementação em Hardware Sinal Direcção Dimensão(bits) Descrição clk entrada 1 Sinal de relógio rst entrada 1 Sinal de reset activo a 1 en entrada 1 Sinal de enable activo a 1 A entrada 16 Sinal a multiplicar com sinal em complemento para 2 B entrada 16 Sinal a multiplicar com sinal em complemento para 2 Out saída 32 Resultado do dobro da multiplicação de A com B Tabela 5.1: Sinais do módulo multiplier desses 2 registos é multiplicado e guardado num registo de 48 bits, obtendo-se na saída o resultado da multiplicação de A e B com 48 bits. São necessários apenas dois ciclos de relógio para efectuar a multiplicação das duas entradas. De seguida é calculado o dobro do resultado obtido anteriormente. Para isso basta somar o resultado a si mesmo. A figura 5.2 mostra esse processo. A entrada A mostrada na figura representa o resultado do processo anterior. Esta entrada é de 32 bits o que significa que o resultado anterior de 48 bits foi truncado para 32 bits. Isto não produz nenhum efeito negativo, visto que, as duas variáveis inicíais a multiplicar são de 16 bits, e o resultado da multiplicação de duas variáveis de 16 bits é de 32 bits. Para evitar que haja overflow, se o valor de A for igual a 32’h4000_0000, a saída é saturada em 32’h7000_0000, caso contrário, a saída será o dobro de A. No total, o módulo multiplier produz uma latência de 3 ciclos de relógio, sendo 2 ciclos de relógio gastos na multiplicação no bloco DSP48 e mais 1 ciclo de relógio gastos para calcular o dobro do resultado anterior. 5.1.2 Somador O módulo adder calcula a soma de duas variáveis de 32 bits com sinal em complemento para 2. Para prevenir overflow, a implementação segue as seguintes regras: •Se a soma de duas variáveis de sinal positivo produzir um resultado negativo, houve overflow; •Se a soma de duas variáveis de sinal negativo produzir um resultado positivo, houve overflow; Figura 5.1: Inferir o DSP48
5.1 Sub-Módulos 35 Figura 5.2: 2aparte do módulo multiplier •Caso contrário, não houve overflow no resultado. A tabela 5.2 mostra os sinais de entrada e saída do módulo adder: Sinal Direcção Dimensão(bits) Descrição clk entrada 1 Sinal de relógio rst entrada 1 Sinal de reset activo a 1 en entrada 1 Sinal de enable activo a 1 A entrada 16 Sinal a adicionar com sinal em complemento para 2 B entrada 16 Sinal a adicionar com sinal em complemento para 2 Out saída 32 Resultado da soma de A com B Tabela 5.2: Sinais do módulo adder De seguida é mostrada uma parte do código que implementa a adição: . . . i f ( enable ) begin sign <= A[ 31] ^ B[ 3 1 ] ; add <= A + B; A1 <= A[ 3 1 ] ; i f ( ( sign == 1 ’ b0 ) && ( ( add [31] ^ A1) == 1 ’ b1 ) ) begin i f (A1 == 1 ’ b1 ) begin Out <= MIN_32 ; end
36 Implementação em Hardware else begin Out <= MAX_32; end end else begin Out <= add ; end end else . . . O registo sign contém o resultado do xor lógico entre os sinais das entradas A e B, sendo 0 caso tiverem o mesmo sinal(isto é, serem ambos de sinais positivos ou ambos negativos) ou 1 caso tiverem sinais diferentes. O registo add contém o resultado da soma da entrada A com a entrada B. O registo A1 contém o sinal de uma das entradas (neste caso, da entrada A). Caso as duas entradas A e B tiverem o mesmo sinal, isto é, o registo sign for 0, e o resultado da adição de A com B tiver sinal contrário as entradas (o xor lógico entre o sinal de add e A1 é 1, caso tiverem sinais diferentes), a saída é saturada, caso contrário, a saída será a soma das entradas. 5.2 Residue Para a implementação em Hardware da função Residue, três casos de teste diferentes na placa de desenvolvimento foram explorados. No primeiro caso, duas versões especializadas da função foram implementadas para M = 10 e M = 30. Esses dois módulos, Residue10 eResidue30, são completamente paralelizavéis, isto é, utilizam-se 11 multiplicadores e 31 multiplicadores, respectivamente. No segundo caso, o mesmo módulo Residue10 é usado mas, na especialização M = 30, é usado o módulo Residue30_10 apenas com 11 multiplicadores. No terceiro caso, um módulo genérico Residue com 11 multiplicadores que permite M = 10 e M = 30 é usado. No total 4 módulos foram implementados. As figuras 5.3,5.4 e5.5 mostram os três casos de teste na placa de desenvolvimento. 5.2.1 Residue10,Residue30 eResidue30_10 O módulo Residue10 implementa a função Residue para valor de M=10 e os módulos Residue30 eResidue30_10 implementam a função Residue para valor de M=30, sendo nos três casos valor de lg variável. O módulo Residue10 usa 11 multiplicadores e o módulo Residue30 usa 31 multiplicadores, sendo eles completamente paralelizáveis e os módulos mais rápidos mas também com maior gasto de multiplicadores. O módulo Residue30_10, por sua vez, usa apenas 11 multiplicadores, o que o torna menos paralelizável e mais lento que Residue30. Cada um dos módulos,
5.2 Residue 37 Figura 5.3: O primeiro caso de teste da função Residue na placa de desenvolvimento Figura 5.4: O segundo caso de teste da função Residue na placa de desenvolvimento Figura 5.5: O terceiro caso de teste da função Residue na placa de desenvolvimento
44 Implementação em Hardware Figura 5.10: Registos de deslocamentos dos módulos Residue30 eResidue30_10 shiftrega eshiftrega. Após as multiplicações, mais 4 níveis de blocos adder são necessários até que os valores das multiplicações sejam adicionados. E por fim, o valor obtido, que é de 32 bits, passa para o bloco shift_round onde será deslocado 3 bits à esquerda e depois truncado para um valor de 16 bits. A saída out_final é, assim, o valor do resíduo de 16 bits para cada iteração de lg. Esta estrutura de cálculo introduz uma latência de 15 ciclos de relógios. Tal como dito anteriormente, os blocos multiplier apresentam uma latência de 3 ciclos de relógio, os blocos adder apresentam uma latência de 2 ciclos de relógios, e o bloco shift_round introduz mais uma latência de 4 ciclos de relógios. 3ciclosderelogio +4niveis ∗2ciclosderelogios +4ciclosderelogios =15ciclosderelogio (5.1) Esta estrutura de cálculo é também em pipelining, o que vai permitir que a cada ciclo de relógio sejam aplicados os valores à entrada dos blocos multiplier, e a cada ciclo de relógio, após a latência, é obtido um valor de resíduo na saída out_final até se obterem os lg valores de resíduo. Para o módulo Residue30, a estrutura de cálculo do resíduo é semelhante (fig. 5.12). Neste caso, são utilizados 31 blocos multiplier em paralelo e são necessário 5 níveis de blocos adder para obter um resultado das adições. E posteriormente, este valor é aplicado ao bloco shift_round, obtendo na saída out_final o valor do resíduo. A latência introduzida é 3ciclosderelogio +5niveis ∗2ciclosderelogios +4ciclosderelogios =17ciclosderelogio (5.2) Após a latência, a cada ciclo de relógio é obtido na saída out_final um valor de resíduo. Para o módulo Residue30_10 5.13 são utilizados apenas 11 blocos multiplier para efectuar 31 multiplicações, o que leva a que as multiplicações são sejam todos paralelizáveis mas sim divididos em 3 ciclos de relógios. Um bloco accumulator é usado para acumular os valores das adições de cada uma das 3 partes que constituem o cálculo de um valor de resíduo. Só a cada 3 ciclos de relógio obtém-se na saída out_final um valor de resíduo. Tal como visto na figura 5.13, as multiplicações são efectuadas entre o registo de deslocamento
5.2 Residue 45 Figura 5.11: Estrutura de cálculo do resíduo no módulo Residue10 shiftrega nas posições 0 a 10 e um conjunto de 11 registos auxiliares chamados regs. A cada ciclo de relógio, o registo de deslocamento shiftrega, de 31 registos, é rodado 10 posições à esquerda por forma a colocar nas posições de 0 a 10 os valores a serem calculados. Para os 11 registos auxiliares regs são copiados partes do registo shiftregx, tal como mostrado na figura 5.14. No primeiro ciclo de relógio é copiado para regs shiftregx[0:10], no segundo ciclo de relógio é copiado shiftregx[11:21] e no terceiro ciclo de relógio é copiado shiftregx[22:30] Porque foi escolhido utilizar os registos auxiliares regs em vez de multiplexers? Foi escolhido utilizar estes registos auxiliares para tornar o módulo mais rápido. O uso de multiplexers (lógica combinacional) teria um custo mais negativo em termos de frequência de síntese do módulo. E, por outro lado, registos são recursos abundantes na FPGA utilizada. Latência Para exemplificar com mais detalhe os efeitos da latência no cálculo do resíduo, é mostrado a figura 5.15. O cálculo dos lg valores de resíduo apresenta uma estrutura em trapézio. A parte superior do trapézio representa as lg iterações em que os registos de deslocamento são deslocados e enviados para os blocos multiplier, e a parte inferior do trapézio representa a saída dos resultados dos resíduos. A latência vai introduzir um desfasamento de n ciclos de relógio até à saída dos resultados do resíduo. Isto justifica a necessidade de existência do estado WAIT na máquina de estado. Após complementar as lg iterações de deslocamento dos registos de deslocamento e envio dos valores para cálculo, é necessário aguardar que os restantes valores de resíduo sejam obtidos e guardados na memória e só depois o módulo termina o seu funcionamento e coloca a saída done a 1. Nos módulos Residue10 eResidue30, as partes superiores e inferiores do trapézio têm uma
46 Implementação em Hardware Figura 5.12: Estrutura de cálculo do resíduo no módulo Residue30
5.2 Residue 47 Figura 5.13: Estrutura de cálculo do resíduo no módulo Residue30_10 Figura 5.14: Estrutura de cálculo do resíduo no módulo Residue30_10
48 Implementação em Hardware Figura 5.15: Latência duração de lg ciclos de relógios porque são completamente paralelizáveis e os resultados de resíduo são produzidos a cada ciclo de relógio. No módulo Residue30_10, ao contrário dos módulos anteriores, as lg iterações não correspondem a lg ciclos de relógios mas sim a 3*lg ciclos de relógios. Este módulo não é completamente paralelizável sendo cada resultado de resíduo produzido a cada 3 ciclos de relógios. 5.2.1.4 Leitura e escrita das BRAM Os módulos recebem em três portas de entrada, addr_x,addr_a eaddr_out os endereços onde devem começar a ler os valores de x e a e onde deve começar a escrever os valores de resíduo, respectivamente. Três contadores são utilizados para gerar os endereços, counter_addrx, counter_addra ecounter_addrout. Esses contadores são inicializados com os valores das entradas addr_x,addr_a eaddr_out respectivamente, e vão sendo incrementadas para gerar o próximo endereço. É colocada nas saídas do endereço para as RAMs os valores desses contadores. Após a latência dos cálculos, na porta de saída para a RAM2, ram2_out, é colocada, o valor de resíduo calculado, out_final, e a saída ram2_we é colocada a 1. 5.2.1.5 Ligação dos módulos as BRAM e aos registos acessíveis por Software Na integração dos módulos ao userlogic para construir os seus respectivos IP_Core, os módulos são ligados a duas Dual Port BRAM de onde lerá os valores das entradas a e x e de onde escreverá os valores dos resíduos calculados. Os módulos são ligados a porta B das DPBRAM e a porta A das DPBRAM é ligada a lógica de ligação a PLB. A figura 5.16 mostra as ligações. Cada uma das DPBRAM são de 16Kbits. Na primeira DPRAM os módulos lêem os valores da entrada x, e na segunda DPBRAM lêem os valores de entrada e escrevem os resultados da saída. O uso de duas DPRAM permitiu que as entradas a e x fossem lidas ao mesmo tempo diminuindo os ciclos de relógios necessários para encher os dois registos de deslocamentos shiftrega eshiftregx porque são preenchidas ao mesmo tempo. E também permitiu que os valores de saída fossem escritas na RAM enquanto é lida a entrada x.
5.2 Residue 49 Figura 5.16: Ligação dos módulos aos respectivos DPBRAM
50 Implementação em Hardware As restantes portas dos módulos, com excepção da porta de entrada do relógio, estão ligadas a registos acessíveis por Software. A porta de entrada do relógio clk está ligada ao relógio da PLB. A tabela 5.7 mostra o mapeamento das portas do módulo aos registos acessíveis por Software, registos esses de 32 bits. Na tabela estão representados apenas os 16 bits mais significativos dos registos. Os outros 16 bits menos significativos não foram utilizados. Bits Índice Registos 31 30 29 28 27 26 25 24 23 22 21 20 19 18 17 16 0 slv_reg0 start 1 slv_reg1 done 2 slv_reg2 lg 3 slv_reg3 addr_x 4 slv_reg4 addr_a 5 slv_reg5 addr_out 6 slv_reg6 reset Tabela 5.7: Mapeamento das entradas e saídas dos módulos nos registos acessíveis por Software 5.2.2 Residue O módulo Residue implementa a função Residue para ambos os valores de M=10 e M=30, sendo o valor de lg variável. A escolha de funcionamento para cada um dos valores de M é feita através de uma porta de entrada de 1 bit. O módulo Residue usa apenas 11 multiplicadores. Funciona como o módulo Residue10 caso for escolhido M=10 e funciona como o módulo Residue30_10 caso for escolhido M=30. Este módulo vai permitir uma minimização da área da FPGA utilizada. O módulo lê os valores da entrada e escreve os resultados em dois blocos BRAM e também lê e escreve para variavéis acessíveis por Software. A tabela 5.8 mostra os sinais de entrada e saída do módulo e a tabela 5.9 faz a descrição dos parâmetros. Para permitir o funcionamento para os dois valores de M, é utilizado registos de deslocamento para o caso de maior valor de M, isto é, são utilizados 31 registos para cada um dos registos de deslocamento. Assim sendo, os registos de deslocamento são semelhantes aos do módulo Residue30_10, tal como, mostrada na figura 5.10. O módulo Residue apresenta um funcionamento igual ao módulo Residue10 caso a entrada m seja 0, isto é, a cada ciclo de relógio um resultado é guardado na memória; e apresenta um funcionamento igual ao módulo Residue30_10 caso a entrada m seja 1, guardando um resultado na memória a cada três ciclos de relógio. A figura 5.17 mostra o funcionamento do módulo para cada valor de m. À semelhança dos três módulos anteriores, o módulo Residue está ligado a duas Dual Port BRAM de 16Kbits, de onde lerá os valores das entradas a e x e de onde escreverá os valores dos resíduos calculados. O módulo é ligado a porta B das DPBRAM e a porta A das DPBRAM é ligada a lógica de ligação a PLB. A figura 5.18 mostra as ligações. Na primeira DPRAM o módulo lê os
5.2 Residue 51 Sinal Direcção Dimensão(bits) Descrição clk entrada 1 Sinal de relógio rst entrada 1 Sinal de reset activo a 1 start entrada 1 Sinal para o módulo começar a funcionar m entrada 1 Sinal que permite escolher o valor de M, sendo 0 para M=10 e 1 para M=30 done saída 1 Sinal que o módulo transmite para indicar o fim das operações e que todos os resultados estão guardados na memória; activo a 1 addr_x entrada ADDR Endereço da memória onde o módulo deve começar a ler a entrada x addr_a entrada ADDR Endereço da memória onde o módulo deve começar a ler a entrada a addr_out entrada ADDR Endereço da memória onde o módulo deve começar a escrever o resultado da saída lg entrada 16 O número de resultados que o módulo irá calcular ram1_inx entrada 16 Entrada dos valores de x ram1_addr saída ADDR Endereço para a BRAM1 ram2_addr saída ADDR Endereço para a BRAM2 ram2_we saída 1 Sinal de enable de escrita na BRAM2; activo a 1 ram2_ina entrada 16 Entrada dos valores de a ram2_out saída 16 Saída dos resultados para a BRAM2 Tabela 5.8: Sinais do módulo Residue Parâmetro Descrição ADDR Descrição: Variável que define o limite do endereço dos blocos BRAM conforme as suas dimensões Valor padrão: 10 Valor mínimo: Depende da quantidade de dados a ser guardados nos blocos BRAM Valor máximo: Depende da tecnologia usada. A virtex-5 permite implementar blocos RAM de 36K. Tabela 5.9: Descrição dos parâmetros do módulo Figura 5.17: Funcionamento do módulo Residue
52 Implementação em Hardware Figura 5.18: Ligação do módulo aos DPBRAMs valores da entrada x, e na segunda DPBRAM lê os valores de entrada e escrevem os resultados da saída. As restantes portas do módulo, com excepção da porta de entrada do relógio, estão ligadas a registos acessíveis por Software. A porta de entrada do relógio clk está ligada ao relógio da PLB. A tabela 5.10 mostra o mapeamento das portas do módulo aos registos acessíveis por Software, registos esses de 32 bits. Na tabela estão representados apenas os 16 bits mais significativos dos registos. Os outros 16 bits menos significativos não foram utilizados. Bits Índice Registos 31 30 29 28 27 26 25 24 23 22 21 20 19 18 17 16 0 slv_reg0 start 0 slv_reg1 m 1 slv_reg2 done 2 slv_reg3 lg 3 slv_reg4 addr_x 4 slv_reg5 addr_a 5 slv_reg6 addr_out 6 slv_reg7 reset Tabela 5.10: Mapeamento das entradas e saídas do módulo Residue nos registos acessíveis por Software
Capítulo 6 Implementação em Software Neste capítulo é descrito o software desenvolvido para aceder a Hardware e as modificações efectuadas no código fonte da aplicação para substituir a chamada as funções pelo acesso aos módulos em Hardware. 6.1 Desenvolvimento de Software de acesso a Hardware Para mapear os módulos escolheu-se usar o dev/mem em vez de desenvolver um kernel driver. O dev/mem proporciona o acesso a memória física do sistema e é usado para aceder a memória IO de Hardware periférico. Ele permite que o sinal seja transmitido a uma alta velocidade mas não é muito seguro por isso só deve ser usado para situações de teste. O primeiro passo é abrir o dev/mem. Este é aberto da mesma forma que se abre um ficheiro, usando a função open. Para leitura e escrita deve ser aberto usando o modo O_RDWR. # d e fi n e RESIDUE_PATH " / dev /mem" Word32 Open ( void ) { fd = open (RESIDUE_PATH, O_RDWR) ; i f ( fd == −1){ per ror (" Erro r opening f i l e . " ) ; return −1; } r e t u r n 0; } Para fechar o dev/mem usa-se: cl ose ( fd ) ; Após abrir o dev mem, cada um dos módulos e as RAMs devem ser mapeados na dev/mem. Para mapear usa-se a função mmap. 53
60 Validação e Análise de resultados Para mostrar o peso que a transferência de dados de/para as memórias BRAMs tem no desempenho temporal da aplicação, nas tabelas 7.6 e7.7 são mostrados os tempos de leitura e escrita das BRAMs. O vector speech, sendo o vector de maior dimensão, apresenta maior tempo de transferência. No entanto, este vector é transferido uma única vez para os BRAMs. Os vectores A_t_bwd eA_t_fwd_q são também transferidos uma única vez para os BRAMs. Para além desses vectores, outros vectores são também transferidos, tais como o vector erro. Mas a trasferência desses vectores, dá-se dentro de ciclos for o que tornou difícil a sua medição, e por outro lado, esses vectores são menos expressivos para a os resultados. A leitura dos dados das BRAMs acontece sempre, o que faz com que tenha uma expressão significativa no tempo de processamento da função. Vector Comprimento (bits) Tempo (us) speech 90 9 A_t_bwd 62 8 A_t_fwd_q 22 5 Tabela 7.6: Tempo de escrita dos vectores nas BRAMs Vector Comprimento (bits) Tempo (us) res 80 9 40 6 Tabela 7.7: Tempo de leitura dos vectores nas BRAMs 7.1.2 Comparação entre os três testes A tabela 7.8 faz um resumo do desempenho temporal e dos recursos usados para cada um dos casos de teste. Pela tabela é possível verificar que o teste 1 é o teste mais rápido mas a que usa mais recursos importantes da FPGA, tais como, os blocos DSP48. Este caso de teste pode ser escolhido para implementação em FPGA em que o desempenho temporal e a aceleração são os principais factores a ter em conta. No caso em que a área e a limitação dos recursos utilizados são os principais factores na implementação em FPGA, o teste 3 torna-se o principal candidato para implementação em FPGA. O teste 2 procura um equilíbrio entre os testes 1 e 2. Teste 1 Teste 2 Teste 3 Desempenho temporal Máxima Aceleração: 6.44% Máxima Aceleração: 6.27% Máxima Aceleração: 5.75% Recursos da FPGA Node blocos DSP48: 42, Node BRAMs de 18Kbits: 4 Node blocos DSP48: 22, Node BRAMs de 18Kbits: 4 Node blocos DSP48: 11, Node BRAMs de 18Kbits: 2 Tabela 7.8: Resumo dos resultados obtidos
Capítulo 8 Conclusão Neste projeto foram implementadas em Hardware duas funções, Residue eLag-Max, presentes no codificador de fala G.729, com o objetivo de acelerar a aplicação em C do codificador. A plataforma de desenvolvimento ML507 foi utilizada. A aplicação em linguagem C do codificador é executada no processador PowerPC 440 que corre Linux e a comunicação entre Software e Hardware é feita através de um device driver. Foi cumprido o objetivo principal do projeto de aceleração da aplicação, tendo obtido uma percentagem máxima de 6,44% com a implementação do teste 1 da função Residue. Concluí que a partição Software/Hardware permitiu melhorar o desempenho total da aplicação; a exploração do paralelismo das operações permitiu tornar os módulos mais rápidos, refletindose no desempenho da aplicação; e que a transferência de dados de/para as memórias BRAMs tem um peso significativo no desempenho total da aplicação. 8.1 Trabalhos Futuros Três estudos podem ser feitos no projeto já implementado: •Implementação em Hardware de outras funções para além das já implementadas - No capítulo 2 foram apresentadas quatro funções com maiores tempos de execução. Destas quatro funções apenas duas foram implementadas em Hardware, Residue eLag-Max. As outras duas funções poderiam, futuramente, serem também implementadas em Hardware e analisada o impacto que teriam na aceleração da aplicação em C do codificador de fala. •Implementação das duas funções, Residue eLag-Max, na plataforma de desenvolvimento ML507 - No projeto desenvolvido, as duas funções foram implementadas de forma separadas. A implementação das duas funções ao mesmo tempo na plataforma de desenvolvimento poderia trazer melhor desempenho temporal da aplicação. No entanto, os recursos da FPGA são limitados, o que levaria a um estudo de quais os casos de teste em que ambas as funções poderiam ser implementadas juntas na FPGA. 61
62 Conclusão •Exploração da Reconfiguração Dinâmica - A Reconfiguração Dinâmica permitiria a partilha de recursos entre os módulos e assim ultrapassar algumas limitações de implementação na FPGA. No entanto, o processo de reconfiguração dinãmica apresenta um custo temporal o que tornaria necessário explorar até que ponto a reconfiguração dinâmica permitiria acelerar ou não a aplicação.
Referências [1] REFLECT consortium. Deliverable D1.5 - Technical report about application requirements for reconfigurability and hardware templates, 06 2011. [2] INTERNATIONAL TELECOMMUNICATION UNION. GENERAL ASPECTS OF DIGITAL TRANSMISSION SYSTEMS - CODING OF SPEECH AT 8 kbit/s USING CONJUGATESTRUCTURE ALGEBRAIC-CODE-EXCITED LINEAR-PREDICTION (CS-ACELP) - ITUT Recommendation G.729, 03 1996. [3] REFLECT consortium. Deliverable D1.4 - Technical report of applications delivered by Coreworks, 06 2011. [4] Xilinc Inc. Virtex-5 Family Overview, Product Specification, February 6 2009. DS100 (V5.0). [5] Xilinx Inc. Field programmable gate array (fpga). http://www.xilinx.com/training/fpga/ fpga-eld-programmable-gate-array.htm . [6] ALTERA. Fpgas. http://www.altera.com/products/fpga.html . [7] REFLECT consortium. Deliverable D2.4 - Technical Report on Generic Architectures and Reconfigurable Schemes, 09 2011. [8] Xilinc Inc. ML505/ML506/ML507 Evaluation Platform - UG347, May 16 2011. v3.1.2. [9] Jeffrey Osier. Gnu gprof. http://www.cs.utah.edu/dept/old/texinfo/as/gprof.html , 1993. [10] Mentor Graphics. Modelsim - advanced simulation and debugging. http://model.com/ . [11] Xilinx Inc. Xilinx platform studio. http://www.xilinx.com/tools/xps.htm . [12] Xilinx Inc. Project navigator overview. http://www.xilinx.com/itp/xilinx10/isehelp/ ise_c_project_navigator_overview.htm , 2008. [13] Xilinx Inc. Xilinx software development kit (sdk). http://www.xilinx.com/tools/sdk.htm . [14] DENX Software Engineering. Embedded linux development kit. http://www.denx.de/ wiki/DULG/ELDK , Nov 2008. [15] João Canas Ferreira e Nuno Paulino. Application Analysis: G.729, Internal Report, 09 2011. 63