|  line  | 
 stmt  | 
 bran  | 
 cond  | 
 sub  | 
 pod  | 
 time  | 
 code  | 
| 
1
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 /*  | 
| 
2
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
  * Base64 encoding function  | 
| 
3
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
  *  | 
| 
4
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
  * source: https://en.wikibooks.org/wiki/Algorithm_Implementation/Miscellaneous/Base64#C  | 
| 
5
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
  *  | 
| 
6
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
  */  | 
| 
7
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
    | 
| 
8
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 #ifndef BASE64_H  | 
| 
9
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 #define BASE64_H  | 
| 
10
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
    | 
| 
11
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 #include   | 
| 
12
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 #include   | 
| 
13
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
    | 
| 
14
 | 
12
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 int B64_encode(const void* data_buf, size_t dataLength, char* result, size_t resultSize) {  | 
| 
15
 | 
12
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
   const char     base64chars[] = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";  | 
| 
16
 | 
12
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
   const uint8_t* data          = (const uint8_t*)data_buf;  | 
| 
17
 | 
12
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
   size_t         resultIndex   = 0;  | 
| 
18
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
   size_t         x;  | 
| 
19
 | 
12
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
   uint32_t       n        = 0;  | 
| 
20
 | 
12
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
   int            padCount = dataLength % 3;  | 
| 
21
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
   uint8_t        n0, n1, n2, n3;  | 
| 
22
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
    | 
| 
23
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
   /* increment over the length of the string, three characters at a time */  | 
| 
24
 | 
96
 | 
  
100
  
 | 
 
 | 
 
 | 
 
 | 
 
 | 
   for (x = 0; x < dataLength; x += 3) {  | 
| 
25
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     /* these three 8-bit (ASCII) characters become one 24-bit number */  | 
| 
26
 | 
84
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     n = ((uint32_t)data[x]) << 16;  // parenthesis needed, compiler depending on flags can do the  | 
| 
27
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
                                     // shifting before conversion to uint32_t, resulting to 0  | 
| 
28
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
    | 
| 
29
 | 
84
 | 
  
 50
  
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     if ((x + 1) < dataLength)  | 
| 
30
 | 
84
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
       n += ((uint32_t)data[x + 1]) << 8;  // parenthesis needed, compiler depending on flags can do  | 
| 
31
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
                                           // the shifting before conversion to uint32_t, resulting  | 
| 
32
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
                                           // to 0  | 
| 
33
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
    | 
| 
34
 | 
84
 | 
  
100
  
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     if ((x + 2) < dataLength) n += data[x + 2];  | 
| 
35
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
    | 
| 
36
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     /* this 24-bit number gets separated into four 6-bit numbers */  | 
| 
37
 | 
84
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     n0 = (uint8_t)(n >> 18) & 63;  | 
| 
38
 | 
84
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     n1 = (uint8_t)(n >> 12) & 63;  | 
| 
39
 | 
84
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     n2 = (uint8_t)(n >> 6) & 63;  | 
| 
40
 | 
84
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     n3 = (uint8_t)n & 63;  | 
| 
41
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
    | 
| 
42
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     /*  | 
| 
43
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     * if we have one byte available, then its encoding is spread  | 
| 
44
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     * out over two characters  | 
| 
45
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     */  | 
| 
46
 | 
84
 | 
  
 50
  
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     if (resultIndex >= resultSize) return 1; /* indicate failure: buffer too small */  | 
| 
47
 | 
84
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     result[resultIndex++] = base64chars[n0];  | 
| 
48
 | 
84
 | 
  
 50
  
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     if (resultIndex >= resultSize) return 1; /* indicate failure: buffer too small */  | 
| 
49
 | 
84
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     result[resultIndex++] = base64chars[n1];  | 
| 
50
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
    | 
| 
51
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     /*  | 
| 
52
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     * if we have only two bytes available, then their encoding is  | 
| 
53
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     * spread out over three chars  | 
| 
54
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     */  | 
| 
55
 | 
84
 | 
  
 50
  
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     if ((x + 1) < dataLength) {  | 
| 
56
 | 
84
 | 
  
 50
  
 | 
 
 | 
 
 | 
 
 | 
 
 | 
       if (resultIndex >= resultSize) return 1; /* indicate failure: buffer too small */  | 
| 
57
 | 
84
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
       result[resultIndex++] = base64chars[n2];  | 
| 
58
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     }  | 
| 
59
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
    | 
| 
60
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     /*  | 
| 
61
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     * if we have all three bytes available, then their encoding is spread  | 
| 
62
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     * out over four characters  | 
| 
63
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     */  | 
| 
64
 | 
84
 | 
  
100
  
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     if ((x + 2) < dataLength) {  | 
| 
65
 | 
72
 | 
  
 50
  
 | 
 
 | 
 
 | 
 
 | 
 
 | 
       if (resultIndex >= resultSize) return 1; /* indicate failure: buffer too small */  | 
| 
66
 | 
72
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
       result[resultIndex++] = base64chars[n3];  | 
| 
67
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     }  | 
| 
68
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
   }  | 
| 
69
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
    | 
| 
70
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
   /*  | 
| 
71
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
   * create and add padding that is required if we did not have a multiple of 3  | 
| 
72
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
   * number of characters available  | 
| 
73
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
   */  | 
| 
74
 | 
12
 | 
  
 50
  
 | 
 
 | 
 
 | 
 
 | 
 
 | 
   if (padCount > 0) {  | 
| 
75
 | 
24
 | 
  
100
  
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     for (; padCount < 3; padCount++) {  | 
| 
76
 | 
12
 | 
  
 50
  
 | 
 
 | 
 
 | 
 
 | 
 
 | 
       if (resultIndex >= resultSize) return 1; /* indicate failure: buffer too small */  | 
| 
77
 | 
12
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
       result[resultIndex++] = '=';  | 
| 
78
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
     }  | 
| 
79
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
   }  | 
| 
80
 | 
12
 | 
  
 50
  
 | 
 
 | 
 
 | 
 
 | 
 
 | 
   if (resultIndex >= resultSize) return 1; /* indicate failure: buffer too small */  | 
| 
81
 | 
12
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
   result[resultIndex] = 0;  | 
| 
82
 | 
12
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
   return 0; /* indicate success */  | 
| 
83
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 }  | 
| 
84
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
    | 
| 
85
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 
 | 
 #endif /* BASE64_H */  |