Skip to content

Commit 7ecdade

Browse files
Gidon Gershinskyggershinsky
Gidon Gershinsky
authored andcommitted
iv comment and buffer length
1 parent 8e7fe90 commit 7ecdade

File tree

1 file changed

+30
-29
lines changed

1 file changed

+30
-29
lines changed

cpp/src/parquet/util/crypto.cc

+30-29
Original file line numberDiff line numberDiff line change
@@ -142,19 +142,19 @@ int gcm_encrypt(const uint8_t* plaintext, int plaintext_len, uint8_t* key, int k
142142

143143
uint8_t tag[gcmTagLen];
144144
memset(tag, 0, gcmTagLen);
145-
uint8_t iv[nonceLen];
146-
memset(iv, 0, nonceLen);
145+
uint8_t nonce[nonceLen];
146+
memset(nonce, 0, nonceLen);
147147

148-
// Random IV
148+
// Random nonce
149149
RAND_load_file("/dev/urandom", rndMaxBytes);
150-
RAND_bytes(iv, sizeof(iv));
150+
RAND_bytes(nonce, sizeof(nonce));
151151

152152
// Init cipher context
153153
EvpCipher cipher(aesGcm, key_len, encryptType);
154154

155-
// Setting key and IV
156-
if (1 != EVP_EncryptInit_ex(cipher.get(), nullptr, nullptr, key, iv)) {
157-
throw ParquetException("Couldn't set key and IV");
155+
// Setting key and IV (nonce)
156+
if (1 != EVP_EncryptInit_ex(cipher.get(), nullptr, nullptr, key, nonce)) {
157+
throw ParquetException("Couldn't set key and nonce");
158158
}
159159

160160
// Setting additional authenticated data
@@ -183,37 +183,38 @@ int gcm_encrypt(const uint8_t* plaintext, int plaintext_len, uint8_t* key, int k
183183
throw ParquetException("Couldn't get AES-GCM tag");
184184
}
185185

186-
// Copying the buffer size, IV and tag to ciphertext
186+
// Copying the buffer size, nonce and tag to ciphertext
187187
int bufferSize = nonceLen + ciphertext_len + gcmTagLen;
188188
uint8_t bufferSizeArray [bufferSizeLen];
189189
bufferSizeArray[3] = 0xff & (bufferSize >> 24);
190190
bufferSizeArray[2] = 0xff & (bufferSize >> 16);
191191
bufferSizeArray[1] = 0xff & (bufferSize >> 8);
192192
bufferSizeArray[0] = 0xff & (bufferSize);
193193
std::copy(bufferSizeArray, bufferSizeArray + bufferSizeLen, ciphertext);
194-
std::copy(iv, iv + nonceLen, ciphertext + bufferSizeLen);
194+
std::copy(nonce, nonce + nonceLen, ciphertext + bufferSizeLen);
195195
std::copy(tag, tag + gcmTagLen, ciphertext + bufferSizeLen + nonceLen + ciphertext_len);
196196

197-
return bufferSize;
197+
return bufferSizeLen + bufferSize;
198198
}
199199

200200
int ctr_encrypt(const uint8_t* plaintext, int plaintext_len, uint8_t* key, int key_len,
201201
uint8_t* ciphertext) {
202202
int len;
203203
int ciphertext_len;
204-
205-
uint8_t iv[ctrIvLen];
206-
memset(iv, 0, ctrIvLen);
207-
iv[ctrIvLen - 1] = 1;
208204

209205
uint8_t nonce[nonceLen];
210-
memset(iv, 0, nonceLen);
206+
memset(nonce, 0, nonceLen);
211207

212208
// Random nonce
213209
RAND_load_file("/dev/urandom", rndMaxBytes);
214210
RAND_bytes(nonce, sizeof(nonce));
215-
211+
212+
// Parquet CTR IVs are comprised of a 12-byte nonce and a 4-byte initial counter field.
213+
// The first 31 bits of the initial counter field are set to 0, the last bit is set to 1.
214+
uint8_t iv[ctrIvLen];
215+
memset(iv, 0, ctrIvLen);
216216
std::copy(nonce, nonce + nonceLen, iv);
217+
iv[ctrIvLen - 1] = 1;
217218

218219
// Init cipher context
219220
EvpCipher cipher(aesCtr, key_len, encryptType);
@@ -248,7 +249,7 @@ int ctr_encrypt(const uint8_t* plaintext, int plaintext_len, uint8_t* key, int k
248249
std::copy(bufferSizeArray, bufferSizeArray + bufferSizeLen, ciphertext);
249250
std::copy(iv, iv + ctrIvLen, ciphertext + bufferSizeLen);
250251

251-
return bufferSize;
252+
return bufferSizeLen + bufferSize;
252253
}
253254

254255
int Encrypt(Encryption::type alg_id, bool metadata, const uint8_t* plaintext,
@@ -283,30 +284,30 @@ int gcm_decrypt(const uint8_t* ciphertext, int ciphertext_len, uint8_t* key, int
283284

284285
uint8_t tag[gcmTagLen];
285286
memset(tag, 0, gcmTagLen);
286-
uint8_t iv[nonceLen];
287-
memset(iv, 0, nonceLen);
287+
uint8_t nonce[nonceLen];
288+
memset(nonce, 0, nonceLen);
288289

289290
// Extract ciphertext length
290-
int ciphertext_length =
291+
int written_ciphertext_len =
291292
((ciphertext[3] & 0xff) << 24) |
292293
((ciphertext[2] & 0xff) << 16) |
293294
((ciphertext[1] & 0xff) << 8) |
294295
((ciphertext[0] & 0xff));
295296

296-
if (ciphertext_len > 0 && ciphertext_len != ciphertext_length) {
297+
if (ciphertext_len > 0 && ciphertext_len != (written_ciphertext_len + bufferSizeLen)) {
297298
throw ParquetException("Wrong ciphertext length");
298299
}
299-
ciphertext_len = ciphertext_length;
300+
ciphertext_len = written_ciphertext_len + bufferSizeLen;
300301

301302
// Extracting IV and tag
302-
std::copy(ciphertext + bufferSizeLen, ciphertext + bufferSizeLen + nonceLen, iv);
303+
std::copy(ciphertext + bufferSizeLen, ciphertext + bufferSizeLen + nonceLen, nonce);
303304
std::copy(ciphertext + ciphertext_len - gcmTagLen, ciphertext + ciphertext_len, tag);
304305

305306
// Init cipher context
306307
EvpCipher cipher(aesGcm, key_len, decryptType);
307308

308309
// Setting key and IV
309-
if (1 != EVP_DecryptInit_ex(cipher.get(), nullptr, nullptr, key, iv)) {
310+
if (1 != EVP_DecryptInit_ex(cipher.get(), nullptr, nullptr, key, nonce)) {
310311
throw ParquetException("Couldn't set key and IV");
311312
}
312313

@@ -347,18 +348,18 @@ int ctr_decrypt(const uint8_t* ciphertext, int ciphertext_len, uint8_t* key, int
347348
memset(iv, 0, ctrIvLen);
348349

349350
// Extract ciphertext length
350-
int ciphertext_length =
351+
int written_ciphertext_len =
351352
((ciphertext[3] & 0xff) << 24) |
352353
((ciphertext[2] & 0xff) << 16) |
353354
((ciphertext[1] & 0xff) << 8) |
354355
((ciphertext[0] & 0xff));
355356

356-
if (ciphertext_len > 0 && ciphertext_len != ciphertext_length) {
357+
if (ciphertext_len > 0 && ciphertext_len != (written_ciphertext_len + bufferSizeLen)) {
357358
throw ParquetException("Wrong ciphertext length");
358359
}
359-
ciphertext_len = ciphertext_length;
360+
ciphertext_len = written_ciphertext_len;
360361

361-
// Extracting IV and tag
362+
// Extracting IV
362363
std::copy(ciphertext + bufferSizeLen, ciphertext + bufferSizeLen + ctrIvLen, iv);
363364

364365
// Init cipher context
@@ -371,7 +372,7 @@ int ctr_decrypt(const uint8_t* ciphertext, int ciphertext_len, uint8_t* key, int
371372

372373
// Decryption
373374
if (!EVP_DecryptUpdate(cipher.get(), plaintext, &len, ciphertext + bufferSizeLen + ctrIvLen,
374-
ciphertext_len - bufferSizeLen - ctrIvLen)) {
375+
ciphertext_len - ctrIvLen)) {
375376
throw ParquetException("Failed decryption update");
376377
}
377378

0 commit comments

Comments
 (0)