Azure IoT common library

Fork of azure_c_shared_utility by Azure IoT

Committer:
Azure.IoT Build
Date:
Fri Jul 01 10:43:23 2016 -0700
Revision:
6:c55b013dfc2a
Parent:
5:921351ce6973
Child:
7:1af47e3a19b6
1.0.10

Who changed what in which revision?

UserRevisionLine numberNew contents of line
Azure.IoT Build 0:fa2de1b79154 1 // Copyright (c) Microsoft. All rights reserved.
Azure.IoT Build 0:fa2de1b79154 2 // Licensed under the MIT license. See LICENSE file in the project root for full license information.
Azure.IoT Build 0:fa2de1b79154 3
Azure.IoT Build 0:fa2de1b79154 4 //
Azure.IoT Build 0:fa2de1b79154 5 // PUT NO INCLUDES BEFORE HERE !!!!
Azure.IoT Build 0:fa2de1b79154 6 //
Azure.IoT Build 0:fa2de1b79154 7 #include <stdlib.h>
Azure.IoT Build 0:fa2de1b79154 8 #ifdef _CRTDBG_MAP_ALLOC
Azure.IoT Build 0:fa2de1b79154 9 #include <crtdbg.h>
Azure.IoT Build 0:fa2de1b79154 10 #endif
Azure.IoT Build 0:fa2de1b79154 11 #include "azure_c_shared_utility/gballoc.h"
Azure.IoT Build 0:fa2de1b79154 12
Azure.IoT Build 0:fa2de1b79154 13 #include <stddef.h>
Azure.IoT Build 0:fa2de1b79154 14 #include <string.h>
Azure.IoT Build 0:fa2de1b79154 15 //
Azure.IoT Build 0:fa2de1b79154 16 // PUT NO CLIENT LIBRARY INCLUDES BEFORE HERE !!!!
Azure.IoT Build 0:fa2de1b79154 17 //
Azure.IoT Build 0:fa2de1b79154 18 #include "azure_c_shared_utility/base64.h"
Azure.IoT Build 6:c55b013dfc2a 19 #include "azure_c_shared_utility/xlogging.h"
Azure.IoT Build 0:fa2de1b79154 20
Azure.IoT Build 0:fa2de1b79154 21 static const char base64char[64] = {
Azure.IoT Build 0:fa2de1b79154 22 'A', 'B', 'C', 'D', 'E', 'F', 'G', 'H', 'I', 'J',
Azure.IoT Build 0:fa2de1b79154 23 'K', 'L', 'M', 'N', 'O', 'P', 'Q', 'R', 'S', 'T',
Azure.IoT Build 0:fa2de1b79154 24 'U', 'V', 'W', 'X', 'Y', 'Z', 'a', 'b', 'c', 'd',
Azure.IoT Build 0:fa2de1b79154 25 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n',
Azure.IoT Build 0:fa2de1b79154 26 'o', 'p', 'q', 'r', 's', 't', 'u', 'v', 'w', 'x',
Azure.IoT Build 0:fa2de1b79154 27 'y', 'z', '0', '1', '2', '3', '4', '5', '6', '7',
Azure.IoT Build 0:fa2de1b79154 28 '8', '9', '+', '/'
Azure.IoT Build 0:fa2de1b79154 29 };
Azure.IoT Build 0:fa2de1b79154 30
Azure.IoT Build 0:fa2de1b79154 31 static const char base64b16[16] = {
Azure.IoT Build 0:fa2de1b79154 32 'A', 'E', 'I', 'M', 'Q', 'U', 'Y', 'c', 'g', 'k',
Azure.IoT Build 0:fa2de1b79154 33 'o', 's', 'w', '0', '4', '8'
Azure.IoT Build 0:fa2de1b79154 34 };
Azure.IoT Build 0:fa2de1b79154 35
Azure.IoT Build 0:fa2de1b79154 36 static const char base64b8[4] = {
Azure.IoT Build 0:fa2de1b79154 37 'A', 'Q', 'g', 'w'
Azure.IoT Build 0:fa2de1b79154 38 };
Azure.IoT Build 0:fa2de1b79154 39
Azure.IoT Build 0:fa2de1b79154 40 static int base64toValue(char base64character, unsigned char* value)
Azure.IoT Build 0:fa2de1b79154 41 {
Azure.IoT Build 0:fa2de1b79154 42 int result = 0;
Azure.IoT Build 0:fa2de1b79154 43 if (('A' <= base64character) && (base64character <= 'Z'))
Azure.IoT Build 0:fa2de1b79154 44 {
Azure.IoT Build 0:fa2de1b79154 45 *value = base64character - 'A';
Azure.IoT Build 0:fa2de1b79154 46 }
Azure.IoT Build 0:fa2de1b79154 47 else if (('a' <= base64character) && (base64character <= 'z'))
Azure.IoT Build 0:fa2de1b79154 48 {
Azure.IoT Build 0:fa2de1b79154 49 *value = ('Z' - 'A') + 1 + (base64character - 'a');
Azure.IoT Build 0:fa2de1b79154 50 }
Azure.IoT Build 0:fa2de1b79154 51 else if (('0' <= base64character) && (base64character <= '9'))
Azure.IoT Build 0:fa2de1b79154 52 {
Azure.IoT Build 0:fa2de1b79154 53 *value = ('Z' - 'A') + 1 + ('z' - 'a') + 1 + (base64character - '0');
Azure.IoT Build 0:fa2de1b79154 54 }
Azure.IoT Build 0:fa2de1b79154 55 else if ('+' == base64character)
Azure.IoT Build 0:fa2de1b79154 56 {
Azure.IoT Build 0:fa2de1b79154 57 *value = 62;
Azure.IoT Build 0:fa2de1b79154 58 }
Azure.IoT Build 0:fa2de1b79154 59 else if ('/' == base64character)
Azure.IoT Build 0:fa2de1b79154 60 {
Azure.IoT Build 0:fa2de1b79154 61 *value = 63;
Azure.IoT Build 0:fa2de1b79154 62 }
Azure.IoT Build 0:fa2de1b79154 63 else
Azure.IoT Build 0:fa2de1b79154 64 {
Azure.IoT Build 0:fa2de1b79154 65 *value = 0;
Azure.IoT Build 0:fa2de1b79154 66 result = -1;
Azure.IoT Build 0:fa2de1b79154 67 }
Azure.IoT Build 0:fa2de1b79154 68 return result;
Azure.IoT Build 0:fa2de1b79154 69 }
Azure.IoT Build 0:fa2de1b79154 70
Azure.IoT Build 0:fa2de1b79154 71 static size_t numberOfBase64Characters(const char* encodedString)
Azure.IoT Build 0:fa2de1b79154 72 {
Azure.IoT Build 0:fa2de1b79154 73 size_t length = 0;
Azure.IoT Build 0:fa2de1b79154 74 unsigned char junkChar;
Azure.IoT Build 0:fa2de1b79154 75 while (base64toValue(encodedString[length],&junkChar) != -1)
Azure.IoT Build 0:fa2de1b79154 76 {
Azure.IoT Build 0:fa2de1b79154 77 length++;
Azure.IoT Build 0:fa2de1b79154 78 }
Azure.IoT Build 0:fa2de1b79154 79 return length;
Azure.IoT Build 0:fa2de1b79154 80 }
AzureIoTClient 5:921351ce6973 81
AzureIoTClient 5:921351ce6973 82 /*returns the count of original bytes before being base64 encoded*/
AzureIoTClient 5:921351ce6973 83 /*notice NO validation of the content of encodedString. Its length is validated to be a multiple of 4.*/
Azure.IoT Build 0:fa2de1b79154 84 static size_t Base64decode_len(const char *encodedString)
Azure.IoT Build 0:fa2de1b79154 85 {
AzureIoTClient 5:921351ce6973 86 size_t result;
AzureIoTClient 5:921351ce6973 87 size_t sourceLength = strlen(encodedString);
AzureIoTClient 5:921351ce6973 88
AzureIoTClient 5:921351ce6973 89 if (sourceLength == 0)
Azure.IoT Build 0:fa2de1b79154 90 {
AzureIoTClient 5:921351ce6973 91 result = 0;
AzureIoTClient 5:921351ce6973 92 }
AzureIoTClient 5:921351ce6973 93 else
AzureIoTClient 5:921351ce6973 94 {
AzureIoTClient 5:921351ce6973 95 result = sourceLength / 4 * 3;
AzureIoTClient 5:921351ce6973 96 if (encodedString[sourceLength - 1] == '=')
Azure.IoT Build 0:fa2de1b79154 97 {
AzureIoTClient 5:921351ce6973 98 if (encodedString[sourceLength - 2] == '=')
Azure.IoT Build 0:fa2de1b79154 99 {
AzureIoTClient 5:921351ce6973 100 result --;
Azure.IoT Build 0:fa2de1b79154 101 }
AzureIoTClient 5:921351ce6973 102 result--;
Azure.IoT Build 0:fa2de1b79154 103 }
Azure.IoT Build 0:fa2de1b79154 104 }
AzureIoTClient 5:921351ce6973 105 return result;
Azure.IoT Build 0:fa2de1b79154 106 }
Azure.IoT Build 0:fa2de1b79154 107
Azure.IoT Build 0:fa2de1b79154 108 static void Base64decode(unsigned char *decodedString, const char *base64String)
Azure.IoT Build 0:fa2de1b79154 109 {
Azure.IoT Build 0:fa2de1b79154 110
Azure.IoT Build 0:fa2de1b79154 111 size_t numberOfEncodedChars;
Azure.IoT Build 0:fa2de1b79154 112 size_t indexOfFirstEncodedChar;
Azure.IoT Build 0:fa2de1b79154 113 size_t decodedIndex;
Azure.IoT Build 0:fa2de1b79154 114
Azure.IoT Build 0:fa2de1b79154 115 //
Azure.IoT Build 0:fa2de1b79154 116 // We can only operate on individual bytes. If we attempt to work
Azure.IoT Build 0:fa2de1b79154 117 // on anything larger we could get an alignment fault on some
Azure.IoT Build 0:fa2de1b79154 118 // architectures
Azure.IoT Build 0:fa2de1b79154 119 //
Azure.IoT Build 0:fa2de1b79154 120
Azure.IoT Build 0:fa2de1b79154 121 numberOfEncodedChars = numberOfBase64Characters(base64String);
Azure.IoT Build 0:fa2de1b79154 122 indexOfFirstEncodedChar = 0;
Azure.IoT Build 0:fa2de1b79154 123 decodedIndex = 0;
Azure.IoT Build 0:fa2de1b79154 124 while (numberOfEncodedChars >= 4)
Azure.IoT Build 0:fa2de1b79154 125 {
Azure.IoT Build 0:fa2de1b79154 126 unsigned char c1;
Azure.IoT Build 0:fa2de1b79154 127 unsigned char c2;
Azure.IoT Build 0:fa2de1b79154 128 unsigned char c3;
Azure.IoT Build 0:fa2de1b79154 129 unsigned char c4;
Azure.IoT Build 0:fa2de1b79154 130 (void)base64toValue(base64String[indexOfFirstEncodedChar], &c1);
Azure.IoT Build 0:fa2de1b79154 131 (void)base64toValue(base64String[indexOfFirstEncodedChar + 1], &c2);
Azure.IoT Build 0:fa2de1b79154 132 (void)base64toValue(base64String[indexOfFirstEncodedChar + 2], &c3);
Azure.IoT Build 0:fa2de1b79154 133 (void)base64toValue(base64String[indexOfFirstEncodedChar + 3], &c4);
Azure.IoT Build 0:fa2de1b79154 134 decodedString[decodedIndex] = (c1 << 2) | (c2 >> 4);
Azure.IoT Build 0:fa2de1b79154 135 decodedIndex++;
Azure.IoT Build 0:fa2de1b79154 136 decodedString[decodedIndex] = ((c2 & 0x0f) << 4) | (c3 >> 2);
Azure.IoT Build 0:fa2de1b79154 137 decodedIndex++;
Azure.IoT Build 0:fa2de1b79154 138 decodedString[decodedIndex] = ((c3 & 0x03) << 6) | c4;
Azure.IoT Build 0:fa2de1b79154 139 decodedIndex++;
Azure.IoT Build 0:fa2de1b79154 140 numberOfEncodedChars -= 4;
Azure.IoT Build 0:fa2de1b79154 141 indexOfFirstEncodedChar += 4;
Azure.IoT Build 0:fa2de1b79154 142
Azure.IoT Build 0:fa2de1b79154 143 }
Azure.IoT Build 0:fa2de1b79154 144
Azure.IoT Build 0:fa2de1b79154 145 if (numberOfEncodedChars == 2)
Azure.IoT Build 0:fa2de1b79154 146 {
Azure.IoT Build 0:fa2de1b79154 147 unsigned char c1;
Azure.IoT Build 0:fa2de1b79154 148 unsigned char c2;
Azure.IoT Build 0:fa2de1b79154 149 (void)base64toValue(base64String[indexOfFirstEncodedChar], &c1);
Azure.IoT Build 0:fa2de1b79154 150 (void)base64toValue(base64String[indexOfFirstEncodedChar + 1], &c2);
Azure.IoT Build 0:fa2de1b79154 151 decodedString[decodedIndex] = (c1 << 2) | (c2 >> 4);
Azure.IoT Build 0:fa2de1b79154 152 }
Azure.IoT Build 0:fa2de1b79154 153 else if (numberOfEncodedChars == 3)
Azure.IoT Build 0:fa2de1b79154 154 {
Azure.IoT Build 0:fa2de1b79154 155 unsigned char c1;
Azure.IoT Build 0:fa2de1b79154 156 unsigned char c2;
Azure.IoT Build 0:fa2de1b79154 157 unsigned char c3;
Azure.IoT Build 0:fa2de1b79154 158 (void)base64toValue(base64String[indexOfFirstEncodedChar], &c1);
Azure.IoT Build 0:fa2de1b79154 159 (void)base64toValue(base64String[indexOfFirstEncodedChar + 1], &c2);
Azure.IoT Build 0:fa2de1b79154 160 (void)base64toValue(base64String[indexOfFirstEncodedChar + 2], &c3);
Azure.IoT Build 0:fa2de1b79154 161 decodedString[decodedIndex] = (c1 << 2) | (c2 >> 4);
Azure.IoT Build 0:fa2de1b79154 162 decodedIndex++;
Azure.IoT Build 0:fa2de1b79154 163 decodedString[decodedIndex] = ((c2 & 0x0f) << 4) | (c3 >> 2);
Azure.IoT Build 0:fa2de1b79154 164 }
Azure.IoT Build 0:fa2de1b79154 165 }
Azure.IoT Build 0:fa2de1b79154 166
Azure.IoT Build 0:fa2de1b79154 167 BUFFER_HANDLE Base64_Decoder(const char* source)
Azure.IoT Build 0:fa2de1b79154 168 {
AzureIoTClient 5:921351ce6973 169 BUFFER_HANDLE result;
Azure.IoT Build 0:fa2de1b79154 170 /*Codes_SRS_BASE64_06_008: [If source is NULL then Base64_Decode shall return NULL.]*/
AzureIoTClient 5:921351ce6973 171 if (source == NULL)
Azure.IoT Build 0:fa2de1b79154 172 {
AzureIoTClient 5:921351ce6973 173 LogError("invalid parameter const char* source=%p", source);
AzureIoTClient 5:921351ce6973 174 result = NULL;
AzureIoTClient 5:921351ce6973 175 }
AzureIoTClient 5:921351ce6973 176 else
AzureIoTClient 5:921351ce6973 177 {
AzureIoTClient 5:921351ce6973 178 if ((strlen(source) % 4) != 0)
Azure.IoT Build 0:fa2de1b79154 179 {
Azure.IoT Build 0:fa2de1b79154 180 /*Codes_SRS_BASE64_06_011: [If the source string has an invalid length for a base 64 encoded string then Base64_Decode shall return NULL.]*/
AzureIoTClient 1:9190c0f4d23a 181 LogError("Invalid length Base64 string!");
AzureIoTClient 5:921351ce6973 182 result = NULL;
Azure.IoT Build 0:fa2de1b79154 183 }
Azure.IoT Build 0:fa2de1b79154 184 else
Azure.IoT Build 0:fa2de1b79154 185 {
AzureIoTClient 5:921351ce6973 186 size_t lengthOfSource = numberOfBase64Characters(source);
Azure.IoT Build 0:fa2de1b79154 187 if ((result = BUFFER_new()) == NULL)
Azure.IoT Build 0:fa2de1b79154 188 {
Azure.IoT Build 0:fa2de1b79154 189 /*Codes_SRS_BASE64_06_010: [If there is any memory allocation failure during the decode then Base64_Decode shall return NULL.]*/
AzureIoTClient 1:9190c0f4d23a 190 LogError("Could not create a buffer to decoding.");
Azure.IoT Build 0:fa2de1b79154 191 }
Azure.IoT Build 0:fa2de1b79154 192 else
Azure.IoT Build 0:fa2de1b79154 193 {
Azure.IoT Build 0:fa2de1b79154 194 size_t sizeOfOutputBuffer = Base64decode_len(source);
Azure.IoT Build 0:fa2de1b79154 195 /*Codes_SRS_BASE64_06_009: [If the string pointed to by source is zero length then the handle returned shall refer to a zero length buffer.]*/
Azure.IoT Build 0:fa2de1b79154 196 if (sizeOfOutputBuffer > 0)
Azure.IoT Build 0:fa2de1b79154 197 {
Azure.IoT Build 0:fa2de1b79154 198 if (BUFFER_pre_build(result, sizeOfOutputBuffer) != 0)
Azure.IoT Build 0:fa2de1b79154 199 {
Azure.IoT Build 0:fa2de1b79154 200 /*Codes_SRS_BASE64_06_010: [If there is any memory allocation failure during the decode then Base64_Decode shall return NULL.]*/
AzureIoTClient 1:9190c0f4d23a 201 LogError("Could not prebuild a buffer for base 64 decoding.");
Azure.IoT Build 0:fa2de1b79154 202 BUFFER_delete(result);
Azure.IoT Build 0:fa2de1b79154 203 result = NULL;
Azure.IoT Build 0:fa2de1b79154 204 }
Azure.IoT Build 0:fa2de1b79154 205 else
Azure.IoT Build 0:fa2de1b79154 206 {
Azure.IoT Build 0:fa2de1b79154 207 Base64decode(BUFFER_u_char(result), source);
Azure.IoT Build 0:fa2de1b79154 208 }
Azure.IoT Build 0:fa2de1b79154 209 }
Azure.IoT Build 0:fa2de1b79154 210 }
Azure.IoT Build 0:fa2de1b79154 211 }
Azure.IoT Build 0:fa2de1b79154 212 }
Azure.IoT Build 0:fa2de1b79154 213 return result;
Azure.IoT Build 0:fa2de1b79154 214 }
Azure.IoT Build 0:fa2de1b79154 215
Azure.IoT Build 0:fa2de1b79154 216
Azure.IoT Build 0:fa2de1b79154 217 static STRING_HANDLE Base64_Encode_Internal(const unsigned char* source, size_t size)
Azure.IoT Build 0:fa2de1b79154 218 {
Azure.IoT Build 0:fa2de1b79154 219 STRING_HANDLE result;
Azure.IoT Build 0:fa2de1b79154 220 size_t neededSize = 0;
Azure.IoT Build 0:fa2de1b79154 221 char* encoded;
Azure.IoT Build 0:fa2de1b79154 222 size_t currentPosition = 0;
Azure.IoT Build 0:fa2de1b79154 223 neededSize += (size == 0) ? (0) : ((((size - 1) / 3) + 1) * 4);
Azure.IoT Build 0:fa2de1b79154 224 neededSize += 1; /*+1 because \0 at the end of the string*/
Azure.IoT Build 0:fa2de1b79154 225 /*Codes_SRS_BASE64_06_006: [If when allocating memory to produce the encoding a failure occurs then Base64_Encode shall return NULL.]*/
Azure.IoT Build 0:fa2de1b79154 226 encoded = (char*)malloc(neededSize);
Azure.IoT Build 0:fa2de1b79154 227 if (encoded == NULL)
Azure.IoT Build 0:fa2de1b79154 228 {
Azure.IoT Build 0:fa2de1b79154 229 result = NULL;
AzureIoTClient 1:9190c0f4d23a 230 LogError("Base64_Encode:: Allocation failed.");
Azure.IoT Build 0:fa2de1b79154 231 }
Azure.IoT Build 0:fa2de1b79154 232 else
Azure.IoT Build 0:fa2de1b79154 233 {
Azure.IoT Build 0:fa2de1b79154 234 /*b0 b1(+1) b2(+2)
Azure.IoT Build 0:fa2de1b79154 235 7 6 5 4 3 2 1 0 7 6 5 4 3 2 1 0 7 6 5 4 3 2 1 0
Azure.IoT Build 0:fa2de1b79154 236 |----c1---| |----c2---| |----c3---| |----c4---|
Azure.IoT Build 0:fa2de1b79154 237 */
Azure.IoT Build 0:fa2de1b79154 238
Azure.IoT Build 0:fa2de1b79154 239 size_t destinationPosition = 0;
Azure.IoT Build 0:fa2de1b79154 240 while (size - currentPosition >= 3)
Azure.IoT Build 0:fa2de1b79154 241 {
Azure.IoT Build 0:fa2de1b79154 242 char c1 = base64char[source[currentPosition] >> 2];
Azure.IoT Build 0:fa2de1b79154 243 char c2 = base64char[
Azure.IoT Build 0:fa2de1b79154 244 ((source[currentPosition] & 3) << 4) |
Azure.IoT Build 0:fa2de1b79154 245 (source[currentPosition + 1] >> 4)
Azure.IoT Build 0:fa2de1b79154 246 ];
Azure.IoT Build 0:fa2de1b79154 247 char c3 = base64char[
Azure.IoT Build 0:fa2de1b79154 248 ((source[currentPosition + 1] & 0x0F) << 2) |
Azure.IoT Build 0:fa2de1b79154 249 ((source[currentPosition + 2] >> 6) & 3)
Azure.IoT Build 0:fa2de1b79154 250 ];
Azure.IoT Build 0:fa2de1b79154 251 char c4 = base64char[
Azure.IoT Build 0:fa2de1b79154 252 source[currentPosition + 2] & 0x3F
Azure.IoT Build 0:fa2de1b79154 253 ];
Azure.IoT Build 0:fa2de1b79154 254 currentPosition += 3;
Azure.IoT Build 0:fa2de1b79154 255 encoded[destinationPosition++] = c1;
Azure.IoT Build 0:fa2de1b79154 256 encoded[destinationPosition++] = c2;
Azure.IoT Build 0:fa2de1b79154 257 encoded[destinationPosition++] = c3;
Azure.IoT Build 0:fa2de1b79154 258 encoded[destinationPosition++] = c4;
Azure.IoT Build 0:fa2de1b79154 259
Azure.IoT Build 0:fa2de1b79154 260 }
Azure.IoT Build 0:fa2de1b79154 261 if (size - currentPosition == 2)
Azure.IoT Build 0:fa2de1b79154 262 {
Azure.IoT Build 0:fa2de1b79154 263 char c1 = base64char[source[currentPosition] >> 2];
Azure.IoT Build 0:fa2de1b79154 264 char c2 = base64char[
Azure.IoT Build 0:fa2de1b79154 265 ((source[currentPosition] & 0x03) << 4) |
Azure.IoT Build 0:fa2de1b79154 266 (source[currentPosition + 1] >> 4)
Azure.IoT Build 0:fa2de1b79154 267 ];
Azure.IoT Build 0:fa2de1b79154 268 char c3 = base64b16[source[currentPosition + 1] & 0x0F];
Azure.IoT Build 0:fa2de1b79154 269 encoded[destinationPosition++] = c1;
Azure.IoT Build 0:fa2de1b79154 270 encoded[destinationPosition++] = c2;
Azure.IoT Build 0:fa2de1b79154 271 encoded[destinationPosition++] = c3;
Azure.IoT Build 0:fa2de1b79154 272 encoded[destinationPosition++] = '=';
Azure.IoT Build 0:fa2de1b79154 273 }
Azure.IoT Build 0:fa2de1b79154 274 else if (size - currentPosition == 1)
Azure.IoT Build 0:fa2de1b79154 275 {
Azure.IoT Build 0:fa2de1b79154 276 char c1 = base64char[source[currentPosition] >> 2];
Azure.IoT Build 0:fa2de1b79154 277 char c2 = base64b8[source[currentPosition] & 0x03];
Azure.IoT Build 0:fa2de1b79154 278 encoded[destinationPosition++] = c1;
Azure.IoT Build 0:fa2de1b79154 279 encoded[destinationPosition++] = c2;
Azure.IoT Build 0:fa2de1b79154 280 encoded[destinationPosition++] = '=';
Azure.IoT Build 0:fa2de1b79154 281 encoded[destinationPosition++] = '=';
Azure.IoT Build 0:fa2de1b79154 282 }
Azure.IoT Build 0:fa2de1b79154 283
Azure.IoT Build 0:fa2de1b79154 284 /*null terminating the string*/
Azure.IoT Build 0:fa2de1b79154 285 encoded[destinationPosition] = '\0';
Azure.IoT Build 0:fa2de1b79154 286 /*Codes_SRS_BASE64_06_007: [Otherwise Base64_Encode shall return a pointer to STRING, that string contains the base 64 encoding of input.]*/
Azure.IoT Build 0:fa2de1b79154 287 result = STRING_new_with_memory(encoded);
Azure.IoT Build 0:fa2de1b79154 288 if (result == NULL)
Azure.IoT Build 0:fa2de1b79154 289 {
Azure.IoT Build 0:fa2de1b79154 290 free(encoded);
AzureIoTClient 1:9190c0f4d23a 291 LogError("Base64_Encode:: Allocation failed for return value.");
Azure.IoT Build 0:fa2de1b79154 292 }
Azure.IoT Build 0:fa2de1b79154 293 }
Azure.IoT Build 0:fa2de1b79154 294 return result;
Azure.IoT Build 0:fa2de1b79154 295 }
Azure.IoT Build 0:fa2de1b79154 296
Azure.IoT Build 0:fa2de1b79154 297 STRING_HANDLE Base64_Encode_Bytes(const unsigned char* source, size_t size)
Azure.IoT Build 0:fa2de1b79154 298 {
Azure.IoT Build 0:fa2de1b79154 299 STRING_HANDLE result;
Azure.IoT Build 0:fa2de1b79154 300 /*Codes_SRS_BASE64_02_001: [If source is NULL then Base64_Encode_Bytes shall return NULL.] */
Azure.IoT Build 0:fa2de1b79154 301 if (source == NULL)
Azure.IoT Build 0:fa2de1b79154 302 {
Azure.IoT Build 0:fa2de1b79154 303 result = NULL;
Azure.IoT Build 0:fa2de1b79154 304 }
Azure.IoT Build 0:fa2de1b79154 305 /*Codes_SRS_BASE64_02_002: [If source is not NULL and size is zero, then Base64_Encode_Bytes shall produce an empty STRING_HANDLE.] */
Azure.IoT Build 0:fa2de1b79154 306 else if (size == 0)
Azure.IoT Build 0:fa2de1b79154 307 {
Azure.IoT Build 0:fa2de1b79154 308 result = STRING_new(); /*empty string*/
Azure.IoT Build 0:fa2de1b79154 309 }
Azure.IoT Build 0:fa2de1b79154 310 else
Azure.IoT Build 0:fa2de1b79154 311 {
Azure.IoT Build 0:fa2de1b79154 312 result = Base64_Encode_Internal(source, size);
Azure.IoT Build 0:fa2de1b79154 313 }
Azure.IoT Build 0:fa2de1b79154 314 return result;
Azure.IoT Build 0:fa2de1b79154 315 }
Azure.IoT Build 0:fa2de1b79154 316
Azure.IoT Build 0:fa2de1b79154 317 STRING_HANDLE Base64_Encode(BUFFER_HANDLE input)
Azure.IoT Build 0:fa2de1b79154 318 {
Azure.IoT Build 0:fa2de1b79154 319 STRING_HANDLE result;
Azure.IoT Build 0:fa2de1b79154 320 /*the following will happen*/
Azure.IoT Build 0:fa2de1b79154 321 /*1. the "data" of the binary shall be "eaten" 3 characters at a time and produce 4 base64 encoded characters for as long as there are more than 3 characters still to process*/
Azure.IoT Build 0:fa2de1b79154 322 /*2. the remaining characters (1 or 2) shall be encoded.*/
Azure.IoT Build 0:fa2de1b79154 323 /*there's a level of assumption that 'a' corresponds to 0b000000 and that '_' corresponds to 0b111111*/
Azure.IoT Build 0:fa2de1b79154 324 /*the encoding will use the optional [=] or [==] at the end of the encoded string, so that other less standard aware libraries can do their work*/
Azure.IoT Build 0:fa2de1b79154 325 /*these are the bits of the 3 normal bytes to be encoded*/
Azure.IoT Build 0:fa2de1b79154 326
Azure.IoT Build 0:fa2de1b79154 327 /*Codes_SRS_BASE64_06_001: [If input is NULL then Base64_Encode shall return NULL.]*/
Azure.IoT Build 0:fa2de1b79154 328 if (input == NULL)
Azure.IoT Build 0:fa2de1b79154 329 {
Azure.IoT Build 0:fa2de1b79154 330 result = NULL;
AzureIoTClient 1:9190c0f4d23a 331 LogError("Base64_Encode:: NULL input");
Azure.IoT Build 0:fa2de1b79154 332 }
Azure.IoT Build 0:fa2de1b79154 333 else
Azure.IoT Build 0:fa2de1b79154 334 {
Azure.IoT Build 0:fa2de1b79154 335 size_t inputSize;
Azure.IoT Build 0:fa2de1b79154 336 const unsigned char* inputBinary;
Azure.IoT Build 0:fa2de1b79154 337 if ((BUFFER_content(input, &inputBinary) != 0) ||
Azure.IoT Build 0:fa2de1b79154 338 (BUFFER_size(input, &inputSize) != 0))
Azure.IoT Build 0:fa2de1b79154 339 {
Azure.IoT Build 0:fa2de1b79154 340 result = NULL;
AzureIoTClient 1:9190c0f4d23a 341 LogError("Base64_Encode:: BUFFER_routines failure.");
Azure.IoT Build 0:fa2de1b79154 342 }
Azure.IoT Build 0:fa2de1b79154 343 else
Azure.IoT Build 0:fa2de1b79154 344 {
Azure.IoT Build 0:fa2de1b79154 345 result = Base64_Encode_Internal(inputBinary, inputSize);
Azure.IoT Build 0:fa2de1b79154 346 }
Azure.IoT Build 0:fa2de1b79154 347 }
Azure.IoT Build 0:fa2de1b79154 348 return result;
Azure.IoT Build 0:fa2de1b79154 349 }