Este blog está dedicado a mis experiencias, proyectos, dificultades y demás en todo lo relacionado a la electrónica y la programación en general sobre GNU/Linux

Linux, Nivel: Básico, Programación

Generador de LookUp Table de señales senoidales

Nivel: Básico

¿Qué tengo que saber para este post?

  • Compilar utilizando el comando make.

—————————————

Este no va a ser un posteo largo, simplemente para anunciar una pequeña práctica de programación en C++. Este es un software que ya había programado anteriormente en C, pero lo perdí en una formateada de mi PC y decidí rehacerlo en C++ para practicar un poco en este lenguaje.

Es algo que se puede conseguir facilmente online, pero ¿quién te quita la satisfacción de haberlo programado vos mismo? Además de que se adapta específicamente a tu necesidad. Por ejemplo, mi soft ya genera el nombre de la variable utilizando el tipo de datos de stdint necesario para la cantidad de bits o resolución que queramos para la tabla.

Aquí les dejo una captura de cómo se utiliza y lo que genera para 8 bits y 128 entradas en la LUT:

Les dejo el código que está bajo licencia AGPLv3, está señaladas las lineas donde se generan e imprimen los valores calculados y el repositorio para que puedan verlo y clonarlo:

https://gitlab.com/tute-avalos/sinewave-lut-generator

#include <iostream>
#include <string>
#include <sstream>
#include <cstdint>
#include <cmath>
#include <iomanip>

#define _exit_with_error(X) {cout << (X) << endl; exit(1);}

using namespace std;

int main(int argc, char *argv[]) {

    const uint8_t bytes[] = {8,16,32,64};

    if(argc != 3) {
        cout << "usage:\n\t " << *argv << " <bits> <steps>" << endl;
    } else {
        int ib, bits, entries;
        
        /****************************** Validaciones **********************************/
        if(!(stringstream(argv[1]) >> bits) or bits <= 0 or bits > 64) 
            _exit_with_error("<bits> must be greater than 0 and less or equal than 64.");
        
        for(ib=0; ib < 4 and bits > bytes[ib]; ib++);

        if(ib == 4) 
            _exit_with_error("<bits> must be greater than 0 and less or equal than 64.");
        
        if(!(stringstream(argv[2]) >> entries) or entries <= 0)
            _exit_with_error("<entries> must be greater than 0.");
        /******************************************************************************/
        
        /************************* Generación de la tabla *****************************/
        // se calculan los pasos para 1 periodo
        const double step = (2.0*M_PI)/(double)entries; 
        
        // Se imprime el tipo de dato stdint
        cout << "uint" << (uint32_t)bytes[ib] << "_t sineLUT[] = {";
        cout << internal << setfill('0'); // formateo de la salida para rellenar con 0
        
        double value;
        const double maxValue = pow(2,bits)-1;
        // Se calculan los valores de la tabla:
        for(uint16_t i=0; i < entries; i++) {
            // cada 8 entradas 1 salto de linea:
            if(!(i%8)) cout << "\n    "; 
            // Se calcula el valor:
            value = ((sin(i*step)+1.0)/2.0)*(maxValue);
            // Se imprime el valor:
            cout << "0x" << hex << uppercase << setw(((bits-1)/4)+1) << (uint64_t)(value+0.5) << ",";
        }
        // Se borra la última coma y se termina la tabla:
        cout << "\b \n};" << endl;
        /******************************************************************************/
    } 
}

Espero que les sea útil y son más que bienvenidos a criticar mi código y proponer mejoras en el gitlab.

Dejar una respuesta