Bacula Helper App

I had the need to parse the raw data from the bacula database in mysql. I wanted to figure out the file size of a file, but bacula base64 encodes the file size information. After browsing the bacula source code, I pulled out the functions that did the decoding and made it a command line application. I also make a php function for it as well, but the php function doesn’t support 64 bit integers, so it can’t give reliable file sizes for anything above 2.1gb. The C application works fine for 64bit integers (at least on my FreeBSD system.)

The C source code:

#include 

int const base64_digits[64] =
{
  'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M',
  'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z',
  'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm',
  'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z',
  '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', '+', '/'
};

int base64_inited = 0;
int base64_map[128];

/* Initialize the Base 64 conversion routines */

void base64_init(void)
{
   int i;
   memset(base64_map, 0, sizeof(base64_map));
   for (i=0; i<64; i++)
      base64_map[(int)base64_digits[i]] = i;
   base64_inited = 1;
}

int from_base64(long long *value, char *where)
{
   long long val = 0;
   int i, neg;

   if (!base64_inited)
      base64_init();
   /* Check if it is negative */
   i = neg = 0;
   if (where[i] == '-') {
      i++;
      neg = 1;
   }
   /* Construct value */
   while (where[i] != 0 && where[i] != ' ') {
      val <<= 6;
      val += base64_map[(int)where[i++]];
   }

   *value = neg ? -(long long)val : (long long)val;
   return i;
}

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

    if(argc < 2) {
        printf("Usage: %s \n", argv[0]);
        printf("%s --help for more information.n",argv[0]);
        return 1;
    }

    if(!strcmp(argv[1],"-h") || !strcmp(argv[1],"--help") || !strcmp(argv[1],"-?")) {
        printf("%s by Eric McConkey (www.ericmcconkey.com)\n",argv[0]);
        printf("Usage: %s <value> \n", argv[0]);
        printf("Where <value> is the base64 encoded data from the LStat table in a bacula database.\n");
        printf("Example:\n----\n%s UUUAn5326080\n\n----\nn",argv[0]);
        return 0;
    }
    from_base64(&val,argv[1]);
    printf("%lldn",val);
    return 0;
}

The PHP source code:
$base64_digits = array(
  'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J', 'K', 'L', 'M',
  'N', 'O', 'P', 'Q', 'R', 'S', 'T', 'U', 'V', 'W', 'X', 'Y', 'Z',
  'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm',
  'n', 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x', 'y', 'z',
  '0', '1', '2', '3', '4', '5', '6', '7', '8', '9', '+', '/'
);

$base64_map = array_flip($base64_digits);

function from_base64($where) {
    $val = 0.0;
    $i = 0;
    global $base64_map;
    while(($where{$i}) != "") {
        $val = $val << 6;
        $val = $val + $base64_map[$where{$i}];
        $i = $i + 1;
    }
    return $val;
}
// Sample usage
// print(from_base64("JiuiAA"));



Back to Article Index

blog comments powered by Disqus