README.md

    libbase64

    Библиотека на C для кодирования и декодирования base64 по умолчанию используется вариант RFC4648, но имеется возможность задать любой иной вариант алфавита кодирования

    Не использует выделения памяти, работает с входным и выходным буферами, кодирует и декодирует данные целиком

    Можно использовать не как библиотеку, а просто расположить base64.c и base64.h в дереве исходников вашего проекта.

    Зависимости

    • Заголовки
      • stdint.h
      • stddef.h
    • C компилятор
      • C99 или C11

    Установка и удаление

    Глобально

    make
    sudo make install
    sudo make uninstall
    

    Локально

    make
    make PREFIX=$HOME/.local install
    make PREFIX=$HOME/.local uninstall
    

    Независимо

    make
    make DESTDIR=$HOME/some_you_dir install
    make DESTDIR=$HOME/some_you_dir uninstall
    

    Использование

    Минимальный пример кодирования

    /* This example code licensed as Public Domain CC0 */
    /* https://creativecommons.org/public-domain/cc0/  */
    #include <stdio.h>
    #include <string.h>
    #include "base64.h"
    int main(int argc, char **argv)
    {
        /* prepare input */
        unsigned char inp[] = "Hello World!";
        size_t        inp_size = strlen(inp);
        /* prepare ouput */
        size_t        out_size = inp_size * 1.5; // or ((inp_size / 3) * 4) + 4
        unsigned char out[out_size];
        /* prepare variable to save data len (can ignore it and set NULL) */
        size_t        written = 0;
        /* set data, if last parametr is NULL used RFC4648 base64 alphabet */
        int status = base64_encode(inp,inp_size,out,out_size,&written,NULL);
        if(status != BASE64_SUCCESS)
        {
            fprintf(stderr,"Error: code = %d\n",status);
            return status;
        }
        /* out_size > written size, in this case need set '\0' */
        out[written] = '\0';
        /* show result */
        printf("data = %s  size = %d\n",out, written);
        return 0;
    }
    
    make && cc encode.c -o app libbase64.a
    ./app
    data = SGVsbG8gV29ybGQh  size = 16
    

    Минимальный пример декодирования

    /* This example code licensed as Public Domain CC0 */
    /* https://creativecommons.org/public-domain/cc0/  */
    #include <stdio.h>
    #include <string.h>
    #include "base64.h"
    int main(int argc, char **argv)
    {
        /* prepare input */
        unsigned char inp[] = "SGVsbG8gV29ybGQh";
        size_t        inp_size = strlen(inp);
        /* prepare ouput */
        size_t        out_size = inp_size; /* or calculate own*/
        unsigned char out[out_size];
        /* prepare variable to save data len (can ignore it and set NULL) */
        size_t        written = 0;
        /* set data, if last parametr is NULL used RFC4648 base64 alphabet */
        int status = base64_decode(inp,inp_size,out,out_size,&written,NULL);
        if(status != BASE64_SUCCESS)
        {
            fprintf(stderr,"Error: code = %d\n",status);
            return status;
        }
        /*out_size > written size, in this case need set '\0' */
        out[written] = '\0';
        /* show result */
        printf("data = %s  size = %d\n",out, written);
        return 0;
    }
    
    make && cc encode.c -o app libbase64.a
    ./app
    data = Hello World!  size = 12
    

    Пример использования альтернативного кодирования

    /* This example code licensed as Public Domain CC0 */
    /* https://creativecommons.org/public-domain/cc0/  */
    #include <stdio.h>
    #include <string.h>
    #include "base64.h"
    int main(int argc, char **argv)
    {
        /* create you own base64 */
        unsigned char alphabet[] =
        "ABCDEFGcdefghijHIJKLMN0123456789*?abkOPQRSTUVWXYZlmnopqrstuvwxyz";
        unsigned char endcode    = '@';
        struct base64 mybase;
        int reg_status =  base64_register(alphabet,endcode,&mybase);
        if(reg_status != BASE64_SUCCESS)
        {
            fprintf(stderr,"Error: code = %d\n",reg_status);
            return reg_status;
        }
        /* prepare input */
        unsigned char inp[] = "Hello World!";
        size_t        inp_size = strlen(inp);
        /* prepare ouput */
        size_t        out_size = inp_size * 1.5; // or ((inp_size / 3) * 4) + 4
        unsigned char out[out_size];
        /* prepare variable to save data len (can ignore it and set NULL) */
        size_t        written = 0;
        /* set data, if last parametr is NULL used RFC4648 base64 alphabet */
        int status = base64_encode(inp,inp_size,out,out_size,&written,&mybase);
        if(status != BASE64_SUCCESS)
        {
            fprintf(stderr,"Error: code = %d\n",status);
            return status;
        }
        /*out_size > written size, in this case need set '\0' */
        out[written] = '\0';
        printf("data = %s  size = %d\n",out, written);
        return 0;
    }
    
    make && cc custom.c -o app libbase64.a
    ./app
    data = KGNV5Gw*Nqxm5GI?  size = 16
    

    Различные варианты Base64 существующие в реальности. Этот список не претендует на полноту, есть полные совпадения с rfc4648.

    ----------
    basename = "rfc4648"
    endcode  = '='
    alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
    ----------
    baename  = "rfc1421"
    endcode  = '='
    alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
    ----------
    baename  = "rfc2045"
    endcode  = '='
    alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
    ----------
    basename = "freenet"
    endcode  = '='
    alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789~-";
    ----------
    basename = "rfc3548"
    endcode  = '='
    alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
    ----------
    basename = "rfc4880"
    endcode  = '='
    alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
    ----------
    basename = "y64"
    endcode  = '-'
    alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789._";
    ----------
    basename = "rfc1642"
    endcode  = '\0'
    alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";
    ----------
    basename = "xmltoken"
    endcode  = '\0'
    alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789.-";
    ----------
    basename = "xmlname"
    endcode  = '\0'
    alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789_:";
    ----------
    basename = "pident1"
    endcode  = '\0'
    alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789_-";
    ----------
    basename = "pident2"
    endcode  = '\0'
    alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789._";
    ----------
    basename = "rfc3501"
    endcode  = '\0'
    alphabet = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+,";
    

    На заметку

    Кажется всё работает правильно. Потоковый механизм кодирования и декодирования base64 в планах.

    Описание

    Кодирование и декодирование base64

    Конвейеры
    0 успешных
    0 с ошибкой