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

Side by Side Diff: components/os_crypt/os_crypt_util_linux_unittest.cc

Issue 1973483002: OSCrypt for POSIX uses libsecret to store a randomised encryption key. (Closed) Base URL: https://chromium.googlesource.com/chromium/src.git@master
Patch Set: Fixed lsan failure Created 4 years, 7 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
OLDNEW
(Empty)
1 // Copyright 2016 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 <dlfcn.h>
Lei Zhang 2016/05/18 22:38:16 Is this needed?
cfroussios 2016/05/19 21:18:19 Done.
6 #include <memory>
7 #include <string>
8 #include <utility>
9
10 #include "base/lazy_instance.h"
Lei Zhang 2016/05/18 22:38:16 Not needed?
cfroussios 2016/05/19 21:18:19 Done.
11 #include "base/logging.h"
12 #include "base/macros.h"
13 #include "components/os_crypt/key_storage_libsecret.h"
14 #include "components/os_crypt/key_storage_linux.h"
15 #include "components/os_crypt/libsecret_util_linux.h"
16 #include "components/os_crypt/os_crypt.h"
17 #include "testing/gtest/include/gtest/gtest.h"
18
19 namespace {
20
21 struct MockSecretValue {
Lei Zhang 2016/05/18 22:38:16 Structs with a single value seem unnecessary.
cfroussios 2016/05/19 21:18:19 Done. It was struct to keep some symmetry between
22 public:
23 std::unique_ptr<std::string> password;
Lei Zhang 2016/05/18 22:38:16 Can this just be std::string password?
cfroussios 2016/05/19 21:18:19 Done.
24
25 explicit MockSecretValue(const gchar* password);
26
27 ~MockSecretValue();
28 };
29
30 // Replaces some of LibsecretLoader's methods with mocked ones.
31 class MockLibsecretLoader : public LibsecretLoader {
32 public:
33 // Sets up the minimum mock implementation necessary for |Libsecret| to work.
34 // Also resets the state to mock a clean database.
35 static bool ResetForOSCrypt();
36
37 // Shorthand for setting OSCrypt's password in the libsecret mock to a
38 // specific value
39 static void SetOSCryptPassword(const char*);
40
41 // Release memory. Does not restore functions
42 static void TearDown();
43
44 static MockSecretValue* stored_password_mock_ptr_;
45
46 private:
47 // These methods are used to redirect calls through LibsecretLoader
48 static const gchar* mock_secret_value_get_text(MockSecretValue* value);
49
50 static gboolean mock_secret_password_store_sync(const SecretSchema* schema,
51 const gchar* collection,
52 const gchar* label,
53 const gchar* password,
54 GCancellable* cancellable,
55 GError** error,
56 ...);
57
58 static MockSecretValue* mock_secret_service_lookup_sync(
59 SecretService* service,
60 const SecretSchema* schema,
61 GHashTable* attributes,
62 GCancellable* cancellable,
63 GError** error);
64
65 static void mock_secret_value_unref(gpointer value);
66
67 static GList* mock_secret_service_search_sync(SecretService* service,
68 const SecretSchema* schema,
69 GHashTable* attributes,
70 SecretSearchFlags flags,
71 GCancellable* cancellable,
72 GError** error);
73 };
74
75 MockSecretValue* MockLibsecretLoader::stored_password_mock_ptr_ = nullptr;
76
77 MockSecretValue::MockSecretValue(const gchar* password)
78 : password(new std::string(password)) {}
79
80 MockSecretValue::~MockSecretValue() = default;
81
82 const gchar* MockLibsecretLoader::mock_secret_value_get_text(
83 MockSecretValue* value) {
84 return value->password->c_str();
85 }
86
87 gboolean MockLibsecretLoader::mock_secret_password_store_sync(
88 const SecretSchema* schema,
89 const gchar* collection,
90 const gchar* label,
91 const gchar* password,
92 GCancellable* cancellable,
93 GError** error,
94 ...) {
95 if (stored_password_mock_ptr_ != nullptr)
96 delete stored_password_mock_ptr_;
Lei Zhang 2016/05/18 22:38:16 There's no need to check a value against nullptr b
cfroussios 2016/05/19 21:18:19 Done.
97 stored_password_mock_ptr_ = new MockSecretValue(password);
98 return true;
99 }
100
101 MockSecretValue* MockLibsecretLoader::mock_secret_service_lookup_sync(
102 SecretService* service,
103 const SecretSchema* schema,
104 GHashTable* attributes,
105 GCancellable* cancellable,
106 GError** error) {
107 return stored_password_mock_ptr_;
108 }
109
110 void MockLibsecretLoader::mock_secret_value_unref(gpointer value) {}
111
112 GList* MockLibsecretLoader::mock_secret_service_search_sync(
113 SecretService* service,
114 const SecretSchema* schema,
115 GHashTable* attributes,
116 SecretSearchFlags flags,
117 GCancellable* cancellable,
118 GError** error) {
119 *error = nullptr;
120 return nullptr;
121 }
122
123 // static
124 bool MockLibsecretLoader::ResetForOSCrypt() {
125 // 4 methods used by Libsecret.GetPassword();
126 secret_password_store_sync =
127 &MockLibsecretLoader::mock_secret_password_store_sync;
128 secret_value_get_text = (decltype(&::secret_value_get_text)) &
129 MockLibsecretLoader::mock_secret_value_get_text;
130 secret_value_unref = &MockLibsecretLoader::mock_secret_value_unref;
131 secret_service_lookup_sync =
132 (decltype(&::secret_service_lookup_sync)) &
133 MockLibsecretLoader::mock_secret_service_lookup_sync;
134 // 1 method used by LibsecretLoader::EnsureLibsecretLoaded
135 secret_service_search_sync =
136 &MockLibsecretLoader::mock_secret_service_search_sync;
137
138 if (stored_password_mock_ptr_)
139 delete stored_password_mock_ptr_;
140 stored_password_mock_ptr_ = nullptr;
141 libsecret_loaded_ = true;
142
143 return true;
144 }
145
146 void MockLibsecretLoader::SetOSCryptPassword(const char* value) {
147 if (stored_password_mock_ptr_ != nullptr)
148 delete stored_password_mock_ptr_;
149 stored_password_mock_ptr_ = new MockSecretValue(value);
150 }
151
152 void MockLibsecretLoader::TearDown() {
153 if (stored_password_mock_ptr_)
154 delete stored_password_mock_ptr_;
155 stored_password_mock_ptr_ = nullptr;
156 }
157
158 class OSCryptLinuxTest : public testing::Test {
159 public:
160 OSCryptLinuxTest() = default;
161 ~OSCryptLinuxTest() override = default;
162
163 void SetUp() override { key_storage_ = OSCrypt::UseMockKeyStorage(true); }
164
165 void TearDown() override { OSCrypt::UseMockKeyStorage(false); }
Lei Zhang 2016/05/18 22:38:16 Curious, how does OSCryptTest get away without doi
cfroussios 2016/05/19 21:18:19 This allows calls to OSCrypt functions to reach al
166
167 protected:
168 KeyStorageMock* key_storage_ = nullptr;
169
170 private:
171 DISALLOW_COPY_AND_ASSIGN(OSCryptLinuxTest);
172 };
173
174 TEST_F(OSCryptLinuxTest, VerifyV0) {
175 const std::string originaltext = "hello";
176 std::string ciphertext;
177 std::string decipheredtext;
178
179 key_storage_->ResetTo(std::string());
180 ciphertext = originaltext; // No encryption
181 ASSERT_TRUE(OSCrypt::DecryptString(ciphertext, &decipheredtext));
182 ASSERT_EQ(originaltext, decipheredtext);
183 }
184
185 TEST_F(OSCryptLinuxTest, VerifyV10) {
186 const std::string originaltext = "hello";
187 std::string ciphertext;
188 std::string decipheredtext;
189
190 key_storage_->ResetTo(std::string("peanuts"));
191 ASSERT_TRUE(OSCrypt::EncryptString(originaltext, &ciphertext));
192 key_storage_->ResetTo(std::string("not_peanuts"));
193 ciphertext = ciphertext.substr(3).insert(0, "v10");
194 ASSERT_TRUE(OSCrypt::DecryptString(ciphertext, &decipheredtext));
195 ASSERT_EQ(originaltext, decipheredtext);
196 }
197
198 TEST_F(OSCryptLinuxTest, VerifyV11) {
199 const std::string originaltext = "hello";
200 std::string ciphertext;
201 std::string decipheredtext;
202
203 key_storage_->ResetTo(std::string());
204 ASSERT_TRUE(OSCrypt::EncryptString(originaltext, &ciphertext));
205 ASSERT_EQ(ciphertext.substr(0, 3), "v11");
206 ASSERT_TRUE(OSCrypt::DecryptString(ciphertext, &decipheredtext));
207 ASSERT_EQ(originaltext, decipheredtext);
208 }
209
210 class LibsecretTest : public testing::Test {
211 public:
212 LibsecretTest() = default;
213 ~LibsecretTest() override = default;
214
215 void SetUp() override { MockLibsecretLoader::ResetForOSCrypt(); }
216
217 void TearDown() override { MockLibsecretLoader::TearDown(); }
218
219 protected:
Lei Zhang 2016/05/18 22:38:16 Remove.
cfroussios 2016/05/19 21:18:19 Done.
220 private:
221 DISALLOW_COPY_AND_ASSIGN(LibsecretTest);
222 };
223
224 TEST_F(LibsecretTest, LibsecretRepeats) {
225 KeyStorageLibsecret libsecret;
226 MockLibsecretLoader::ResetForOSCrypt();
227 std::string password = libsecret.GetKey();
228 EXPECT_FALSE(password.empty());
229 std::string password_repeat = libsecret.GetKey();
230 EXPECT_EQ(password, password_repeat);
231 }
232
233 TEST_F(LibsecretTest, LibsecretCreatesRandomised) {
234 KeyStorageLibsecret libsecret;
235 MockLibsecretLoader::ResetForOSCrypt();
236 std::string password = libsecret.GetKey();
237 MockLibsecretLoader::ResetForOSCrypt();
238 std::string password_new = libsecret.GetKey();
239 EXPECT_NE(password, password_new);
240 }
241
242 } // namespace
OLDNEW
« components/os_crypt/os_crypt_linux.cc ('K') | « components/os_crypt/os_crypt_unittest.cc ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698