These modules can be used to encode and decode data to and from base64 (described in RFC 3548) and base224 (not described in any standard, uses all non-control characters, briefly described in a comment at the beginning of ucw/base224.c).

ucw/base64.h


uint base64_encode(byte *dest, const byte *src, uint len);

Encodes len bytes of data pointed to by src by base64 encoding. Stores them in dest and returns the number of bytes the output takes.


uint base64_decode(byte *dest, const byte *src, uint len);

Decodes len bytes of data pointed to by src from base64 encoding. All invalid characters are ignored. The result is stored into dest and length of the result is returned.


#define BASE64_ENC_LENGTH(x) (((x)+2)/3 *4)

Use this macro to calculate base64_encode() output buffer size.


#define BASE64_IN_CHUNK 3

Size of chunk on the un-encoded side.


#define BASE64_OUT_CHUNK 4

Size of chunk on the encoded side.

ucw/base224.h


uint base224_encode(byte *dest, const byte *src, uint len);

Encodes len bytes of data pointed to by src by base224 encoding. Stores them in dest and returns the number of bytes the output takes.


uint base224_decode(byte *dest, const byte *src, uint len);

Decodes len bytes of data pointed to by src from base224 encoding. All invalid characters are ignored. The result is stored into dest and length of the result is returned.


#define BASE224_ENC_LENGTH(x) (((x)*8+38)/39*5)

Use this macro to calculate base224_encode() output buffer size. It can happen 4 more bytes would be needed, this macro takes care of that.


#define BASE224_IN_CHUNK 39

Chunk size on the un-encoded side.


#define BASE224_OUT_CHUNK 40

Chunk size on the encoded side.

Usage

  • You may want to encode small block of known size. Just allocate the output buffer and feed the data to the function.

    byte output[BASE64_ENC_LENGTH(input_size)];
    uint output_size = base64_encode(output, input, input_size);
  • Decoding can be done in similar way. It is enough to have output buffer of the same size as the input one.

  • Encoding of a stream of unknown or large size can be split into chunks. The input chunk size must be multiple of BASE64_IN_CHUNK. The output will be corresponding multiple of BASE64_OUT_CHUNK.

    uint input_size;
    byte input[BASE64_IN_CHUNK * 10];
    while(input_size = read_chunk(input, BASE64_IN_CHUNK * 10)) {
      byte output[BASE64_OUT_CHUNK * 10];
      uint output_size = base64_encode(output, input, input_size);
      use_chunk(output, output_size);
    }
  • Decoding of a stream is done in the same way, just swap BASE64_IN_CHUNK and BASE64_OUT_CHUNK (you feed the decode function with BASE64_OUT_CHUNK multiple and get BASE64_IN_CHUNK multiple).

The base224 has similar interface, therefore you can use it the same way as base64.

The basecode utility

You can use the encoding/decoding routines from command line, trough ucw-basecode command. You have to specify the operation by a command line argument and give it the data on standard input. The arguments are:

  • -e: Encode to base64.

  • -d: Decode from base64.

  • -E: Encode to base224.

  • -D: Decode from base224.

Furthermore, you can provide --prefix argument. If you do, the output (when encoding) will be split to lines by default number of chunks and the value of prefix will be prepended to each of them. When decoding, it removes the prefix from the beginning of line.

You can override the default number of blocks for line-splitting by --blocks argument.