Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
L
libvmod-ece
Project
Project
Details
Activity
Releases
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
uplex-varnish
libvmod-ece
Commits
85d7f62c
Commit
85d7f62c
authored
Sep 05, 2019
by
Geoff Simmons
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
Test encryption against the example in ch 3.2 of RFC8188.
Exposed a bug in padding that has been fixed.
parent
0e70d1a7
Changes
3
Hide whitespace changes
Inline
Side-by-side
Showing
3 changed files
with
97 additions
and
26 deletions
+97
-26
rfc8188.c
src/rfc8188.c
+11
-11
rfc8188.h
src/rfc8188.h
+9
-2
rfc8188_test.c
src/rfc8188_test.c
+77
-13
No files found.
src/rfc8188.c
View file @
85d7f62c
...
@@ -86,11 +86,11 @@ encode_header(uint8_t *hdr, uint32_t rs, uint8_t idlen, uint8_t *keyid)
...
@@ -86,11 +86,11 @@ encode_header(uint8_t *hdr, uint32_t rs, uint8_t idlen, uint8_t *keyid)
int
int
add_salt
(
unsigned
char
*
hdr
,
char
*
errmsg
)
add_salt
(
unsigned
char
*
hdr
,
char
*
errmsg
)
{
{
if
(
RAND_bytes
(
hdr
,
SALT_LEN
)
!=
1
)
{
if
(
RAND_bytes
(
hdr
,
SALT_LEN
)
!=
1
)
{
mk_error
(
errmsg
);
mk_error
(
errmsg
);
return
(
-
1
);
return
(
-
1
);
}
}
return
0
;
return
0
;
}
}
/* ch 2.2 pseudorandom key */
/* ch 2.2 pseudorandom key */
...
@@ -272,7 +272,7 @@ encrypt_record(EVP_CIPHER_CTX *ctx, unsigned char *plaintext,
...
@@ -272,7 +272,7 @@ encrypt_record(EVP_CIPHER_CTX *ctx, unsigned char *plaintext,
unsigned
char
nonce
[
NONCE_LEN
],
int
last
,
unsigned
char
*
ciphertext
,
unsigned
char
nonce
[
NONCE_LEN
],
int
last
,
unsigned
char
*
ciphertext
,
char
errmsg
[
ERRMSG_LEN
])
char
errmsg
[
ERRMSG_LEN
])
{
{
int
delim_idx
,
len
,
ciphertext_len
;
int
len
,
ciphertext_len
;
uint8_t
*
tag
;
uint8_t
*
tag
;
AN
(
ctx
);
AN
(
ctx
);
...
@@ -285,12 +285,11 @@ encrypt_record(EVP_CIPHER_CTX *ctx, unsigned char *plaintext,
...
@@ -285,12 +285,11 @@ encrypt_record(EVP_CIPHER_CTX *ctx, unsigned char *plaintext,
assert
(
rs
>=
18
);
assert
(
rs
>=
18
);
assert
((
unsigned
)
plaintext_len
<=
rs
-
(
TAG_LEN
+
1
));
assert
((
unsigned
)
plaintext_len
<=
rs
-
(
TAG_LEN
+
1
));
delim_idx
=
rs
-
(
TAG_LEN
+
1
);
if
(
!
last
)
if
(
!
last
)
plaintext
[
delim_idx
]
=
'\1'
;
plaintext
[
plaintext_len
]
=
'\1'
;
else
else
plaintext
[
delim_idx
]
=
'\2'
;
plaintext
[
plaintext_len
]
=
'\2'
;
for
(
int
i
=
delim_idx
-
1
;
i
>
plaintext_len
;
i
--
)
for
(
unsigned
i
=
plaintext_len
+
1
;
i
<
rs
-
TAG_LEN
;
i
++
)
plaintext
[
i
]
=
'\0'
;
plaintext
[
i
]
=
'\0'
;
if
(
EVP_CipherInit_ex
(
ctx
,
EVP_aes_128_gcm
(),
NULL
,
cek
,
nonce
,
-
1
)
if
(
EVP_CipherInit_ex
(
ctx
,
EVP_aes_128_gcm
(),
NULL
,
cek
,
nonce
,
-
1
)
...
@@ -317,8 +316,9 @@ encrypt_record(EVP_CIPHER_CTX *ctx, unsigned char *plaintext,
...
@@ -317,8 +316,9 @@ encrypt_record(EVP_CIPHER_CTX *ctx, unsigned char *plaintext,
return
(
-
1
);
return
(
-
1
);
}
}
ciphertext_len
+=
len
;
ciphertext_len
+=
len
;
assert
((
unsigned
)
ciphertext_len
==
rs
-
TAG_LEN
);
tag
=
ciphertext
+
(
rs
-
TAG_LEN
)
;
tag
=
ciphertext
+
ciphertext_len
;
if
(
!
EVP_CIPHER_CTX_ctrl
(
ctx
,
EVP_CTRL_GCM_GET_TAG
,
TAG_LEN
,
tag
))
{
if
(
!
EVP_CIPHER_CTX_ctrl
(
ctx
,
EVP_CTRL_GCM_GET_TAG
,
TAG_LEN
,
tag
))
{
mk_error
(
errmsg
);
mk_error
(
errmsg
);
return
(
-
1
);
return
(
-
1
);
...
...
src/rfc8188.h
View file @
85d7f62c
...
@@ -165,17 +165,24 @@ ssize_t decrypt_record(EVP_CIPHER_CTX *ctx, unsigned char *ciphertext,
...
@@ -165,17 +165,24 @@ ssize_t decrypt_record(EVP_CIPHER_CTX *ctx, unsigned char *ciphertext,
* ciphertext
* ciphertext
*
*
* The buffer at plaintext MUST have at least rs bytes allocated.
* The buffer at plaintext MUST have at least rs bytes allocated.
* plaintext is modified for padding during the call; make a copy if the
* original plaintext must be retained. This is necessary in particular
* when more than one record is required for a message, since the
* plaintext for subsequent records must begin at a location that will
* have been overwritten.
*
*
* plaintext_len MAY NOT be > rs - (TAG_LEN + 1).
* plaintext_len MAY NOT be > rs - (TAG_LEN + 1).
*
*
* rs for every record MUST equal the record size set for the entire
* message, except possibly for the last record, which may be smaller.
*
* If last is non-zero, then this is the last record in the message.
* If last is non-zero, then this is the last record in the message.
*
*
* At least rs bytes must be allocated for the buffer at ciphertext.
* At least rs bytes must be allocated for the buffer at ciphertext.
* The authentication tag is appended at ciphertext + (rs - TAG_LEN).
* The authentication tag is appended at ciphertext + (rs - TAG_LEN).
*
*
* Returns -1 on error, otherwise the number of ciphertext bytes. That
* Returns -1 on error, otherwise the number of ciphertext bytes. That
* number will be equal to rs for every record but the last, which may be
* number will be equal to (rs - TAG_LEN) for every record.
* smaller.
*/
*/
ssize_t
encrypt_record
(
EVP_CIPHER_CTX
*
ctx
,
unsigned
char
*
plaintext
,
ssize_t
encrypt_record
(
EVP_CIPHER_CTX
*
ctx
,
unsigned
char
*
plaintext
,
int
plaintext_len
,
uint32_t
rs
,
uint8_t
cek
[
AES128_KEYLEN
],
int
plaintext_len
,
uint32_t
rs
,
uint8_t
cek
[
AES128_KEYLEN
],
...
...
src/rfc8188_test.c
View file @
85d7f62c
...
@@ -77,6 +77,7 @@ const unsigned char body2_b64[] =
...
@@ -77,6 +77,7 @@ const unsigned char body2_b64[] =
"uNCkWiNYzKTnBN9ji3+qWAAAABkCYTHOG8chz/gnvgOqdGYovxyjuqRyJFjEDyoF1Fvkj6hQPdPHI51OEUKEpgz3SsLWIqS/uA=="
,
"uNCkWiNYzKTnBN9ji3+qWAAAABkCYTHOG8chz/gnvgOqdGYovxyjuqRyJFjEDyoF1Fvkj6hQPdPHI51OEUKEpgz3SsLWIqS/uA=="
,
key2_b64
[]
=
"BO3ZVPxUlnLORbVGMpbT1Q=="
,
key2_b64
[]
=
"BO3ZVPxUlnLORbVGMpbT1Q=="
,
exp_keyid2
[]
=
"a1"
;
exp_keyid2
[]
=
"a1"
;
static
const
int
exp_bodylen2
=
73
;
static
const
uint32_t
exp_rs2
=
25
;
static
const
uint32_t
exp_rs2
=
25
;
static
const
uint8_t
exp_idlen2
=
2
;
static
const
uint8_t
exp_idlen2
=
2
;
...
@@ -85,7 +86,7 @@ main(int argc, char *argv[])
...
@@ -85,7 +86,7 @@ main(int argc, char *argv[])
{
{
EVP_CIPHER_CTX
*
ctx
;
EVP_CIPHER_CTX
*
ctx
;
unsigned
char
prk_b64
[
45
],
cek_b64
[
25
],
nonce_b64
[
17
],
unsigned
char
prk_b64
[
45
],
cek_b64
[
25
],
nonce_b64
[
17
],
body1_test_b64
[
73
];
body1_test_b64
[
73
]
,
body2_test_b64
[
101
]
;
unsigned
char
key1
[
AES128_KEYLEN
+
2
],
key2
[
AES128_KEYLEN
+
2
],
unsigned
char
key1
[
AES128_KEYLEN
+
2
],
key2
[
AES128_KEYLEN
+
2
],
salt
[
SALT_LEN
+
2
],
prk
[
SHA256_LEN
],
cek
[
SHA256_LEN
],
salt
[
SALT_LEN
+
2
],
prk
[
SHA256_LEN
],
cek
[
SHA256_LEN
],
nonce
[
SHA256_LEN
],
seq
[
NONCE_LEN
],
nonce
[
SHA256_LEN
],
seq
[
NONCE_LEN
],
...
@@ -93,7 +94,7 @@ main(int argc, char *argv[])
...
@@ -93,7 +94,7 @@ main(int argc, char *argv[])
char
errmsg
[
ERRMSG_LEN
];
char
errmsg
[
ERRMSG_LEN
];
uint32_t
rs
;
uint32_t
rs
;
uint8_t
idlen
;
uint8_t
idlen
;
int
len
,
last
,
plaintext_len
;
int
len
,
last
,
plaintext_len
,
ciphertext_len
;
(
void
)
argc
;
(
void
)
argc
;
(
void
)
argv
;
(
void
)
argv
;
...
@@ -162,10 +163,7 @@ main(int argc, char *argv[])
...
@@ -162,10 +163,7 @@ main(int argc, char *argv[])
/* example 2, ch 3.2 */
/* example 2, ch 3.2 */
if
((
ctx
=
cipher_ctx_reset
(
ctx
,
0
,
errmsg
))
==
NULL
)
{
memset
(
plaintext
,
0x00
,
sizeof
(
plaintext
));
fprintf
(
stderr
,
"ex2: cipher_ctx_reset: %s
\n
"
,
errmsg
);
exit
(
-
1
);
}
len
=
EVP_DecodeBlock
(
key2
,
key2_b64
,
sizeof
(
key2_b64
)
-
1
);
len
=
EVP_DecodeBlock
(
key2
,
key2_b64
,
sizeof
(
key2_b64
)
-
1
);
assert
(
len
==
AES128_KEYLEN
+
2
);
assert
(
len
==
AES128_KEYLEN
+
2
);
...
@@ -178,15 +176,15 @@ main(int argc, char *argv[])
...
@@ -178,15 +176,15 @@ main(int argc, char *argv[])
AZ
(
memcmp
(
&
body2
[
HDR_PREFIX_LEN
],
exp_keyid2
,
idlen
));
AZ
(
memcmp
(
&
body2
[
HDR_PREFIX_LEN
],
exp_keyid2
,
idlen
));
if
(
derive_prk
(
body2
,
key2
,
prk
,
errmsg
)
!=
0
)
{
if
(
derive_prk
(
body2
,
key2
,
prk
,
errmsg
)
!=
0
)
{
fprintf
(
stderr
,
"ex2 PRK: %s
\n
"
,
errmsg
);
fprintf
(
stderr
,
"ex2
decrypt
PRK: %s
\n
"
,
errmsg
);
exit
(
-
1
);
exit
(
-
1
);
}
}
if
(
derive_cek
(
prk
,
cek
,
errmsg
)
!=
0
)
{
if
(
derive_cek
(
prk
,
cek
,
errmsg
)
!=
0
)
{
fprintf
(
stderr
,
"ex2 CEK: %s
\n
"
,
errmsg
);
fprintf
(
stderr
,
"ex2
decrypt
CEK: %s
\n
"
,
errmsg
);
exit
(
-
1
);
exit
(
-
1
);
}
}
if
(
derive_prenonce
(
prk
,
nonce
,
errmsg
)
!=
0
)
{
if
(
derive_prenonce
(
prk
,
nonce
,
errmsg
)
!=
0
)
{
fprintf
(
stderr
,
"ex2 NONCE: %s
\n
"
,
errmsg
);
fprintf
(
stderr
,
"ex2
decrypt
NONCE: %s
\n
"
,
errmsg
);
exit
(
-
1
);
exit
(
-
1
);
}
}
...
@@ -222,7 +220,7 @@ main(int argc, char *argv[])
...
@@ -222,7 +220,7 @@ main(int argc, char *argv[])
/* example 1, ch 3.1, encryption */
/* example 1, ch 3.1, encryption */
memset
(
plaintext
,
0xff
,
64
);
memset
(
plaintext
,
0xff
,
sizeof
(
plaintext
)
);
memcpy
(
plaintext
,
exp_plaintext
,
exp_plaintext_len
);
memcpy
(
plaintext
,
exp_plaintext
,
exp_plaintext_len
);
/* Ordinarily call add_salt() to get random salt. */
/* Ordinarily call add_salt() to get random salt. */
...
@@ -278,12 +276,78 @@ main(int argc, char *argv[])
...
@@ -278,12 +276,78 @@ main(int argc, char *argv[])
len
=
EVP_EncodeBlock
(
body1_test_b64
,
body1
,
bodylen1
);
len
=
EVP_EncodeBlock
(
body1_test_b64
,
body1
,
bodylen1
);
assert
(
len
==
72
);
assert
(
len
==
72
);
AZ
(
memcmp
(
body1_test_b64
,
body1_b64
,
len
));
AZ
(
memcmp
(
body1_test_b64
,
body1_b64
,
len
));
cipher_ctx_fini
(
ctx
);
/* example 2, ch 3.2, encryption */
memset
(
plaintext
,
0
,
sizeof
(
plaintext
));
memcpy
(
plaintext
,
exp_plaintext
,
exp_plaintext_len
);
/*
* The salt previously decoded for the decryption test is still in
* body2.
*/
memset
(
body2
+
SALT_LEN
,
0xff
,
sizeof
(
body2
)
-
SALT_LEN
);
encode_header
(
body2
,
exp_rs2
,
exp_idlen2
,
(
uint8_t
*
)
exp_keyid2
);
if
(
derive_prk
(
body2
,
key2
,
prk
,
errmsg
)
!=
0
)
{
fprintf
(
stderr
,
"ex2 encrypt PRK: %s
\n
"
,
errmsg
);
exit
(
-
1
);
}
if
(
derive_cek
(
prk
,
cek
,
errmsg
)
!=
0
)
{
fprintf
(
stderr
,
"ex2 encrypt CEK: %s
\n
"
,
errmsg
);
exit
(
-
1
);
}
if
(
derive_prenonce
(
prk
,
nonce
,
errmsg
)
!=
0
)
{
fprintf
(
stderr
,
"ex2 encrypt NONCE: %s
\n
"
,
errmsg
);
exit
(
-
1
);
}
if
((
ctx
=
cipher_ctx_init
(
1
,
errmsg
))
==
NULL
)
{
fprintf
(
stderr
,
"ex2 encrypt: cipher_ctx_init: %s
\n
"
,
errmsg
);
exit
(
-
1
);
}
/* First record, first 7 bytes of the plaintext */
last
=
0
;
ciphertext
=
body2
+
HDR_PREFIX_LEN
+
exp_idlen2
;
len
=
encrypt_record
(
ctx
,
plaintext
,
7
,
exp_rs2
,
cek
,
nonce
,
last
,
ciphertext
,
errmsg
);
if
(
len
<
0
)
{
fprintf
(
stderr
,
"ex2 1st record encrypt_record: %s
\n
"
,
errmsg
);
exit
(
-
1
);
}
assert
((
unsigned
)
len
==
exp_rs2
-
TAG_LEN
);
ciphertext_len
=
exp_rs2
;
/* Second record, last 8 bytes of the plaintext */
seq
[
NONCE_LEN
-
1
]
=
1
;
// simulates increment
for
(
int
i
=
0
;
i
<
NONCE_LEN
;
i
++
)
nonce
[
i
]
^=
seq
[
i
];
ciphertext
+=
ciphertext_len
;
last
=
1
;
/* plaintext was overwritten for padding */
memcpy
(
plaintext
,
exp_plaintext
,
exp_plaintext_len
);
len
=
encrypt_record
(
ctx
,
plaintext
+
7
,
8
,
exp_rs2
,
cek
,
nonce
,
last
,
ciphertext
,
errmsg
);
if
(
len
<
0
)
{
fprintf
(
stderr
,
"ex1 2nd record encrypt_record: %s
\n
"
,
errmsg
);
exit
(
-
1
);
}
assert
((
unsigned
)
len
==
exp_rs2
-
TAG_LEN
);
ciphertext_len
+=
exp_rs2
;
assert
(
ciphertext_len
+
HDR_PREFIX_LEN
+
exp_idlen2
==
exp_bodylen2
);
len
=
EVP_EncodeBlock
(
body2_test_b64
,
body2
,
exp_bodylen2
);
assert
(
len
==
100
);
AZ
(
memcmp
(
body2_test_b64
,
body2_b64
,
len
));
cipher_ctx_fini
(
ctx
);
cipher_ctx_fini
(
ctx
);
/* Just call add_salt() for sanity's sake. */
/* Just call add_salt() for sanity's sake. */
memset
(
body1
,
0
,
SALT_LEN
);
memset
(
body1
,
0
,
SALT_LEN
);
if
(
add_salt
(
body1
,
errmsg
)
!=
0
)
{
if
(
add_salt
(
body1
,
errmsg
)
!=
0
)
{
fprintf
(
stderr
,
"add_salt: %s
\n
"
,
errmsg
);
fprintf
(
stderr
,
"add_salt: %s
\n
"
,
errmsg
);
exit
(
-
1
);
exit
(
-
1
);
}
}
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment