github.com/jlmucb/cloudproxy@v0.0.0-20170830161738-b5aa0b619bc4/src/tpm2/conversions.cc (about)

     1  //
     2  // Copyright 2014 John Manferdelli, All Rights Reserved.
     3  //
     4  // Licensed under the Apache License, Version 2.0 (the "License");
     5  // you may not use this file except in compliance with the License.
     6  // You may obtain a copy of the License at
     7  //     http://www.apache.org/licenses/LICENSE-2.0
     8  // or in the the file LICENSE-2.0.txt in the top level sourcedirectory
     9  // Unless required by applicable law or agreed to in writing, software
    10  // distributed under the License is distributed on an "AS IS" BASIS,
    11  // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    12  // See the License for the specific language governing permissions and
    13  // limitations under the License
    14  // Project: New Cloudproxy Crypto
    15  
    16  #include <string>
    17  #include <sys/types.h>
    18  #include <sys/stat.h>
    19  #include <string.h>
    20  #include <stdio.h>
    21  #include <tpm2_types.h>
    22  
    23  using namespace std;
    24  
    25  const char* websafebase64_order =
    26      "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-_";
    27  
    28  void ThreeBytesToBase64(byte a, byte b, byte c, char* out) {
    29    byte x;
    30  
    31    x = (a >> 2) & 0x3f;
    32    *out = websafebase64_order[x];
    33    x = ((a << 4) & 0x3f) | (b >> 4);
    34    *(out + 1) = websafebase64_order[x];
    35    x = ((b << 2) & 0x3f) | (c >> 6);
    36    *(out + 2) = websafebase64_order[x];
    37    x = c & 0x3f;
    38    *(out + 3) = websafebase64_order[x];
    39    return;
    40  }
    41  
    42  void TwoBytesToBase64(byte a, byte b, char* out) {
    43    byte x;
    44  
    45    x = (a >> 2) & 0x3f;
    46    *out = websafebase64_order[x];
    47    x = ((a << 4) & 0x3f) | (b >> 4);
    48    *(out + 1) = websafebase64_order[x];
    49    x = (b << 2) & 0x3f;
    50    *(out + 2) = websafebase64_order[x];
    51    *(out + 3) = '=';
    52    return;
    53  }
    54  
    55  void OneByteToBase64(byte a, char* out) {
    56    byte x;
    57  
    58    x = a >> 2;
    59    *out = websafebase64_order[x];
    60    x = (a & 0x3) << 4;
    61    *(out + 1) = websafebase64_order[x];
    62    *(out + 2) = '=';
    63    *(out + 3) = '=';
    64    return;
    65  }
    66  
    67  int NumBase64StringInBytes(int size, byte* in) {
    68    int n = (size + 3) / 3;
    69    return n * 4;
    70  }
    71  
    72  int NumBytesInBase64String(char* in) {
    73    if (in == nullptr)
    74      return 0;
    75    int j = strlen(in);
    76    // j should be a multiple of 4
    77    if ((j & 0x3) != 0)
    78      return -1;
    79    int n = (j / 4) * 3;
    80    if (in[j - 1] == '=') {
    81      if (in[j - 2] == '=')
    82        return n - 2;
    83      return n - 1;
    84    }
    85    return n;
    86  }
    87  
    88  byte Base64CharValue(char a) {
    89    if (a >= 'A' && a <= 'Z') {
    90      return a - 'A';
    91    } else if (a >= 'a' && a <= 'z') {
    92      return a - 'a' + 26;
    93    } else if (a >= '0' && a <= '9') {
    94      return a - '0' + 52;
    95    } else if (a == '-') {
    96      return 62;
    97    } else if (a == '_') {
    98      return 63;
    99    } else {
   100      return 0xff;
   101    }
   102  }
   103  
   104  bool FourBase64ToBytes(char* in, byte* out) {
   105    byte x, y;
   106  
   107    x = Base64CharValue(*in);
   108    y = Base64CharValue(*(in + 1));
   109    if (x == 0xff || y == 0xff)
   110      return false;
   111    *out = (x << 2) | (y >> 4);
   112    if (*(in + 2) == '=') {
   113      return true;
   114    }
   115    x = Base64CharValue(*(in + 2));
   116    if (x == 0xff)
   117      return false;
   118    *(out + 1) = y << 4 | x >> 2;
   119    if (*(in + 3) == '=')
   120      return true;
   121    y = Base64CharValue(*(in + 3));
   122    if (y == 0xff)
   123      return false;
   124    *(out + 2) = (x << 6) | y;
   125    return true;
   126  }
   127  
   128  bool FourBase64ToBytesReverse(char* in, byte* out) {
   129    byte x, y;
   130  
   131    x = Base64CharValue(*in);
   132    y = Base64CharValue(*(in + 1));
   133    if (x == 0xff || y == 0xff)
   134      return false;
   135    *out = (x << 2) | (y >> 4);
   136    if (*(in + 2) == '=') {
   137      return true;
   138    }
   139    x = Base64CharValue(*(in + 2));
   140    if (x == 0xff)
   141      return false;
   142    *(out - 1) = y << 4 | x >> 2;
   143    if (*(in + 3) == '=')
   144      return true;
   145    y = Base64CharValue(*(in + 3));
   146    if (y == 0xff)
   147      return false;
   148    *(out - 2) = (x << 6) | y;
   149    return true;
   150  }
   151  
   152  string* ByteToBase64LeftToRight(int size, byte* in) {
   153    int n = NumBase64StringInBytes(size, in);
   154    string* out = new string(n, 0);
   155    char* str = (char*)out->c_str();
   156  
   157    if (size <= 0 || in == nullptr)
   158      return nullptr;
   159    while (size >= 3) {
   160      ThreeBytesToBase64(*in, *(in + 1), *(in + 2), str);
   161      in += 3;
   162      str += 4;
   163      size -= 3;
   164    }
   165    if (size == 2) {
   166      TwoBytesToBase64(*in, *(in + 1), str);
   167      in += 2;
   168      str += 4;
   169      size -= 2;
   170    }
   171    if (size == 1) {
   172      OneByteToBase64(*in, str);
   173      in += 1;
   174      str += 4;
   175      size -= 1;
   176    }
   177    return out;
   178  }
   179  
   180  string* ByteToBase64RightToLeft(int size, byte* in) {
   181    int n = NumBase64StringInBytes(size, in);
   182    string* out = new string(n, 0);
   183    char* str = (char*)out->c_str();
   184  
   185    if (size <= 0 || in == nullptr)
   186      return nullptr;
   187    in += size - 1;
   188    while (size >= 3) {
   189      ThreeBytesToBase64(*in, *(in - 1), *(in - 2), str);
   190      in -= 3;
   191      str += 4;
   192      size -= 3;
   193    }
   194    if (size == 2) {
   195      TwoBytesToBase64(*in, *(in - 1), str);
   196      in -= 2;
   197      str += 4;
   198      size -= 2;
   199    }
   200    if (size == 1) {
   201      OneByteToBase64(*in, str);
   202      in -= 1;
   203      str += 4;
   204      size -= 1;
   205    }
   206    return out;
   207  }
   208  
   209  int Base64ToByteLeftToRight(char* in, int size, byte* out) {
   210    if (in == nullptr)
   211       return -1;
   212  
   213    int k = strlen(in);
   214    if ((k & 0x3) != 0)
   215      return -1;
   216    int n = NumBytesInBase64String(in);
   217  
   218    if (n > size)
   219      return -1;
   220  
   221    while (k > 0) {
   222      FourBase64ToBytes(in, out);
   223      in += 4;
   224      out += 3;
   225      k -= 4;
   226    }
   227  
   228    return n;
   229  }
   230  
   231  int Base64ToByteRightToLeft(char* in, int size, byte* out) {
   232    if (in == nullptr)
   233      return -1;
   234    int k = strlen(in);
   235    if ((k & 0x3) != 0)
   236      return -1;
   237  
   238    int n = NumBytesInBase64String(in);
   239    if (n > size)
   240      return -1;
   241  
   242    out += n - 1;
   243    while (k > 0) {
   244      FourBase64ToBytesReverse(in, out);
   245      in += 4;
   246      out -= 3;
   247      k -= 4;
   248    }
   249    return n;
   250  }
   251  
   252  int NumHexInBytes(int size, byte* in) { return 2 * size; }
   253  
   254  int NumBytesInHex(char* in) {
   255    if (in == nullptr)
   256      return -1;
   257    int len = strlen(in);
   258    return ((len + 1) / 2);
   259  }
   260  
   261  char ValueToHex(byte x) {
   262    if (x >= 0 && x <= 9) {
   263      return x + '0';
   264    } else if (x >= 10 && x <= 15) {
   265      return x - 10 + 'a';
   266    } else {
   267      return ' ';
   268    }
   269  }
   270  
   271  byte HexToValue(char x) {
   272    if (x >= '0' && x <= '9') {
   273      return x - '0';
   274    } else if (x >= 'a' && x <= 'f') {
   275      return x + 10 - 'a';
   276    } else {
   277      return 0;
   278    }
   279  }
   280  
   281  string* ByteToHexLeftToRight(int size, byte* in) {
   282    if (in == nullptr)
   283      return nullptr;
   284    int n = NumHexInBytes(size, in);
   285    string* out = new string(n, 0);
   286    char* str = (char*)out->c_str();
   287    byte a, b;
   288  
   289    while (size > 0) {
   290      a = (*in) >> 4;
   291      b = (*in) & 0xf;
   292      in++;
   293      *(str++) = ValueToHex(a);
   294      *(str++) = ValueToHex(b);
   295      size--;
   296    }
   297    return out;
   298  }
   299  
   300  int HexToByteLeftToRight(char* in, int size, byte* out) {
   301    if (in == nullptr)
   302      return -1;
   303    int n = NumBytesInHex(in);
   304    int m = strlen(in);
   305    byte a, b;
   306  
   307    if (n > size) {
   308      return -1;
   309    }
   310    while (m > 0) {
   311      a = HexToValue(*(in++));
   312      b = HexToValue(*(in++));
   313      *(out++) = (a << 4) | b;
   314      m -= 2;
   315    }
   316    return n;
   317  }
   318  
   319  string* ByteToHexRightToLeft(int size, byte* in) {
   320    if (in == nullptr)
   321      return nullptr;
   322    int n = NumHexInBytes(size, in);
   323    string* out = new string(n, 0);
   324    char* str = (char*)out->c_str();
   325    byte a, b;
   326  
   327    in += size - 1;
   328    while (size > 0) {
   329      a = (*in) >> 4;
   330      b = (*in) & 0xf;
   331      in--;
   332      *(str++) = ValueToHex(a);
   333      *(str++) = ValueToHex(b);
   334      size--;
   335    }
   336    return out;
   337  }
   338  
   339  int HexToByteRightToLeft(char* in, int size, byte* out) {
   340    if (in == nullptr) {
   341      return -1;
   342    }
   343    int n = NumBytesInHex(in);
   344    int m = strlen(in);
   345    byte a, b;
   346  
   347    out += n - 1;
   348    if (m < 0) {
   349      return -1;
   350    }
   351    while (m > 0) {
   352      a = HexToValue(*(in++));
   353      b = HexToValue(*(in++));
   354      *(out--) = (a << 4) | b;
   355      m -= 2;
   356    }
   357    return n;
   358  }