8000 memory locking · githubzhaoliang/sqlcipher@1511806 · GitHub
[go: up one dir, main page]

Skip to content

Commit 1511806

Browse files
committed
memory locking
1 parent a2a5488 commit 1511806

File tree

1 file changed

+49
-10
lines changed

1 file changed

+49
-10
lines changed

src/crypto_impl.c

Lines changed: 49 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,13 @@
44
#include "sqliteInt.h"
55
#include "btreeInt.h"
66
#include "crypto.h"
7+
#ifndef OMIT_MEMLOCK
8+
#if defined __unix__ || defined MAC_OS_X
9+
#include <sys/mman.h>
10+
#elif defined _WIN32
11+
# include <windows.h>
12+
#endif
13+
#endif
714

815

916
/* the default implementation of SQLCipher uses a cipher_ctx
@@ -70,17 +77,49 @@ int sqlcipher_random (void *buffer, int length) {
7077
}
7178

7279
/**
73-
* Free and wipe memory
80+
* Free and wipe memory. Uses SQLites internal sqlite3_free so that memory
81+
* can be countend and memory leak detection works in the tet suite.
7482
* If ptr is not null memory will be freed.
7583
* If sz is greater than zero, the memory will be overwritten with zero before it is freed
84+
* If sz is > 0, and not compiled with OMIT_MEMLOCK, system will attempt to unlock the
85+
* memory segment so it can be paged
7686
*/
7787
void sqlcipher_free(void *ptr, int sz) {
7888
if(ptr) {
79-
if(sz > 0) memset(ptr, 0, sz);
89+
if(sz > 0) {
90+
memset(ptr, 0, sz);
91+
#ifndef OMIT_MEMLOCK
92+
#if defined __unix__ || defined MAC_OS_X
93+
munlock(ptr, sz);
94+
#elif defined _WIN32
95+
VirtualUnlock(ptr, sz);
96+
#endif
97+
#endif
98+
}
8099
sqlite3_free(ptr);
81100
}
82101
}
83102

103+
/**
104+
* allocate memory. Uses sqlite's internall malloc wrapper so memory can be
105+
* reference counted and leak detection works. Unless compiled with OMIT_MEMLOCK
106+
* attempts to lock the memory pages so sensitive information won't be swapped
107+
*/
108+
void* sqlcipher_malloc(size_t sz) {
109+
void *ptr = sqlite3Malloc(sz);
110+
#ifndef OMIT_MEMLOCK
111+
if(ptr) {
112+
#ifdef __unix__
113+
mlock(ptr, sz);
114+
#elif defined _WIN32
115+
VirtualLock(ptr, sz);
116+
#endif
117+
}
118+
#endif
119+
return ptr;
120+
}
121+
122+
84123
/**
85124
* Initialize a a new cipher_ctx struct. This function will allocate memory
86125
* for the cipher context and for the key
@@ -90,12 +129,12 @@ void sqlcipher_free(void *ptr, int sz) {
90129
*/
91130
int sqlcipher_cipher_ctx_init(cipher_ctx **iCtx) {
92131
cipher_ctx *ctx;
93-
*iCtx = sqlite3Malloc(sizeof(cipher_ctx));
132+
*iCtx = sqlcipher_malloc(sizeof(cipher_ctx));
94133
ctx = *iCtx;
95134
if(ctx == NULL) return SQLITE_NOMEM;
96135
memset(ctx, 0, sizeof(cipher_ctx));
97-
ctx->key = sqlite3Malloc(EVP_MAX_KEY_LENGTH);
98-
ctx->hmac_key = sqlite3Malloc(EVP_MAX_KEY_LENGTH);
136+
ctx->key = sqlcipher_malloc(EVP_MAX_KEY_LENGTH);
137+
ctx->hmac_key = sqlcipher_malloc(EVP_MAX_KEY_LENGTH);
99138
if(ctx->key == NULL) return SQLITE_NOMEM;
100139
if(ctx->hmac_key == NULL) return SQLITE_NOMEM;
101140
return SQLITE_OK;
@@ -160,7 +199,7 @@ int sqlcipher_cipher_ctx_copy(cipher_ctx *target, cipher_ctx *source) {
160199
target->hmac_key = hmac_key; //restore pointer to previously allocated hmac key data
161200
memcpy(target->hmac_key, source->hmac_key, EVP_MAX_KEY_LENGTH);
162201

163-
target->pass = sqlite3Malloc(source->pass_sz);
202+
target->pass = sqlcipher_malloc(source->pass_sz);
164203
if(target->pass == NULL) return SQLITE_NOMEM;
165204
memcpy(target->pass, source->pass, source->pass_sz);
166205

@@ -179,7 +218,7 @@ int sqlcipher_cipher_ctx_set_pass(cipher_ctx *ctx, const void *zKey, int nKey) {
179218
sqlcipher_free(ctx->pass, ctx->pass_sz);
180219
ctx->pass_sz = nKey;
181220
if(zKey && nKey) {
182-
ctx->pass = sqlite3Malloc(nKey);
221+
ctx->pass = sqlcipher_malloc(nKey);
183222
if(ctx->pass == NULL) return SQLITE_NOMEM;
184223
memcpy(ctx->pass, zKey, nKey);
185224
return SQLITE_OK;
@@ -285,7 +324,7 @@ int sqlcipher_codec_ctx_set_pagesize(codec_ctx *ctx, int size) {
285324
/* pre-allocate a page buffer of PageSize bytes. This will
286325
be used as a persistent buffer for encryption and decryption
287326
operations to avoid overhead of multiple memory allocations*/
288-
ctx->buffer = sqlite3Malloc(size);
327+
ctx->buffer = sqlcipher_malloc(size);
289328
if(ctx->buffer == NULL) return SQLITE_NOMEM;
290329

291330
return SQLITE_OK;
@@ -294,7 +333,7 @@ int sqlcipher_codec_ctx_set_pagesize(codec_ctx *ctx, int size) {
294333
int sqlcipher_codec_ctx_init(codec_ctx **iCtx, Db *pDb, Pager *pPager, sqlite3_file *fd, const void *zKey, int nKey) {
295334
int rc;
296335
codec_ctx *ctx;
297-
*iCtx = sqlite3Malloc(sizeof(codec_ctx));
336+
*iCtx = sqlcipher_malloc(sizeof(codec_ctx));
298337
ctx = *iCtx;
299338

300339
if(ctx == NULL) return SQLITE_NOMEM;
@@ -307,7 +346,7 @@ int sqlcipher_codec_ctx_init(codec_ctx **iCtx, Db *pDb, Pager *pPager, sqlite3_f
307346
key derivation function. If we get a short read allocate
308347
a new random salt value */
309348
ctx->kdf_salt_sz = FILE_HEADER_SZ;
310-
ctx->kdf_salt = sqlite3Malloc(ctx->kdf_salt_sz);
349+
ctx->kdf_salt = sqlcipher_malloc(ctx->kdf_salt_sz);
311350
if(ctx->kdf_salt == NULL) return SQLITE_NOMEM;
312351

313352
/*

0 commit comments

Comments
 (0)
0