Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(362)

Side by Side Diff: pkcs11.cc

Issue 2523001: Implemented ReadObjectsFromSlot() to populate pkcs11.slots on initialization. (Closed) Base URL: ssh://git@chromiumos-git/entd.git
Patch Set: Small change from feedback Created 10 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « pkcs11.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2010 The Chromium OS Authors. All rights reserved. 1 // Copyright (c) 2010 The Chromium OS Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "entd/pkcs11.h" 5 #include "entd/pkcs11.h"
6 6
7 #include <algorithm> 7 #include <algorithm>
8 #include <iostream> 8 #include <iostream>
9 #include <map> 9 #include <map>
10 #include <string> 10 #include <string>
(...skipping 10 matching lines...) Expand all
21 #include <openssl/bn.h> 21 #include <openssl/bn.h>
22 22
23 #include "entd/utils.h" 23 #include "entd/utils.h"
24 24
25 namespace entd { 25 namespace entd {
26 26
27 // Class SlotObject declaration (implementation below) 27 // Class SlotObject declaration (implementation below)
28 // SlotObject JavaScript interface wrapper around Pkcs11SlotHandler. 28 // SlotObject JavaScript interface wrapper around Pkcs11SlotHandler.
29 class SlotObject : public JSObjectWrapper<SlotObject> { 29 class SlotObject : public JSObjectWrapper<SlotObject> {
30 public: 30 public:
31 SlotObject() : slot_handler_(NULL) { } 31 SlotObject() : slot_handler_(NULL) {}
32 SlotObject(const std::string& label, const std::string& key_id)
33 : label_(label), key_identifier_(key_id), slot_handler_(NULL) {}
32 virtual ~SlotObject() {} 34 virtual ~SlotObject() {}
33 35
34 virtual bool Initialize(); 36 virtual bool Initialize();
35 37
36 // JSObjectWrapper Interface 38 // JSObjectWrapper Interface
37 virtual void ParseConstructorArgs( 39 virtual void ParseConstructorArgs(
38 v8::Handle<v8::Object> obj, const v8::Arguments& args); 40 v8::Handle<v8::Object> obj, const v8::Arguments& args);
39 static void SetTemplateBindings( 41 static void SetTemplateBindings(
40 v8::Handle<v8::ObjectTemplate> template_object); 42 v8::Handle<v8::ObjectTemplate> template_object);
41 static const char* GetClassName() { return "SlotObject"; } 43 static const char* GetClassName() { return "SlotObject"; }
42 44
43 // Accessors 45 // Accessors
44 const std::string& label() const { return label_; } 46 const std::string& label() const { return label_; }
45 const std::string& key_identifier() const { return key_identifier_; } 47 const std::string& key_identifier() const { return key_identifier_; }
46 const std::string& passphrase() const { return passphrase_; } 48 const std::string& passphrase() const { return passphrase_; }
47 std::string GetPublicKey() const { 49 std::string GetPublicKey() const {
48 return slot_handler()->GetPublicKey(label_); 50 return slot_handler()->GetPublicKey(label_);
49 } 51 }
50 Pkcs11SlotHandler* slot_handler() const { return slot_handler_; } 52 Pkcs11SlotHandler* slot_handler() const { return slot_handler_; }
51 53
52 // Setters 54 // Setters
53 55
54 // Stores the key identifier and passes it to the slot handler. 56 // Stores the key identifier and passes it to the slot handler.
55 const bool SetKeyIdentifier(const std::string& id) { 57 bool SetKeyIdentifier(const std::string& id) {
56 key_identifier_ = id; 58 key_identifier_ = id;
57 return slot_handler_->SetKeyIdentifier(label_, id); 59 return slot_handler_->SetKeyIdentifier(label_, id);
58 } 60 }
59 const void SetPassphrase(const std::string& passphrase) { 61 const void SetPassphrase(const std::string& passphrase) {
60 passphrase_ = passphrase; 62 passphrase_ = passphrase;
61 } 63 }
62 void SetSlotHandler(Pkcs11SlotHandler* slot_handler) { 64 void SetSlotHandler(Pkcs11SlotHandler* slot_handler) {
63 slot_handler_ = slot_handler; 65 slot_handler_ = slot_handler;
64 } 66 }
65 67
66 private: 68 private:
67 std::string label_; 69 std::string label_;
68 std::string key_identifier_; 70 std::string key_identifier_;
69 std::string passphrase_; 71 std::string passphrase_;
70 Pkcs11SlotHandler* slot_handler_; 72 Pkcs11SlotHandler* slot_handler_;
71 73
72 DISALLOW_COPY_AND_ASSIGN(SlotObject); 74 DISALLOW_COPY_AND_ASSIGN(SlotObject);
73 }; 75 };
74 76
77 // Class Certificate declaration (implementation below)
78 // Certificate JavaScript interface wrapper around Pkcs11CertificateHandler.
79 class Certificate : public JSObjectWrapper<Certificate> {
80 public:
81 Certificate() {}
82 virtual ~Certificate() {}
83
84 // JSObjectWrapper Interface
85 virtual void ParseConstructorArgs(
86 v8::Handle<v8::Object> obj, const v8::Arguments& args);
87 static void SetTemplateBindings(
88 v8::Handle<v8::ObjectTemplate> template_object);
89 static const char* GetClassName() { return "Certificate"; }
90
91 // Accessors
92 const chromeos::Blob& certificate() const { return certificate_; }
93 const std::string& subject() const { return subject_; }
94
95 // Certificate handler management
96 static void InitCertificateHandler(Pkcs11CertificateHandler* handler) {
97 certificate_handler_ = handler;
98 }
99 static Pkcs11CertificateHandler* certificate_handler() {
100 return certificate_handler_;
101 }
102
103 private:
104 // The certificate may contain binary data, so store it as an array of bytes
105 // instead of a string.
106 chromeos::Blob certificate_;
107 std::string subject_;
108 static Pkcs11CertificateHandler* certificate_handler_;
109
110 DISALLOW_COPY_AND_ASSIGN(Certificate);
111 };
75 112
76 // class Pkcs11CertificateHandlerLocalFile 113 // class Pkcs11CertificateHandlerLocalFile
77 // Test Certificate handler that returns the contents of a file. 114 // Test Certificate handler that returns the contents of a file.
78 // 115 //
79 // If the csr or cert file exists, the contents of the file is returned 116 // If the csr or cert file exists, the contents of the file is returned
80 // in BuildCSR or BuildCertificate; subject or content arguments are ignored. 117 // in BuildCSR or BuildCertificate; subject or content arguments are ignored.
81 // If the filename is empty or the file does not exist, a string 118 // If the filename is empty or the file does not exist, a string
82 // containing the subject or content is returned instead. 119 // containing the subject or content is returned instead.
83 class Pkcs11CertificateHandlerLocalFile : public Pkcs11CertificateHandler { 120 class Pkcs11CertificateHandlerLocalFile : public Pkcs11CertificateHandler {
84 public: 121 public:
(...skipping 683 matching lines...) Expand 10 before | Expand all | Expand 10 after
768 LOG(INFO) << "Pkcs11SlotHandlerOpenCryptoki Initialized. Using slot: " 805 LOG(INFO) << "Pkcs11SlotHandlerOpenCryptoki Initialized. Using slot: "
769 << slot_index_; 806 << slot_index_;
770 res = true; 807 res = true;
771 } 808 }
772 809
773 free(slot_list); 810 free(slot_list);
774 if (res) { 811 if (res) {
775 res = Pkcs11SlotHandlerInMemory::Initialize(); 812 res = Pkcs11SlotHandlerInMemory::Initialize();
776 } 813 }
777 814
778 // TODO(stevenjb): read existing objects into objects_ 815 return res;
816 }
779 817
780 return res; 818 bool ReadObjectsFromSlot(Pkcs11* pkcs11) {
819 CK_SESSION_HANDLE session_handle = NULL;
820 CK_RV rv = C_OpenSession(slot_id_,
821 CKF_SERIAL_SESSION|CKF_RW_SESSION, NULL, NULL,
822 &session_handle);
823 if (rv != CKR_OK) {
824 LOG(ERROR) << "C_OpenSession failed, error: " << rv
825 << ", slot: " << slot_index_;
826 return false;
827 }
828
829 // Gather a list of objects in the slot
830 int num_objects = 0;
831
832 rv = C_FindObjectsInit(session_handle, NULL, 0);
833 if (rv != CKR_OK) {
834 LOG(ERROR) << "C_FindObjectsInit failed: " << rv;
835 return false;
836 }
837
838 while (1) {
839 CK_ULONG count;
840 CK_OBJECT_HANDLE object;
841 rv = C_FindObjects(session_handle, &object, 1, &count);
842 if (rv != CKR_OK) {
843 LOG(ERROR) << "C_FindObjects failed: " << rv;
844 return false;
845 }
846 if (count == 0) {
847 // No more objects to read, exit loop.
848 break;
849 }
850 ++num_objects;
851
852 const size_t LABEL_MAX_LENGTH = 256;
853 const size_t IDSTR_MAX_LENGTH = 8;
854 const size_t SUBJECT_MAX_LENGTH = 1024;
855
856 // Define a template with the values we are interested in
857 CK_OBJECT_CLASS obj_class;
858 char obj_label[LABEL_MAX_LENGTH];
859 CK_BYTE idstr[IDSTR_MAX_LENGTH];
860 CK_BYTE subject[SUBJECT_MAX_LENGTH];
861
862 CK_ATTRIBUTE obj_template[] = {
863 { CKA_CLASS, &obj_class, sizeof(obj_class) },
864 { CKA_LABEL, obj_label, LABEL_MAX_LENGTH },
865 { CKA_ID, idstr, IDSTR_MAX_LENGTH },
866 { CKA_SUBJECT, subject, SUBJECT_MAX_LENGTH },
867 };
868 int n_attr = sizeof(obj_template) / sizeof(CK_ATTRIBUTE);
869
870 // Read values into obj_template
871 rv = C_GetAttributeValue(session_handle, object, obj_template, n_attr);
872 if (rv != CKR_OK) {
873 LOG(ERROR) << "C_GetAttributeValue failed: " << rv
874 << " obj: " << num_objects;
875 }
876 obj_class = *(static_cast<CK_OBJECT_CLASS*>(obj_template[0].pValue));
877 if (obj_class == CKO_CERTIFICATE ||
878 obj_class == CKO_PUBLIC_KEY ||
879 obj_class == CKO_PRIVATE_KEY) {
880 if (obj_template[1].ulValueLen > 0) {
881 // Only parse certificate and key objects with a valid label
882 std::string label = TemplateToString(obj_template[1]);
883 std::string idstr = GetKeyFromId(
884 static_cast<CK_BYTE*>(obj_template[2].pValue),
885 obj_template[2].ulValueLen);
886 std::string subject = TemplateToString(obj_template[3]);
887 Object* obj = AddObject(label);
888 if (!obj->key_identifier_.empty() && obj->key_identifier_ != idstr) {
889 LOG(WARNING) << "Object '" << label << "' "
890 << "with mismatched key identifers: "
891 << "'" << obj->key_identifier_ << "'"
892 << " != '" << idstr << "'";
893 } else {
894 obj->key_identifier_ = idstr;
895 obj->subject_ = subject;
896 }
897 }
898 }
899 }
900
901 C_FindObjectsFinal(session_handle);
902
903 LOG(INFO) << "Found " << num_objects << " objects in slot.";
904
905 // Iterate through the list of objects and generate
906 // SlotObject objects and insert them into pkcs11.slots.
907 for (ObjectMap::iterator iter = objects_.begin();
908 iter != objects_.end(); ++iter) {
909 Object* object = iter->second.get();
910
911 // Build a slot object
912 SlotObject* slot_object = new SlotObject(object->label_,
913 object->key_identifier_);
914 slot_object->Initialize();
915 slot_object->SetSlotHandler(pkcs11->slot_handler());
916 slot_object->obj()->Set(v8::String::NewSymbol("label"),
917 v8::String::New(object->label_.c_str()),
918 v8::ReadOnly);
919 slot_object->obj()->Set(v8::String::NewSymbol("keyIdentifier"),
920 v8::String::New(object->key_identifier_.c_str()));
921
922 // Build a certificate
923 Certificate* certificate = new Certificate();
924 certificate->Initialize();
925 certificate->obj()->Set(v8::String::NewSymbol("subject"),
926 v8::String::New(object->subject_.c_str()));
927
928 // Add the certificate to the slot object
929 slot_object->obj()->Set(v8::String::NewSymbol("certificate"),
930 certificate->obj());
931
932 // Add the object to pkcs11.slots ("slots[label] = obj")
933 pkcs11->AddJSSlotObject(slot_object);
934 }
935 return true;
781 } 936 }
782 937
783 // Returns false if the key is longer than a reasonable maximum length. 938 // Returns false if the key is longer than a reasonable maximum length.
784 virtual bool SetKeyIdentifier(const std::string& label, 939 virtual bool SetKeyIdentifier(const std::string& label,
785 const std::string& keyid) { 940 const std::string& keyid) {
786 const std::size_t MAX_KEY_LENGTH = 16; 941 const std::size_t MAX_KEY_LENGTH = 16;
787 if (keyid.length() > MAX_KEY_LENGTH) 942 if (keyid.length() > MAX_KEY_LENGTH)
788 return false; 943 return false;
789 return Pkcs11SlotHandlerInMemory::SetKeyIdentifier(label, keyid); 944 return Pkcs11SlotHandlerInMemory::SetKeyIdentifier(label, keyid);
790 } 945 }
(...skipping 325 matching lines...) Expand 10 before | Expand all | Expand 10 after
1116 rv = C_Login(handle, CKU_USER, 1271 rv = C_Login(handle, CKU_USER,
1117 pin_ptr, user_pin_.length()); 1272 pin_ptr, user_pin_.length());
1118 if (rv != CKR_OK) { 1273 if (rv != CKR_OK) {
1119 LOG(ERROR) << "C_Login failed, error: " << rv 1274 LOG(ERROR) << "C_Login failed, error: " << rv
1120 << " label: " << label << " pin: " << user_pin_; 1275 << " label: " << label << " pin: " << user_pin_;
1121 } 1276 }
1122 1277
1123 return handle; 1278 return handle;
1124 } 1279 }
1125 1280
1281 std::string TemplateToString(const CK_ATTRIBUTE& attr) {
1282 const char* value = static_cast<const char*>(attr.pValue);
1283 return std::string(value, attr.ulValueLen);
1284 }
1285
1126 // openssl crypto library interface 1286 // openssl crypto library interface
1127 1287
1128 struct RsaKeyInfo { 1288 struct RsaKeyInfo {
1129 unsigned char *modulus; 1289 unsigned char *modulus;
1130 int modulus_len; 1290 int modulus_len;
1131 unsigned char *public_exp; 1291 unsigned char *public_exp;
1132 int public_exp_len; 1292 int public_exp_len;
1133 unsigned char *private_exp; 1293 unsigned char *private_exp;
1134 int private_exp_len; 1294 int private_exp_len;
1135 unsigned char *prime_1; 1295 unsigned char *prime_1;
(...skipping 81 matching lines...) Expand 10 before | Expand all | Expand 10 after
1217 if (bytes.size() > max_length) { 1377 if (bytes.size() > max_length) {
1218 LOG(ERROR) << "Too many characters in key: " << keyid; 1378 LOG(ERROR) << "Too many characters in key: " << keyid;
1219 *idstrlenp = 0; 1379 *idstrlenp = 0;
1220 return false; 1380 return false;
1221 } 1381 }
1222 memcpy(idstrp, &bytes.front(), bytes.size()); 1382 memcpy(idstrp, &bytes.front(), bytes.size());
1223 *idstrlenp = bytes.size(); 1383 *idstrlenp = bytes.size();
1224 return true; 1384 return true;
1225 } 1385 }
1226 1386
1387 // Inverse of GetKeyIdStr
1388 std::string GetKeyFromId(CK_BYTE* idstrp, CK_ULONG idstrlen) {
1389 chromeos::Blob bytes = chromeos::Blob(idstrp, idstrp+idstrlen);
1390 return chromeos::AsciiEncode(bytes);
1391 }
1392
1227 std::string user_pin_; 1393 std::string user_pin_;
1228 CK_ULONG slot_index_; 1394 CK_ULONG slot_index_;
1229 CK_SLOT_ID slot_id_; 1395 CK_SLOT_ID slot_id_;
1230 1396
1231 DISALLOW_COPY_AND_ASSIGN(Pkcs11SlotHandlerOpenCryptoki); 1397 DISALLOW_COPY_AND_ASSIGN(Pkcs11SlotHandlerOpenCryptoki);
1232 }; 1398 };
1233 1399
1234 // In "GLaptop mode" we generate the key pair using openssl, and call 1400 // In "GLaptop mode" we generate the key pair using openssl, and call
1235 // AddPrivateKey() instead, so GenerateKeyPair() needs to be a no-op. 1401 // AddPrivateKey() instead, so GenerateKeyPair() needs to be a no-op.
1236 class Pkcs11SlotHandlerGLaptop : public Pkcs11SlotHandlerOpenCryptoki { 1402 class Pkcs11SlotHandlerGLaptop : public Pkcs11SlotHandlerOpenCryptoki {
(...skipping 42 matching lines...) Expand 10 before | Expand all | Expand 10 after
1279 1445
1280 private: 1446 private:
1281 std::string request_; 1447 std::string request_;
1282 1448
1283 static Pkcs11CertificateHandler* certificate_handler_; 1449 static Pkcs11CertificateHandler* certificate_handler_;
1284 1450
1285 DISALLOW_COPY_AND_ASSIGN(CSR); 1451 DISALLOW_COPY_AND_ASSIGN(CSR);
1286 }; 1452 };
1287 1453
1288 // static 1454 // static
1289 Pkcs11CertificateHandler* CSR::certificate_handler_; 1455 Pkcs11CertificateHandler* CSR::certificate_handler_ = NULL;
1290 1456
1291 // Base64 encoded version of the CSR 1457 // Base64 encoded version of the CSR
1292 static v8::Handle<v8::Value> dispatch_CSRToString(const v8::Arguments& args) { 1458 static v8::Handle<v8::Value> dispatch_CSRToString(const v8::Arguments& args) {
1293 CSR* csr = CSR::Unwrap(args.This()); 1459 CSR* csr = CSR::Unwrap(args.This());
1294 if (csr == NULL) { 1460 if (csr == NULL) {
1295 utils::ThrowV8Exception("Method called on incorrect object type."); 1461 utils::ThrowV8Exception("Method called on incorrect object type.");
1296 return v8::False(); 1462 return v8::False();
1297 } 1463 }
1298 v8::Local<v8::String> res = v8::String::New(csr->request().c_str()); 1464 v8::Local<v8::String> res = v8::String::New(csr->request().c_str());
1299 return res; 1465 return res;
(...skipping 30 matching lines...) Expand all
1330 // Build the CSR request 1496 // Build the CSR request
1331 if (!certificate_handler()->BuildCSR(slot_object->label(), 1497 if (!certificate_handler()->BuildCSR(slot_object->label(),
1332 utils::ValueAsUtf8String(subject), 1498 utils::ValueAsUtf8String(subject),
1333 &request_)) { 1499 &request_)) {
1334 utils::ThrowV8Exception("Error building CSR."); 1500 utils::ThrowV8Exception("Error building CSR.");
1335 return; 1501 return;
1336 } 1502 }
1337 } 1503 }
1338 1504
1339 1505
1340 // Class Certificate 1506 // Class Certificate Implementation
1341 // Certificate JavaScript interface wrapper around Pkcs11CertificateHandler.
1342 class Certificate : public JSObjectWrapper<Certificate> {
1343 public:
1344 Certificate() {}
1345 virtual ~Certificate() {}
1346
1347 // JSObjectWrapper Interface
1348 virtual void ParseConstructorArgs(
1349 v8::Handle<v8::Object> obj, const v8::Arguments& args);
1350 static void SetTemplateBindings(
1351 v8::Handle<v8::ObjectTemplate> template_object);
1352 static const char* GetClassName() { return "Certificate"; }
1353
1354 // Accessors
1355 const chromeos::Blob& certificate() const { return certificate_; }
1356 const std::string& subject() const { return subject_; }
1357
1358 // Certificate handler management
1359 static void InitCertificateHandler(Pkcs11CertificateHandler* handler) {
1360 certificate_handler_ = handler;
1361 }
1362 static Pkcs11CertificateHandler* certificate_handler() {
1363 return certificate_handler_;
1364 }
1365
1366 private:
1367 // The certificate may contain binary data, so store it as an array of bytes
1368 // instead of a string.
1369 chromeos::Blob certificate_;
1370 std::string subject_;
1371 static Pkcs11CertificateHandler* certificate_handler_;
1372
1373 DISALLOW_COPY_AND_ASSIGN(Certificate);
1374 };
1375 1507
1376 // static 1508 // static
1377 Pkcs11CertificateHandler* Certificate::certificate_handler_; 1509 Pkcs11CertificateHandler* Certificate::certificate_handler_ = NULL;
1378 1510
1379 // Returns the contents of the Certificate as a string. 1511 // Returns the contents of the Certificate as a string.
1380 // Note: if this is binary and not Base64, results may be unexpected. 1512 // Note: if this is binary and not Base64, results may be unexpected.
1381 // (i.e. don't call this unles you expect the contents to be a string) 1513 // (i.e. don't call this unles you expect the contents to be a string)
1382 static v8::Handle<v8::Value> dispatch_CertificateToString( 1514 static v8::Handle<v8::Value> dispatch_CertificateToString(
1383 const v8::Arguments& args) { 1515 const v8::Arguments& args) {
1384 Certificate* cert = Certificate::Unwrap(args.This()); 1516 Certificate* cert = Certificate::Unwrap(args.This());
1385 const chromeos::Blob& certdata = cert->certificate(); 1517 const chromeos::Blob& certdata = cert->certificate();
1386 const char* certstrptr = reinterpret_cast<const char*>(&(certdata.front())); 1518 const char* certstrptr = reinterpret_cast<const char*>(&(certdata.front()));
1387 v8::Local<v8::String> res = v8::String::New(certstrptr); 1519 v8::Local<v8::String> res = v8::String::New(certstrptr);
(...skipping 19 matching lines...) Expand all
1407 v8::Handle<v8::Value> content = args[0]; 1539 v8::Handle<v8::Value> content = args[0];
1408 1540
1409 // Generate the Certificate data 1541 // Generate the Certificate data
1410 bool res = certificate_handler()->BuildCertificate( 1542 bool res = certificate_handler()->BuildCertificate(
1411 utils::ValueAsUtf8String(content), &certificate_, &subject_); 1543 utils::ValueAsUtf8String(content), &certificate_, &subject_);
1412 if (!res) { 1544 if (!res) {
1413 utils::ThrowV8Exception("Unable to build certificate."); 1545 utils::ThrowV8Exception("Unable to build certificate.");
1414 return; 1546 return;
1415 } 1547 }
1416 1548
1417 // Set the 'content' property to the input content
1418 obj->Set(v8::String::NewSymbol("content"),
1419 content->ToString());
1420 // Set the 'subject' property to the certificate subject 1549 // Set the 'subject' property to the certificate subject
1421 obj->Set(v8::String::NewSymbol("subject"), 1550 obj->Set(v8::String::NewSymbol("subject"),
1422 v8::String::New(subject_.c_str())); 1551 v8::String::New(subject_.c_str()));
1423 } 1552 }
1424 1553
1425 1554
1426 // Class SlotObject Implementation 1555 // Class SlotObject Implementation
1427 1556
1428 bool SlotObject::Initialize() { 1557 bool SlotObject::Initialize() {
1429 // Bind "CSR" here so we can associate this with it 1558 // Bind "CSR" here so we can associate this with it
(...skipping 16 matching lines...) Expand all
1446 utils::ThrowV8Exception("Method called on incorrect object type."); 1575 utils::ThrowV8Exception("Method called on incorrect object type.");
1447 return v8::False(); 1576 return v8::False();
1448 } 1577 }
1449 if (args.Length() < 1) { 1578 if (args.Length() < 1) {
1450 utils::ThrowV8Exception("Not enough parameters."); 1579 utils::ThrowV8Exception("Not enough parameters.");
1451 return v8::False(); 1580 return v8::False();
1452 } 1581 }
1453 1582
1454 // Argument 0 is the key identifier 1583 // Argument 0 is the key identifier
1455 v8::Handle<v8::String> v8keyid = args[0]->ToString(); 1584 v8::Handle<v8::String> v8keyid = args[0]->ToString();
1456 slot->obj()->Set(v8::String::NewSymbol("keyIdentifier"), v8keyid);
1457 std::string keyid = std::string(*v8::String::Utf8Value(v8keyid)); 1585 std::string keyid = std::string(*v8::String::Utf8Value(v8keyid));
1458 bool res = slot->SetKeyIdentifier(keyid); 1586 bool res = slot->SetKeyIdentifier(keyid);
1459 if (!res) { 1587 if (!res) {
1460 utils::ThrowV8Exception(std::string("Invalid key id: ") + keyid); 1588 utils::ThrowV8Exception(std::string("Invalid key id: ") + keyid);
1461 return v8::False(); 1589 return v8::False();
1462 } 1590 }
1591 // Set the JS keyIdentifier property
1592 slot->obj()->Set(v8::String::NewSymbol("keyIdentifier"), v8keyid);
1463 1593
1464 // Argumnet 1 is the passphrase (optional) 1594 // Argumnet 1 is the passphrase (optional)
1465 std::string passphrase; // defaults to empty 1595 std::string passphrase; // defaults to empty
1466 if (!args[1]->IsUndefined()) { 1596 if (!args[1]->IsUndefined()) {
1467 passphrase = utils::ValueAsUtf8String(args[1]); 1597 passphrase = utils::ValueAsUtf8String(args[1]);
1468 slot->SetPassphrase(passphrase); 1598 slot->SetPassphrase(passphrase);
1469 } 1599 }
1470 1600
1471 // Access the slot handler and generate the public/private key pair 1601 // Access the slot handler and generate the public/private key pair
1472 res = slot->slot_handler()->GenerateKeyPair(slot->label(), 1602 res = slot->slot_handler()->GenerateKeyPair(slot->label(),
1473 slot->passphrase()); 1603 slot->passphrase());
1474 if (!res) { 1604 if (!res) {
1475 LOG(ERROR) << "Unable to build key pair with id: " << keyid; 1605 LOG(ERROR) << "Unable to build key pair with id: " << keyid;
1476 return v8::False(); 1606 return v8::False();
1477 } 1607 }
1478 1608
1479 // Set the JS publicKey property
1480 v8::Handle<v8::String> v8_public_key =
1481 v8::String::New(slot->GetPublicKey().c_str());
1482 slot->obj()->Set(v8::String::NewSymbol("publicKey"), v8_public_key);
1483
1484 return v8::True(); 1609 return v8::True();
1485 } 1610 }
1486 1611
1487 static v8::Handle<v8::Value> dispatch_addCertificate( 1612 static v8::Handle<v8::Value> dispatch_addCertificate(
1488 const v8::Arguments& args) { 1613 const v8::Arguments& args) {
1489 // Get the arguments. 1614 // Get the arguments.
1490 SlotObject* slot = SlotObject::Unwrap(args.This()); 1615 SlotObject* slot = SlotObject::Unwrap(args.This());
1491 if (slot == NULL) { 1616 if (slot == NULL) {
1492 utils::ThrowV8Exception("Method called on incorrect object type."); 1617 utils::ThrowV8Exception("Method called on incorrect object type.");
1493 return v8::False(); 1618 return v8::False();
(...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after
1550 obj->Set(v8::String::NewSymbol("label"), v8label, v8::ReadOnly); 1675 obj->Set(v8::String::NewSymbol("label"), v8label, v8::ReadOnly);
1551 label_ = std::string(*v8::String::Utf8Value(v8label)); 1676 label_ = std::string(*v8::String::Utf8Value(v8label));
1552 1677
1553 // Build the SlotObject 1678 // Build the SlotObject
1554 bool res = pkcs11->slot_handler()->BuildSlotObject(label_); 1679 bool res = pkcs11->slot_handler()->BuildSlotObject(label_);
1555 if (!res) { 1680 if (!res) {
1556 LOG(ERROR) << "Unable to build SlotObject with label: " << label_; 1681 LOG(ERROR) << "Unable to build SlotObject with label: " << label_;
1557 return; 1682 return;
1558 } 1683 }
1559 1684
1560 // Add a this to pkcs11.slots ("slots.{label} = {cert}") 1685 // Add this to pkcs11.slots ("slots[label] = obj")
1561 v8::Local<v8::Value> slotsvalue = 1686 pkcs11->AddJSSlotObject(this);
1562 pkcs11->obj()->Get(v8::String::NewSymbol("slots"));
1563 if (slotsvalue.IsEmpty() || !slotsvalue->IsObject()) {
1564 LOG(ERROR) << "'slots' is not an object in pkcs11";
1565 return;
1566 }
1567 v8::Local<v8::Object> slots = v8::Local<v8::Object>::Cast(slotsvalue);
1568 slots->Set(v8label->ToString(), obj);
1569 } 1687 }
1570 1688
1571 1689
1572 // Class Pkcs11 1690 // Class Pkcs11
1573 Pkcs11::Pkcs11(Pkcs11CertificateHandler* cert_handler, 1691 Pkcs11::Pkcs11(Pkcs11CertificateHandler* cert_handler,
1574 Pkcs11SlotHandler* slot_handler) 1692 Pkcs11SlotHandler* slot_handler)
1575 : JSObjectWrapper<Pkcs11>(), 1693 : JSObjectWrapper<Pkcs11>(),
1576 certificate_handler_(cert_handler), 1694 certificate_handler_(cert_handler),
1577 slot_handler_(slot_handler) { 1695 slot_handler_(slot_handler) {
1578 } 1696 }
1579 1697
1580 Pkcs11::~Pkcs11() { 1698 Pkcs11::~Pkcs11() {
1581 CleanupTemplate(); // We only have one Pkcs11 instance. 1699 CleanupTemplate(); // We only have one Pkcs11 instance.
1582 } 1700 }
1583 1701
1702 // Called any time slot_handler_ or certificate_handler_ gets set.
1703 void Pkcs11::SetupHandlers() {
1704 // The certificate handler may need access to the slot handler
1705 certificate_handler()->SetSlotHandler(slot_handler());
1706
1707 // Set up the CSR and Certificate sub-classes with the certificate handler.
1708 CSR::InitCertificateHandler(certificate_handler());
1709 Certificate::InitCertificateHandler(certificate_handler());
1710 }
1711
1712 // This always gets called first by InitializeXXX()
1713 // so that obj() is available for other initialization
1714 // functions (e.g. ReadObjectsFromSlot())
1584 bool Pkcs11::Initialize() { 1715 bool Pkcs11::Initialize() {
1585 if (slot_handler_.get() == NULL) { 1716 if (slot_handler_.get() == NULL) {
1586 // Default slot handler 1717 // Default slot handler
1587 slot_handler_.reset(new Pkcs11SlotHandlerInMemory()); 1718 slot_handler_.reset(new Pkcs11SlotHandlerInMemory());
1588 slot_handler_->Initialize(); 1719 slot_handler_->Initialize();
1589 } 1720 }
1590 if (certificate_handler_.get() == NULL) { 1721 if (certificate_handler_.get() == NULL) {
1591 // Default certificate handler. 1722 // Default certificate handler.
1592 certificate_handler_.reset(new Pkcs11CertificateHandlerLocalFile("", "")); 1723 certificate_handler_.reset(new Pkcs11CertificateHandlerLocalFile("", ""));
1593 certificate_handler_->Initialize(); 1724 certificate_handler_->Initialize();
1594 } 1725 }
1595 // The certificate handler may need access to the slot handler
1596 certificate_handler()->SetSlotHandler(slot_handler());
1597 1726
1598 // Set up the CSR and Certificate sub-classes with the certificate handler. 1727 SetupHandlers();
1599 CSR::InitCertificateHandler(certificate_handler());
1600 Certificate::InitCertificateHandler(certificate_handler());
1601 1728
1602 // Initialize the pkcs11 template specially 1729 // Initialize the pkcs11 template specially
1603 v8::Handle<v8::FunctionTemplate> t = GetTemplate(); 1730 v8::Handle<v8::FunctionTemplate> t = GetTemplate();
1604 v8::Handle<v8::ObjectTemplate> t_obj = t->InstanceTemplate(); 1731 v8::Handle<v8::ObjectTemplate> t_obj = t->InstanceTemplate();
1605 t_obj->Set(v8::String::NewSymbol("SlotObject"), 1732 t_obj->Set(v8::String::NewSymbol("SlotObject"),
1606 v8::FunctionTemplate::New(SlotObject::Construct, 1733 v8::FunctionTemplate::New(SlotObject::Construct,
1607 v8::External::Wrap(this)), 1734 v8::External::Wrap(this)),
1608 v8::ReadOnly); 1735 v8::ReadOnly);
1609 1736
1610 // Build and initialize the V8 object. 1737 // Build and initialize the V8 object.
1611 return JSObjectWrapper<Pkcs11>::Initialize(); 1738 return JSObjectWrapper<Pkcs11>::Initialize();
1612 } 1739 }
1613 1740
1614 bool Pkcs11::InitializeOpenCryptoki(const std::string& test_cert, 1741 bool Pkcs11::InitializeOpenCryptoki(const std::string& test_cert,
1615 const std::string& engine) { 1742 const std::string& engine) {
1616 LOG(INFO) << "Initializing pkcs11 with opencryptoki and engine:" << engine; 1743 LOG(INFO) << "Initializing pkcs11 with opencryptoki and engine:" << engine;
1617 1744
1618 slot_handler_.reset(new Pkcs11SlotHandlerOpenCryptoki()); 1745 bool res = Initialize();
1619 slot_handler_->Initialize(); 1746
1747 Pkcs11SlotHandlerOpenCryptoki* slot_handler =
1748 new Pkcs11SlotHandlerOpenCryptoki();
1749 slot_handler_.reset(slot_handler);
1750 slot_handler->Initialize();
1751 slot_handler->ReadObjectsFromSlot(this);
1620 1752
1621 Pkcs11CertificateHandlerOpenSslPkcs11Engine* cert_handler = 1753 Pkcs11CertificateHandlerOpenSslPkcs11Engine* cert_handler =
1622 new Pkcs11CertificateHandlerOpenSslPkcs11Engine(); 1754 new Pkcs11CertificateHandlerOpenSslPkcs11Engine();
1623 cert_handler->Initialize(); 1755 cert_handler->Initialize();
1624 cert_handler->SetTestCertificate(test_cert); 1756 cert_handler->SetTestCertificate(test_cert);
1625 cert_handler->SetEngineConfigFile(engine); 1757 cert_handler->SetEngineConfigFile(engine);
1626 cert_handler->SetOutputDER(); 1758 cert_handler->SetOutputDER();
1627 certificate_handler_.reset(cert_handler); 1759 certificate_handler_.reset(cert_handler);
1628 1760
1629 return Initialize(); 1761 SetupHandlers();
1762
1763 return res;
1630 } 1764 }
1631 1765
1632 bool Pkcs11::InitializeGLaptop(const std::string& test_cert) { 1766 bool Pkcs11::InitializeGLaptop(const std::string& test_cert) {
1633 LOG(INFO) << "Initializing pkcs11 with opencryptoki, no ssl engine."; 1767 LOG(INFO) << "Initializing pkcs11 with opencryptoki, no ssl engine.";
1634 1768
1635 slot_handler_.reset(new Pkcs11SlotHandlerGLaptop()); 1769 bool res = Initialize();
1636 slot_handler_->Initialize(); 1770
1771 Pkcs11SlotHandlerGLaptop* slot_handler =
1772 new Pkcs11SlotHandlerGLaptop();
1773 slot_handler_.reset(slot_handler);
1774 slot_handler->Initialize();
1775 slot_handler->ReadObjectsFromSlot(this);
1637 1776
1638 Pkcs11CertificateHandlerOpenSsl* cert_handler = 1777 Pkcs11CertificateHandlerOpenSsl* cert_handler =
1639 new Pkcs11CertificateHandlerOpenSsl(); 1778 new Pkcs11CertificateHandlerOpenSsl();
1640 cert_handler->Initialize(); 1779 cert_handler->Initialize();
1641 cert_handler->SetTestCertificate(test_cert); 1780 cert_handler->SetTestCertificate(test_cert);
1642 cert_handler->SetOutputDER(); 1781 cert_handler->SetOutputDER();
1643 certificate_handler_.reset(cert_handler); 1782 certificate_handler_.reset(cert_handler);
1644 1783
1645 return Initialize(); 1784 SetupHandlers();
1785
1786 return res;
1646 } 1787 }
1647 1788
1648 bool Pkcs11::InitializeOpenSSL(const std::string& test_cert) { 1789 bool Pkcs11::InitializeOpenSSL(const std::string& test_cert) {
1649 LOG(INFO) << "Initializing pkcs11 with openssl."; 1790 LOG(INFO) << "Initializing pkcs11 with openssl.";
1650 1791
1792 bool res = Initialize();
1793
1651 slot_handler_.reset(new Pkcs11SlotHandlerInMemory()); 1794 slot_handler_.reset(new Pkcs11SlotHandlerInMemory());
1652 slot_handler_->Initialize(); 1795 slot_handler_->Initialize();
1653 1796
1654 Pkcs11CertificateHandlerOpenSsl* cert_handler = 1797 Pkcs11CertificateHandlerOpenSsl* cert_handler =
1655 new Pkcs11CertificateHandlerOpenSsl(); 1798 new Pkcs11CertificateHandlerOpenSsl();
1656 cert_handler->Initialize(); 1799 cert_handler->Initialize();
1657 cert_handler->SetTestCertificate(test_cert); 1800 cert_handler->SetTestCertificate(test_cert);
1658 certificate_handler_.reset(cert_handler); 1801 certificate_handler_.reset(cert_handler);
1659 1802
1660 return Initialize(); 1803 SetupHandlers();
1804
1805 return res;
1661 } 1806 }
1662 1807
1663 bool Pkcs11::InitializeLocalFiles(const std::string& csr, 1808 bool Pkcs11::InitializeLocalFiles(const std::string& csr,
1664 const std::string& cert) { 1809 const std::string& cert) {
1810 bool res = Initialize();
1811
1665 slot_handler_.reset(new Pkcs11SlotHandlerInMemory()); 1812 slot_handler_.reset(new Pkcs11SlotHandlerInMemory());
1666 slot_handler_->Initialize(); 1813 slot_handler_->Initialize();
1667 1814
1668 certificate_handler_.reset( 1815 certificate_handler_.reset(
1669 new Pkcs11CertificateHandlerLocalFile(csr, cert)); 1816 new Pkcs11CertificateHandlerLocalFile(csr, cert));
1670 certificate_handler_->Initialize(); 1817 certificate_handler_->Initialize();
1671 1818
1672 return Initialize(); 1819 SetupHandlers();
1820
1821 return res;
1822 }
1823
1824 // pkcs11[slot_object->label()] = slot_object->obj()
1825 bool Pkcs11::AddJSSlotObject(const SlotObject* slot_object) {
1826 v8::Local<v8::Value> slotsvalue = obj()->Get(v8::String::NewSymbol("slots"));
1827 if (slotsvalue.IsEmpty() || !slotsvalue->IsObject()) {
1828 LOG(ERROR) << "'slots' is not an object in pkcs11";
1829 return false;
1830 }
1831 v8::Local<v8::Object> slots = v8::Local<v8::Object>::Cast(slotsvalue);
1832 v8::Local<v8::String> v8label = v8::String::New(slot_object->label().c_str());
1833 slots->Set(v8label, slot_object->obj());
1834 return true;
1673 } 1835 }
1674 1836
1675 static v8::Handle<v8::Value> dispatch_setUserPin( 1837 static v8::Handle<v8::Value> dispatch_setUserPin(
1676 const v8::Arguments& args) { 1838 const v8::Arguments& args) {
1677 // Get the arguments. 1839 // Get the arguments.
1678 Pkcs11* pkcs11 = Pkcs11::Unwrap(args.This()); 1840 Pkcs11* pkcs11 = Pkcs11::Unwrap(args.This());
1679 if (pkcs11 == NULL) { 1841 if (pkcs11 == NULL) {
1680 utils::ThrowV8Exception("Method called on incorrect object type."); 1842 utils::ThrowV8Exception("Method called on incorrect object type.");
1681 return v8::False(); 1843 return v8::False();
1682 } 1844 }
(...skipping 53 matching lines...) Expand 10 before | Expand all | Expand 10 after
1736 v8::ReadOnly); 1898 v8::ReadOnly);
1737 template_object->Set(v8::String::NewSymbol("clear"), 1899 template_object->Set(v8::String::NewSymbol("clear"),
1738 v8::FunctionTemplate::New(dispatch_clearSlotObject), 1900 v8::FunctionTemplate::New(dispatch_clearSlotObject),
1739 v8::ReadOnly); 1901 v8::ReadOnly);
1740 template_object->Set(v8::String::NewSymbol("slots"), 1902 template_object->Set(v8::String::NewSymbol("slots"),
1741 v8::Object::New(), 1903 v8::Object::New(),
1742 v8::ReadOnly); 1904 v8::ReadOnly);
1743 } 1905 }
1744 1906
1745 } // namespace entd 1907 } // namespace entd
OLDNEW
« no previous file with comments | « pkcs11.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698