12654012fSReza Sabdar /* 22654012fSReza Sabdar * Copyright 2008 Sun Microsystems, Inc. All rights reserved. 32654012fSReza Sabdar * Use is subject to license terms. 42654012fSReza Sabdar */ 52654012fSReza Sabdar 62654012fSReza Sabdar /* 72654012fSReza Sabdar * BSD 3 Clause License 82654012fSReza Sabdar * 92654012fSReza Sabdar * Copyright (c) 2007, The Storage Networking Industry Association. 102654012fSReza Sabdar * 112654012fSReza Sabdar * Redistribution and use in source and binary forms, with or without 122654012fSReza Sabdar * modification, are permitted provided that the following conditions 132654012fSReza Sabdar * are met: 142654012fSReza Sabdar * - Redistributions of source code must retain the above copyright 152654012fSReza Sabdar * notice, this list of conditions and the following disclaimer. 162654012fSReza Sabdar * 172654012fSReza Sabdar * - Redistributions in binary form must reproduce the above copyright 182654012fSReza Sabdar * notice, this list of conditions and the following disclaimer in 192654012fSReza Sabdar * the documentation and/or other materials provided with the 202654012fSReza Sabdar * distribution. 212654012fSReza Sabdar * 222654012fSReza Sabdar * - Neither the name of The Storage Networking Industry Association (SNIA) 232654012fSReza Sabdar * nor the names of its contributors may be used to endorse or promote 242654012fSReza Sabdar * products derived from this software without specific prior written 252654012fSReza Sabdar * permission. 262654012fSReza Sabdar * 272654012fSReza Sabdar * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 282654012fSReza Sabdar * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 292654012fSReza Sabdar * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 302654012fSReza Sabdar * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE 312654012fSReza Sabdar * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 322654012fSReza Sabdar * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 332654012fSReza Sabdar * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 342654012fSReza Sabdar * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 352654012fSReza Sabdar * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 362654012fSReza Sabdar * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 372654012fSReza Sabdar * POSSIBILITY OF SUCH DAMAGE. 382654012fSReza Sabdar */ 39*8b87c155SJan Kryl /* Copyright 2014 Nexenta Systems, Inc. All rights reserved. */ 402654012fSReza Sabdar 412654012fSReza Sabdar #include <stdio.h> 422654012fSReza Sabdar #include <sys/types.h> 432654012fSReza Sabdar #include <string.h> 442654012fSReza Sabdar #include <ctype.h> 452654012fSReza Sabdar #include <stdlib.h> 462654012fSReza Sabdar #include <libndmp.h> 472654012fSReza Sabdar 482654012fSReza Sabdar #define NDMP_ENC_LEN 1024 492654012fSReza Sabdar #define NDMP_DEC_LEN 256 502654012fSReza Sabdar 512654012fSReza Sabdar static boolean_t ndmp_is_base64(unsigned char); 522654012fSReza Sabdar 532654012fSReza Sabdar static char *b64_data = 542654012fSReza Sabdar "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/"; 552654012fSReza Sabdar 562654012fSReza Sabdar static boolean_t 572654012fSReza Sabdar ndmp_is_base64(unsigned char c) 582654012fSReza Sabdar { 592654012fSReza Sabdar return (isalnum(c) || (c == '+') || (c == '/')); 602654012fSReza Sabdar } 612654012fSReza Sabdar 62*8b87c155SJan Kryl /* caller should use the encoded string and then free the string. */ 632654012fSReza Sabdar char * 64*8b87c155SJan Kryl ndmp_base64_encode(const char *str_to_encode) 652654012fSReza Sabdar { 662654012fSReza Sabdar int ret_cnt = 0; 672654012fSReza Sabdar int i = 0, j = 0; 682654012fSReza Sabdar char arr_3[3], arr_4[4]; 692654012fSReza Sabdar int len = strlen(str_to_encode); 702654012fSReza Sabdar char *ret = malloc(NDMP_ENC_LEN); 712654012fSReza Sabdar 722654012fSReza Sabdar if (ret == NULL) { 732654012fSReza Sabdar ndmp_errno = ENDMP_MEM_ALLOC; 742654012fSReza Sabdar return (NULL); 752654012fSReza Sabdar } 762654012fSReza Sabdar 772654012fSReza Sabdar while (len--) { 782654012fSReza Sabdar arr_3[i++] = *(str_to_encode++); 792654012fSReza Sabdar if (i == 3) { 802654012fSReza Sabdar arr_4[0] = (arr_3[0] & 0xfc) >> 2; 812654012fSReza Sabdar arr_4[1] = ((arr_3[0] & 0x03) << 4) + 822654012fSReza Sabdar ((arr_3[1] & 0xf0) >> 4); 832654012fSReza Sabdar arr_4[2] = ((arr_3[1] & 0x0f) << 2) + 842654012fSReza Sabdar ((arr_3[2] & 0xc0) >> 6); 852654012fSReza Sabdar arr_4[3] = arr_3[2] & 0x3f; 862654012fSReza Sabdar 872654012fSReza Sabdar for (i = 0; i < 4; i++) 882654012fSReza Sabdar ret[ret_cnt++] = b64_data[arr_4[i]]; 892654012fSReza Sabdar i = 0; 902654012fSReza Sabdar } 912654012fSReza Sabdar } 922654012fSReza Sabdar 932654012fSReza Sabdar if (i) { 942654012fSReza Sabdar for (j = i; j < 3; j++) 952654012fSReza Sabdar arr_3[j] = '\0'; 962654012fSReza Sabdar 972654012fSReza Sabdar arr_4[0] = (arr_3[0] & 0xfc) >> 2; 982654012fSReza Sabdar arr_4[1] = ((arr_3[0] & 0x03) << 4) + 992654012fSReza Sabdar ((arr_3[1] & 0xf0) >> 4); 1002654012fSReza Sabdar arr_4[2] = ((arr_3[1] & 0x0f) << 2) + 1012654012fSReza Sabdar ((arr_3[2] & 0xc0) >> 6); 1022654012fSReza Sabdar arr_4[3] = arr_3[2] & 0x3f; 1032654012fSReza Sabdar 1042654012fSReza Sabdar for (j = 0; j < (i + 1); j++) 1052654012fSReza Sabdar ret[ret_cnt++] = b64_data[arr_4[j]]; 1062654012fSReza Sabdar 1072654012fSReza Sabdar while (i++ < 3) 1082654012fSReza Sabdar ret[ret_cnt++] = '='; 1092654012fSReza Sabdar } 1102654012fSReza Sabdar 1112654012fSReza Sabdar ret[ret_cnt++] = '\0'; 1122654012fSReza Sabdar return (ret); 1132654012fSReza Sabdar } 1142654012fSReza Sabdar 1152654012fSReza Sabdar char * 116*8b87c155SJan Kryl ndmp_base64_decode(const char *encoded_str) 1172654012fSReza Sabdar { 1182654012fSReza Sabdar int len = strlen(encoded_str); 1192654012fSReza Sabdar int i = 0, j = 0; 1202654012fSReza Sabdar int en_ind = 0; 1212654012fSReza Sabdar char arr_4[4], arr_3[3]; 1222654012fSReza Sabdar int ret_cnt = 0; 1232654012fSReza Sabdar char *ret = malloc(NDMP_DEC_LEN); 1242654012fSReza Sabdar char *p; 1252654012fSReza Sabdar 1262654012fSReza Sabdar if (ret == NULL) { 1272654012fSReza Sabdar ndmp_errno = ENDMP_MEM_ALLOC; 1282654012fSReza Sabdar return (NULL); 1292654012fSReza Sabdar } 1302654012fSReza Sabdar 1312654012fSReza Sabdar while (len-- && (encoded_str[en_ind] != '=') && 1322654012fSReza Sabdar ndmp_is_base64(encoded_str[en_ind])) { 1332654012fSReza Sabdar arr_4[i++] = encoded_str[en_ind]; 1342654012fSReza Sabdar en_ind++; 1352654012fSReza Sabdar if (i == 4) { 1362654012fSReza Sabdar for (i = 0; i < 4; i++) { 137*8b87c155SJan Kryl if ((p = strchr(b64_data, arr_4[i])) == NULL) { 138*8b87c155SJan Kryl free(ret); 1392654012fSReza Sabdar return (NULL); 140*8b87c155SJan Kryl } 1412654012fSReza Sabdar 1422654012fSReza Sabdar arr_4[i] = (int)(p - b64_data); 1432654012fSReza Sabdar } 1442654012fSReza Sabdar 1452654012fSReza Sabdar arr_3[0] = (arr_4[0] << 2) + 1462654012fSReza Sabdar ((arr_4[1] & 0x30) >> 4); 1472654012fSReza Sabdar arr_3[1] = ((arr_4[1] & 0xf) << 4) + 1482654012fSReza Sabdar ((arr_4[2] & 0x3c) >> 2); 1492654012fSReza Sabdar arr_3[2] = ((arr_4[2] & 0x3) << 6) + 1502654012fSReza Sabdar arr_4[3]; 1512654012fSReza Sabdar 1522654012fSReza Sabdar for (i = 0; i < 3; i++) 1532654012fSReza Sabdar ret[ret_cnt++] = arr_3[i]; 1542654012fSReza Sabdar 1552654012fSReza Sabdar i = 0; 1562654012fSReza Sabdar } 1572654012fSReza Sabdar } 1582654012fSReza Sabdar 1592654012fSReza Sabdar if (i) { 1602654012fSReza Sabdar for (j = i; j < 4; j++) 1612654012fSReza Sabdar arr_4[j] = 0; 1622654012fSReza Sabdar 1632654012fSReza Sabdar for (j = 0; j < 4; j++) { 164*8b87c155SJan Kryl if ((p = strchr(b64_data, arr_4[j])) == NULL) { 165*8b87c155SJan Kryl free(ret); 1662654012fSReza Sabdar return (NULL); 167*8b87c155SJan Kryl } 1682654012fSReza Sabdar 1692654012fSReza Sabdar arr_4[j] = (int)(p - b64_data); 1702654012fSReza Sabdar } 1712654012fSReza Sabdar arr_3[0] = (arr_4[0] << 2) + 1722654012fSReza Sabdar ((arr_4[1] & 0x30) >> 4); 1732654012fSReza Sabdar arr_3[1] = ((arr_4[1] & 0xf) << 4) + 1742654012fSReza Sabdar ((arr_4[2] & 0x3c) >> 2); 1752654012fSReza Sabdar arr_3[2] = ((arr_4[2] & 0x3) << 6) + 1762654012fSReza Sabdar arr_4[3]; 1772654012fSReza Sabdar for (j = 0; j < (i - 1); j++) 1782654012fSReza Sabdar ret[ret_cnt++] = arr_3[j]; 1792654012fSReza Sabdar } 1802654012fSReza Sabdar 1812654012fSReza Sabdar ret[ret_cnt++] = '\0'; 1822654012fSReza Sabdar return (ret); 1832654012fSReza Sabdar } 184