blob: b68c3fba412e17a803cdaba19dc007aad6e1f3d9 [file] [log] [blame]
Michael Ershov1c50ac952020-12-02 21:01:171// Copyright 2020 The Chromium Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5#include "crypto/chaps_support.h"
6
7#include <dlfcn.h>
8#include <secmodt.h>
9
10#include "base/logging.h"
11#include "base/threading/scoped_blocking_call.h"
12#include "nss_util_internal.h"
13
14namespace crypto {
15
16namespace {
17
18// Constants for loading the Chrome OS TPM-backed PKCS #11 library.
19const char kChapsModuleName[] = "Chaps";
20const char kChapsPath[] = "libchaps.so";
21
22class ScopedChapsLoadFixup {
23 public:
24 ScopedChapsLoadFixup();
25 ~ScopedChapsLoadFixup();
26
27 private:
28#if defined(COMPONENT_BUILD)
29 void* chaps_handle_;
30#endif
31};
32
33#if defined(COMPONENT_BUILD)
34
35ScopedChapsLoadFixup::ScopedChapsLoadFixup() {
36 // HACK: libchaps links the system protobuf and there are symbol conflicts
37 // with the bundled copy. Load chaps with RTLD_DEEPBIND to workaround.
38 chaps_handle_ = dlopen(kChapsPath, RTLD_LOCAL | RTLD_NOW | RTLD_DEEPBIND);
39}
40
41ScopedChapsLoadFixup::~ScopedChapsLoadFixup() {
42 // LoadNSSModule() will have taken a 2nd reference.
43 if (chaps_handle_)
44 dlclose(chaps_handle_);
45}
46
47#else
48
49ScopedChapsLoadFixup::ScopedChapsLoadFixup() = default;
50ScopedChapsLoadFixup::~ScopedChapsLoadFixup() = default;
51
52#endif // defined(COMPONENT_BUILD)
53
54} // namespace
55
56SECMODModule* LoadChaps() {
57 // NSS functions may reenter //net via extension hooks. If the reentered
58 // code needs to synchronously wait for a task to run but the thread pool in
59 // which that task must run doesn't have enough threads to schedule it, a
60 // deadlock occurs. To prevent that, the base::ScopedBlockingCall below
61 // increments the thread pool capacity for the duration of the TPM
62 // initialization.
63 base::ScopedBlockingCall scoped_blocking_call(FROM_HERE,
64 base::BlockingType::WILL_BLOCK);
65
66 ScopedChapsLoadFixup chaps_loader;
67
68 DVLOG(3) << "Loading chaps...";
69 return LoadNSSModule(
70 kChapsModuleName, kChapsPath,
71 // For more details on these parameters, see:
72 // https://developer.mozilla.org/en/PKCS11_Module_Specs
73 // slotFlags=[PublicCerts] -- Certificates and public keys can be
74 // read from this slot without requiring a call to C_Login.
75 // askpw=only -- Only authenticate to the token when necessary.
76 "NSS=\"slotParams=(0={slotFlags=[PublicCerts] askpw=only})\"");
77}
78
79bool IsSlotProvidedByChaps(PK11SlotInfo* slot) {
80 if (!slot)
81 return false;
82
83 SECMODModule* pk11_module = PK11_GetModule(slot);
84 return pk11_module && base::StringPiece(pk11_module->commonName) ==
85 base::StringPiece(kChapsModuleName);
86}
87
88} // namespace crypto