summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAnderson Toshiyuki Sasaki <ansasaki@redhat.com>2019-10-03 18:49:59 +0200
committerAnderson Toshiyuki Sasaki <ansasaki@redhat.com>2019-10-07 11:41:30 +0200
commitfe18ef279881b65434e3e44fc4743e4b1c7cb891 (patch)
treeea099100544ad2be9c2cd948d33d4bf26c96b8ab
parent689f1b0a6b8a40bf15917abed450b568c031285b (diff)
downloadlibssh-fe18ef279881b65434e3e44fc4743e4b1c7cb891.tar.gz
libssh-fe18ef279881b65434e3e44fc4743e4b1c7cb891.tar.xz
libssh-fe18ef279881b65434e3e44fc4743e4b1c7cb891.zip
pki_crypto: Use temporary pointer when using i2d_*
These functions modify the provided pointer by advancing to the end of if (point to the byte after the last written). This makes the pointer invalid, making necessary to use a temporary variable. Signed-off-by: Anderson Toshiyuki Sasaki <ansasaki@redhat.com> Reviewed-by: Andreas Schneider <asn@cryptomilk.org>
-rw-r--r--src/pki_crypto.c39
1 files changed, 35 insertions, 4 deletions
diff --git a/src/pki_crypto.c b/src/pki_crypto.c
index 4517e11d..6d312437 100644
--- a/src/pki_crypto.c
+++ b/src/pki_crypto.c
@@ -1642,6 +1642,7 @@ static int pki_signature_from_dsa_blob(UNUSED_PARAM(const ssh_key pubkey),
int raw_sig_len = 0;
unsigned char *raw_sig_data = NULL;
+ unsigned char *temp_raw_sig = NULL;
int rc;
@@ -1700,8 +1701,23 @@ static int pki_signature_from_dsa_blob(UNUSED_PARAM(const ssh_key pubkey),
ps = NULL;
pr = NULL;
- raw_sig_len = i2d_DSA_SIG(dsa_sig, &raw_sig_data);
- if (raw_sig_len < 0) {
+ /* Get the expected size of the buffer */
+ rc = i2d_DSA_SIG(dsa_sig, NULL);
+ if (rc <= 0) {
+ goto error;
+ }
+ raw_sig_len = rc;
+
+ raw_sig_data = (unsigned char *)calloc(1, raw_sig_len);
+ if (raw_sig_data == NULL) {
+ goto error;
+ }
+ temp_raw_sig = raw_sig_data;
+
+ /* It is necessary to use a temporary pointer as i2d_* "advances" the
+ * pointer */
+ raw_sig_len = i2d_DSA_SIG(dsa_sig, &temp_raw_sig);
+ if (raw_sig_len <= 0) {
goto error;
}
@@ -1745,6 +1761,7 @@ static int pki_signature_from_ecdsa_blob(UNUSED_PARAM(const ssh_key pubkey),
uint32_t rlen;
unsigned char *raw_sig_data = NULL;
+ unsigned char *temp_raw_sig = NULL;
size_t raw_sig_len = 0;
int rc;
@@ -1820,12 +1837,26 @@ static int pki_signature_from_ecdsa_blob(UNUSED_PARAM(const ssh_key pubkey),
pr = NULL;
ps = NULL;
- rc = i2d_ECDSA_SIG(ecdsa_sig, &raw_sig_data);
- if (rc < 0) {
+ /* Get the expected size of the buffer */
+ rc = i2d_ECDSA_SIG(ecdsa_sig, NULL);
+ if (rc <= 0) {
goto error;
}
raw_sig_len = rc;
+ raw_sig_data = (unsigned char *)calloc(1, raw_sig_len);
+ if (raw_sig_data == NULL) {
+ goto error;
+ }
+ temp_raw_sig = raw_sig_data;
+
+ /* It is necessary to use a temporary pointer as i2d_* "advances" the
+ * pointer */
+ rc = i2d_ECDSA_SIG(ecdsa_sig, &temp_raw_sig);
+ if (rc <= 0) {
+ goto error;
+ }
+
sig->raw_sig = ssh_string_new(raw_sig_len);
if (sig->raw_sig == NULL) {
explicit_bzero(raw_sig_data, raw_sig_len);