Actualizado a: 19 de enero de 2024
Los lenguajes de programación para el desarrollo de software están al día, y ya hemos visto algo de ello en otros artículos, tanto a nivel de código fuente, como también el funcionamiento o ejecución. Sin embargo, los lenguajes de descripción de hardware, o HDL por sus siglas en inglés, son algo más desconocidos para la mayoría de usuarios. Aquí te vamos a explicar todo sobre ellos…
¿Qué es un HDL?
Un HDL (Hardware Description Lenguage) es un lenguaje dedicado a la explicación de elementos hardware, o en otras palabras, es una herramienta de programación utilizada en la concepción y avance de hardware. Así es, durante las primeras fases de generación del hardware, se utiliza este lenguaje para definir la estructura, configuración y las operaciones que puede ejecutar.
Estos lenguajes HDL vieron la luz en los años 70, época en que los circuitos diseñados estaban volviéndose progresivamente más intrincados, lo cual generó la necesidad de contar con representaciones de alto nivel para la lógica digital. Esto permitiría que los diseñadores tuvieran una comprensión más clara del panorama completo. En otras palabras, los lenguajes HDL desempeñan un papel análogo al de los lenguajes de programación en el diseño de software, ya que proporcionan una capa de abstracción superior. Esto exime a los programadores de la tarea de considerar el lenguaje de máquina directamente.
Estos lenguajes HDL tienen la facultad de simular el desempeño y solventar dificultades potenciales antes de materializarlo físicamente. Por lo tanto, uno de sus beneficios sobresalientes es este aspecto. Por otra parte, también tienen la capacidad de ser aplicados en ambientes EDA. En este contexto, se utilizan para describir lo que se aspira crear, permitiendo que el software utilice componentes estándar de bibliotecas de elementos para generar, al final, el diseño requerido para manufacturar el circuito.
En lo que respecta a su forma, guardan semejanzas considerables con los lenguajes de programación de software, como C, por ejemplo. Esto significa que están constituidos por una descripción en formato de texto que comprende expresiones, declaraciones, estructuras de control, variables, constantes, entre otros elementos. No obstante, también incorporan un aspecto que los lenguajes de software no contemplan, y es la gestión del tiempo, algo crítico en los circuitos que operan en sincronización con un reloj.
Es decir, es un lenguaje que los programadores (diseñadores de hardware en este caso) pueden comprender y, a su vez, se puede «compilar» para generar la jerarquía de bloques que conformarán el circuito. Asimismo, se puede elaborar la lista de conexiones o netlist, simular el comportamiento del circuito para certificar su correcto funcionamiento y, por último, crear los mapas o layouts que se emplearán en la manufactura de los circuitos, tanto analógicos como digitales, en formas impresas o integradas. También es plausible utilizarlo para desarrollar un circuito y posteriormente transferirlo a una FPGA con propósitos de prueba.
Estructura
Los HDL emplean expresiones estandarizadas en formato de texto que representan la arquitectura de los circuitos electrónicos. Si se observaran en el interior de una placa, se podrían visualizar más de un millón de compuertas disponibles para el diseñador. Similar a los lenguajes de programación concurrentes, la estructura y el significado de los HDL incorporan notaciones específicas para la concurrencia.
No obstante, a diferencia de la mayoría de los lenguajes de programación de software, los HDL también abarcan una notación específica para el tiempo (timming), ya que este elemento es esencial en los circuitos electrónicos reales. Los lenguajes cuyo propósito central es representar la conectividad entre una jerarquía de bloques se categorizan más apropiadamente como «lenguajes de listas de conexiones» (o «netlist»), los cuales se emplean en programas de diseño asistido por computadora (CAD). Los HDL son más amplios que estos lenguajes de listas de conexiones, ya que no solo permiten definir la estructura de un circuito, sino también su funcionamiento.
Una netlist en el diseño de circuitos es una representación abstracta y jerárquica de un circuito electrónico que describe las interconexiones entre componentes y sus conexiones eléctricas. Se compone de nodos y conexiones que indican cómo los componentes están interconectados y cómo fluye la señal a través del circuito. Las netlists son esenciales para la simulación, verificación y síntesis de circuitos, ya que permiten analizar y optimizar el funcionamiento del diseño antes de ser físicamente implementado, al mismo tiempo que proporcionan información detallada para la fabricación del circuito final.
Por consiguiente, los HDL tienen la capacidad de generar descripciones «ejecutables» de hardware. Esto significa que un programa elaborado en HDL posibilita al diseñador de hardware modelar y simular un componente electrónico antes de crearlo físicamente. Esta capacidad de ejecución de componentes es lo que ocasionalmente lleva a considerar a los HDL como lenguajes de programación convencionales, aunque en realidad deberían ser clasificados más apropiadamente como lenguajes de modelado.
En la práctica, existen diversos tipos de simuladores capaces de manejar tanto eventos discretos (digitales) como eventos continuos (analógicos), con lenguajes HDL específicos para cada uno de estos casos.
Sin embargo, desde una perspectiva pragmática, una de las principales ventajas de los HDL radica en la posibilidad de utilizar un software denominado sintetizador para deducir, a partir de la expresión textual del programa, el conjunto de operaciones lógicas y el diseño de circuito correspondiente necesario para llevar a cabo la función del programa. Esta capacidad facilita la transición desde el ámbito de la simulación en software hacia la implementación efectiva del hardware en circuitos lógicos reales, tales como ASIC o FPGA.
Ventajas y desventajas
Entre las ventajas de usar HDL para diseñar circuitos tenemos:
- Abstracción de Alto Nivel: permiten describir el diseño a un nivel de abstracción más alto que el diseño a nivel de compuertas, lo que facilita la creación y comprensión de circuitos complejos.
- Simulación y Verificación: te dan la posibilidad de simular y verificar el comportamiento de los circuitos antes de implementarlos físicamente, lo que reduce los errores y mejora la confiabilidad. Esto facilita enormemente la depuración de circuitos complejos.
- Flexibilidad: permiten la creación de diseños altamente personalizados y reconfigurables, lo que es esencial en el diseño de hardware moderno.
- Reutilización: se pueden crear bibliotecas de componentes y módulos reutilizables, lo que acelera el proceso de diseño y permite el uso de diseño modular.
- Síntesis Automática: se pueden sintetizar automáticamente en descripciones de niveles de compuertas o incluso en circuitos físicos.
- Documentación Clara: pueden ser documentadas de manera clara y precisa, lo que facilita la colaboración y el mantenimiento a lo largo del tiempo.
Por supuesto, también encontramos algunas desventajas:
- Curva de Aprendizaje: aprender y dominar los HDL puede llevar tiempo y esfuerzo, especialmente para aquellos que no están familiarizados con la programación o la electrónica digital.
- Complejidad: a medida que los diseños se vuelven más grandes y complejos, la escritura y el mantenimiento de descripciones en HDL pueden volverse complicados. Pero sería aún más complicado sin ellos…
- Limitaciones de Síntesis: a veces, las herramientas de síntesis pueden generar diseños subóptimos o ineficientes, lo que requiere intervención manual.
Diferencias con un lenguaje de programación de bajo nivel
No debes confundir un lenguaje de programación de bajo nivel, e incluso el ASM o ensamblador, con un HDL. Aquí te muestro algunas diferencias clave:
- Propósito y enfoque:
- HDL: se utilizan específicamente para describir el diseño y comportamiento de hardware digital, como circuitos integrados, sistemas embebidos y otros componentes electrónicos. Son herramientas para diseñar y modelar sistemas electrónicos.
- Lenguajes de programación de bajo nivel: están diseñados para programar y controlar directamente la arquitectura de un procesador o hardware subyacente. Son utilizados para desarrollar software y para tareas que requieren un alto nivel de control sobre el hardware, como programación de sistemas y controladores de dispositivos.
- Abstracción:
- HDL: trabajan en un nivel de abstracción más bajo que los lenguajes de programación convencionales. Se centran en describir circuitos electrónicos y conexiones a nivel de compuertas lógicas.
- Lenguajes de programación de bajo nivel: estos lenguajes operan en un nivel más alto de abstracción que los HDL. Aunque son más bajos que los lenguajes de alto nivel, como Python o Java, todavía están por encima del nivel de hardware específico.
- Síntesis y Compilación:
- HDL: son sintetizados para generar circuitos electrónicos reales a partir de las descripciones abstractas. La sintetización es un proceso clave en la creación de hardware basado en HDL.
- Lenguajes de programación de bajo nivel: se compilan para generar código ejecutable que se puede ejecutar en el hardware objetivo.
Lenguajes HDL destacados
Existen varios lenguajes HDL, algunos son propietarios, otros no se conocen detalles, ya que los han creado en algunas grandes compañías de diseño de hardware para uso propio. Sin embargo, principalmente hay que destacar cuatro lenguajes que sí que se pueden usar y sí que son bien conocidos:
Chisel
Representa las iniciales de Constructing Hardware in a Scala Embedded Language. Este lenguaje de diseño de hardware de código abierto ha emergido recientemente y está generando gran atención por sus ventajas distintivas en comparación con otras alternativas. Se utiliza para la descripción de circuitos digitales y Nivel de Transferencia de Registros (RTL, por sus siglas en inglés).
Su base se encuentra en el lenguaje de programación Scala y es una creación de la Universidad de Berkeley, con un enfoque orientado a objetos. Un beneficio adicional radica en que las descripciones de hardware elaboradas en Chisel pueden transformarse en Verilog para su síntesis y simulación.
En la actualidad, Chisel está estrechamente vinculado al proyecto RISC-V y ha encontrado aplicaciones en entidades como DARPA y Google, donde se utiliza en el desarrollo de su unidad TPU. La notable eficiencia de Chisel se refleja en su rapidez de desarrollo, que supera a la de Verilog, y en su capacidad para reducir hasta en cinco veces la cantidad de código necesario en comparación con este último HDL.
Un ejemplo en Chisel para crear un sumador de 4-bit. Este código define un módulo Chisel llamado adder4 que recibe dos números de entrada de 4 bits (a
y b
) y produce la suma de los números junto con el bit de acarreo (sum y carryOut). La suma se calcula simplemente sumando los dos números de entrada. El bit de acarreo se obtiene a partir del bit más significativo del resultado de la suma. La última parte del código, adder4Main, es una pequeña aplicación que utiliza el compilador Chisel para generar el diseño en hardware a partir del módulo adder4:
import chisel3._ class adder4 extends Module { val io = IO(new Bundle { val a = Input(UInt(4.W)) val b = Input(UInt(4.W)) val sum = Output(UInt(4.W)) val carryOut = Output(Bool()) }) val sum = io.a + io.b io.sum := sum io.carryOut := sum(4) } object adder4Main extends App { chisel3.Driver.execute(args, () => new adder4) }
Verilog
Verilog constituye otro lenguaje con una sintaxis inspirada en el lenguaje de programación C, lo que resulta familiar para los ingenieros. También incorpora un preprocesador similar al de C y comparte la mayoría de palabras clave. Sin embargo, presenta diferencias, como el uso de las palabras «Begin» y «End» en lugar de las llaves «{}» utilizadas en C para delimitar bloques de código.
Al igual que Chisel, Verilog puede aplicarse en el diseño, síntesis y simulación de diversos tipos de hardware, desde ASIC hasta la programación de FPGA o CPLD. Este lenguaje fue concebido por Phil Moorby en 1985 durante su trabajo en Automated Integrated Design Systems, que luego cambió de nombre a Gateway Design Automation y finalmente fue adquirida por Cadence. Aunque no es de código abierto, Cadence posteriormente lo convirtió en un estándar abierto debido al éxito de VHDL.
Un ejemplo en Verilog para un sumador de 4-bit. Este módulo adder4 toma dos entradas de 4 bits (a
y b
) y produce la suma de los números junto con el bit de acarreo (sum y carryOut). La suma se calcula dentro del bloque always @(*), donde se asigna la suma de a
y b
a la señal sum. El bit de acarreo se extrae tomando el quinto bit del resultado de la suma (sum[4]). Recuerda que este es solo el código del módulo del sumador:
module adder4 ( input [3:0] a, input [3:0] b, output reg [3:0] sum, output reg carryOut ); always @(*) begin sum = a + b; carryOut = sum[4]; end endmodule
VHDL
VHDL representa las siglas derivadas de la combinación de VHSIC (Very High Speed Integrated Circuit) y HDL. También se emplea para la descripción de una amplia gama de circuitos, como ASIC y para la programación de FPGAs o PLDs, entre otros.
Actualmente, es un estándar definido por el IEEE y fue desarrollado originalmente por el Departamento de Defensa de Estados Unidos a principios de los años 80, tomando como base el lenguaje de programación ADA para el desarrollo y simulación de circuitos digitales. A pesar de ser uno de los lenguajes más utilizados en el desarrollo de chips en la actualidad, Chisel ha capturado la atención de la comunidad al ser la incorporación más reciente en el panorama de los HDLs.
Un ejemplo en VHDL de un sumador de 4-bit. Este código define una entidad llamada adder4 que tiene dos entradas de 4 bits (a y b) y dos salidas (sum y carryOut). El proceso dentro de la arquitectura realiza la suma de a y b, almacenando el resultado en la variable temp_sum. Luego, se asigna temp_sum a la señal sum y se obtiene el bit de acarreo a través de temp_sum(4):
library IEEE; use IEEE.STD_LOGIC_1164.ALL; use IEEE.STD_LOGIC_ARITH.ALL; use IEEE.STD_LOGIC_UNSIGNED.ALL; entity FourBitAdder is Port ( a : in STD_LOGIC_VECTOR (3 downto 0); b : in STD_LOGIC_VECTOR (3 downto 0); sum : out STD_LOGIC_VECTOR (3 downto 0); carryOut : out STD_LOGIC); end FourBitAdder; architecture Behavioral of FourBitAdder is begin process(a, b) variable temp_sum : STD_LOGIC_VECTOR (3 downto 0); begin temp_sum := (others => '0'); temp_sum := a + b; sum <= temp_sum; carryOut <= temp_sum(4); end process; end Behavioral;
ABEL
ABEL es la sigla correspondiente a Advanced Boolean Expression Language (Lenguaje Avanzado de Expresiones Booleanas). Se trata de un lenguaje destinado a la descripción de hardware y un conjunto integral de herramientas de diseño orientadas a programar dispositivos lógicos programables (PLDs).
La característica esencial de ABEL radica en su capacidad para describir un diseño de manera simultánea mediante la utilización de tablas de verdad o ecuaciones lógicas. No obstante, es imporatnte tener en cuenta que el lenguaje ABEL ha quedado en desuso en comparación con las alternativas más modernas como Verilog, VHDL o incluso herramientas como Chisel.
Un ejemplo en ABEL de un sumador de 4-bit. En este ejemplo, se utiliza la macro LPM_MACRO para implementar un sumador de 4 bits utilizando las funciones proporcionadas por las bibliotecas LPM (Library of Parameterized Modules). Las entradas y salidas se definen a través de la declaración PINS. La macro sumador implementa el sumador utilizando el tipo de módulo LPM_ADDER con las dimensiones apropiadas:
-- Definición de las entradas y salidas PINS a 4 I, b 4 I, sum 4 O, carryOut 1 O; -- Implementación del sumador LPM_MACRO sumador LPM_TYPE LPM_ADDER LPM_WIDTH 4 LPM_WIDTHA 4 LPM_WIDTHB 4 LPM_SIGN False LPM_CARRYIN True LPM_INST_NAME sumador_inst LPM_CNTEN True LPM_INJECT False LPM_OUTJECT False LPM_LPMXACT 3 LPM_REGBYPSR 0 LPM_REGFEEDB 0 LPM_LPM_CARRYIN 0 LPM_LPM_CNTEN 1 LPM_LPM_XORCY 0 LPM_LPM_INJECT 0 LPM_LPM_OUTJECT 0;
Otros lenguajes
Para finalizar, vamos a ver otros lenguajes HDL que son propietarios, como pueden ser:
- SpectreHDL: un lenguaje de descripción de hardware analógico propietario de Cadence Design Systems para su simulador de circuitos Spectre.
- Altera Hardware Description Language (AHDL): es otro lenguaje de programación propietario que usa Altera para sus productos. En este caso sirve para circuitos digitales.
Y, por supuesto, no hay que olvidar otros tantos HDLs que existen, como AHPL, Bluespec, COLAMO, ELLA, Impulse C, PALASM, Lola, MyHDL, PipelineC, Ruby HDL, SKiDL, etc.
¡Ahora ya los conoces! ¿Qué te parecen los HDL?