github.com/jlmucb/cloudproxy@v0.0.0-20170830161738-b5aa0b619bc4/src/tpm2/GeneratePolicyKey.cc (about) 1 #include <stdio.h> 2 #include <stdlib.h> 3 #include <sys/types.h> 4 #include <sys/stat.h> 5 #include <fcntl.h> 6 #include <unistd.h> 7 #include <string.h> 8 9 #include <openssl/rsa.h> 10 #include <openssl_helpers.h> 11 12 #include <tpm20.h> 13 #include <tpm2_lib.h> 14 #include <tpm2.pb.h> 15 #include <gflags/gflags.h> 16 17 // 18 // Copyright 2015 Google Corporation, All Rights Reserved. 19 // 20 // Licensed under the Apache License, Version 2.0 (the "License"); 21 // you may not use this file except in compliance with the License. 22 // You may obtain a copy of the License at 23 // http://www.apache.org/licenses/LICENSE-2.0 24 // or in the the file LICENSE-2.0.txt in the top level sourcedirectory 25 // Unless required by applicable law or agreed to in writing, software 26 // distributed under the License is distributed on an "AS IS" BASIS, 27 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 28 // See the License for the specific language governing permissions and 29 // limitations under the License 30 // 31 // Portions of this code were derived TPM2.0-TSS published 32 // by Intel under the license set forth in intel_license.txt 33 // and downloaded on or about August 6, 2015. 34 // Portions of this code were derived tboot published 35 // by Intel under the license set forth in intel_license.txt 36 // and downloaded on or about August 6, 2015. 37 // Portions of this code were derived from the crypto utility 38 // published by John Manferdelli under the Apache 2.0 license. 39 // See github.com/jlmucb/crypto. 40 // File: GeneratePolicyKey.cc 41 42 43 // This program creates public/private key pair and produces a file containing 44 // a protobuf consisting of the keypair. It is usually the root of a Cloudproxy 45 // policy domain. 46 47 // Calling sequence 48 // GeneratePolicyKey.exe --algorithm="RSA" --modulus_size_in_bits=int32 49 // --key_name=input-file --cloudproxy_key_file=output-file 50 using std::string; 51 52 53 #define CALLING_SEQUENCE "GeneratePolicyKey.exe --algorithm=\"RSA\" "\ 54 " --exponent=exponent --modulus_size_in_bits=int32" \ 55 "--signing_instructions=input-file --key_name=input-file " \ 56 "--cloudproxy_key_file=output-file\n" 57 58 void PrintOptions() { 59 printf(CALLING_SEQUENCE); 60 } 61 62 DEFINE_string(algorithm, "RSA", "signing algorithm"); 63 DEFINE_int32(modulus_size_in_bits, 2048, "modulus-size"); 64 DEFINE_int64(exponent, 0x010001ULL, "exponent"); 65 DEFINE_string(signing_instructions, "", "input-file-name"); 66 DEFINE_string(, "", "input-file-name"); 67 DEFINE_string(key_name, "", "key name"); 68 DEFINE_string(cloudproxy_key_file, "", "output-file-name"); 69 70 #ifndef GFLAGS_NS 71 #define GFLAGS_NS google 72 #endif 73 74 #define MAXKEY_BUF 8192 75 #define DEBUG 76 77 int main(int an, char** av) { 78 int ret_val = 0; 79 RSA* rsa_key = nullptr; 80 byte der_array_private[MAXKEY_BUF]; 81 byte* start_private = nullptr; 82 byte* next_private = nullptr; 83 int len_private; 84 private_key_blob_message key_out; 85 string output; 86 87 printf("\nGeneratePolicyKey\n\n"); 88 89 GFLAGS_NS::ParseCommandLineFlags(&an, &av, true); 90 91 if (FLAGS_algorithm != "RSA") { 92 printf("Only RSA supported\n"); 93 ret_val = 1; 94 goto done; 95 } 96 if (FLAGS_signing_instructions == "") { 97 printf("No signing instructions\n"); 98 ret_val = 1; 99 goto done; 100 } 101 if (FLAGS_key_name == "") { 102 printf("No key name\n"); 103 ret_val = 1; 104 goto done; 105 } 106 if (FLAGS_cloudproxy_key_file == "") { 107 printf("No key file\n"); 108 ret_val = 1; 109 goto done; 110 } 111 112 rsa_key = RSA_generate_key(FLAGS_modulus_size_in_bits, 113 FLAGS_exponent, nullptr, nullptr); 114 if (rsa_key == nullptr) { 115 printf("Can't generate RSA key\n"); 116 ret_val = 1; 117 goto done; 118 } 119 len_private = i2d_RSAPrivateKey(rsa_key, nullptr); 120 start_private = der_array_private; 121 next_private = der_array_private; 122 i2d_RSAPrivateKey(rsa_key, (byte**)&next_private); 123 124 #ifdef DEBUG 125 printf("der encoded private key (%d): ", len_private); 126 PrintBytes(len_private, start_private); 127 printf("\n"); 128 #endif 129 130 key_out.set_key_type("RSA"); 131 key_out.set_key_name(FLAGS_key_name); 132 key_out.set_blob((const char*)start_private, len_private); 133 if (!key_out.SerializeToString(&output)) { 134 printf("Can't serialize output\n"); 135 ret_val = 1; 136 goto done; 137 } 138 if (!WriteFileFromBlock(FLAGS_cloudproxy_key_file, output.size(), 139 (byte*)output.data())) { 140 printf("Can't write output file\n"); 141 ret_val = 1; 142 } 143 144 // write it as protobuf too 145 { 146 rsa_private_key_message privateMsg; 147 privateMsg.mutable_public_key()->set_bit_modulus_size(FLAGS_modulus_size_in_bits); 148 byte exp_big_endian[4] = {0, 1, 0, 1}; 149 string e_b_e; 150 e_b_e.assign((const char*)exp_big_endian, 4); 151 152 privateMsg.mutable_public_key()->set_exponent(e_b_e); 153 string* n = BN_to_bin(*rsa_key->n); 154 string* d = BN_to_bin(*rsa_key->d); 155 privateMsg.mutable_public_key()->set_modulus(*n); 156 privateMsg.set_d(*d); 157 if (rsa_key->p != nullptr) { 158 string* p = BN_to_bin(*rsa_key->p); 159 privateMsg.set_p(*p); 160 } 161 if (rsa_key->q != nullptr) { 162 string* q = BN_to_bin(*rsa_key->q); 163 privateMsg.set_q(*q); 164 } 165 string proto_out; 166 if (!privateMsg.SerializeToString(&proto_out)) { 167 printf("Can't serialize proto\n"); 168 goto done; 169 } 170 string proto_file_name; 171 proto_file_name = FLAGS_cloudproxy_key_file + ".proto"; 172 if (!WriteFileFromBlock(proto_file_name, proto_out.size(), 173 (byte*)proto_out.data())) { 174 printf("Can't write output file\n"); 175 ret_val = 1; 176 } 177 } 178 179 done: 180 return ret_val; 181 } 182