aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMichael Brown <mcb30@ipxe.org>2020-02-16 23:19:03 +0000
committerMichael Brown <mcb30@ipxe.org>2020-02-16 23:19:55 +0000
commite2e29e7ae3608261314feab118f887f13d60b5c6 (patch)
treef03d0c3c5e99457fb750047ade585e8570f734ca
parent446e8f14e8a22731b52bad45d94b09f6f1672bd9 (diff)
downloadipxe-e2e29e7ae3608261314feab118f887f13d60b5c6.zip
ipxe-e2e29e7ae3608261314feab118f887f13d60b5c6.tar.gz
ipxe-e2e29e7ae3608261314feab118f887f13d60b5c6.tar.bz2
[iscsi] Eliminate variable-length stack allocations in CHAP handlers
Signed-off-by: Michael Brown <mcb30@ipxe.org>
-rw-r--r--src/net/tcp/iscsi.c52
1 files changed, 41 insertions, 11 deletions
diff --git a/src/net/tcp/iscsi.c b/src/net/tcp/iscsi.c
index f8379b2..4be9c1c 100644
--- a/src/net/tcp/iscsi.c
+++ b/src/net/tcp/iscsi.c
@@ -980,18 +980,26 @@ static int iscsi_handle_chap_i_value ( struct iscsi_session *iscsi,
*/
static int iscsi_handle_chap_c_value ( struct iscsi_session *iscsi,
const char *value ) {
- uint8_t buf[ strlen ( value ) ]; /* Decoding never expands data */
+ uint8_t *buf;
unsigned int i;
int len;
int rc;
+ /* Allocate decoding buffer */
+ len = strlen ( value ); /* Decoding never expands data */
+ buf = malloc ( len );
+ if ( ! buf ) {
+ rc = -ENOMEM;
+ goto err_alloc;
+ }
+
/* Process challenge */
- len = iscsi_large_binary_decode ( value, buf, sizeof ( buf ) );
+ len = iscsi_large_binary_decode ( value, buf, len );
if ( len < 0 ) {
rc = len;
DBGC ( iscsi, "iSCSI %p invalid CHAP challenge \"%s\": %s\n",
iscsi, value, strerror ( rc ) );
- return rc;
+ goto err_decode;
}
chap_update ( &iscsi->chap, buf, len );
@@ -1009,7 +1017,13 @@ static int iscsi_handle_chap_c_value ( struct iscsi_session *iscsi,
}
}
- return 0;
+ /* Success */
+ rc = 0;
+
+ err_decode:
+ free ( buf );
+ err_alloc:
+ return rc;
}
/**
@@ -1050,7 +1064,7 @@ static int iscsi_handle_chap_n_value ( struct iscsi_session *iscsi,
*/
static int iscsi_handle_chap_r_value ( struct iscsi_session *iscsi,
const char *value ) {
- uint8_t buf[ strlen ( value ) ]; /* Decoding never expands data */
+ uint8_t *buf;
int len;
int rc;
@@ -1059,7 +1073,7 @@ static int iscsi_handle_chap_r_value ( struct iscsi_session *iscsi,
if ( ( rc = chap_init ( &iscsi->chap, &md5_algorithm ) ) != 0 ) {
DBGC ( iscsi, "iSCSI %p could not initialise CHAP: %s\n",
iscsi, strerror ( rc ) );
- return rc;
+ goto err_chap_init;
}
chap_set_identifier ( &iscsi->chap, iscsi->chap_challenge[0] );
if ( iscsi->target_password ) {
@@ -1070,31 +1084,47 @@ static int iscsi_handle_chap_r_value ( struct iscsi_session *iscsi,
( sizeof ( iscsi->chap_challenge ) - 1 ) );
chap_respond ( &iscsi->chap );
+ /* Allocate decoding buffer */
+ len = strlen ( value ); /* Decoding never expands data */
+ buf = malloc ( len );
+ if ( ! buf ) {
+ rc = -ENOMEM;
+ goto err_alloc;
+ }
+
/* Process response */
- len = iscsi_large_binary_decode ( value, buf, sizeof ( buf ) );
+ len = iscsi_large_binary_decode ( value, buf, len );
if ( len < 0 ) {
rc = len;
DBGC ( iscsi, "iSCSI %p invalid CHAP response \"%s\": %s\n",
iscsi, value, strerror ( rc ) );
- return rc;
+ goto err_decode;
}
/* Check CHAP response */
if ( len != ( int ) iscsi->chap.response_len ) {
DBGC ( iscsi, "iSCSI %p invalid CHAP response length\n",
iscsi );
- return -EPROTO_INVALID_CHAP_RESPONSE;
+ rc = -EPROTO_INVALID_CHAP_RESPONSE;
+ goto err_response_len;
}
if ( memcmp ( buf, iscsi->chap.response, len ) != 0 ) {
DBGC ( iscsi, "iSCSI %p incorrect CHAP response \"%s\"\n",
iscsi, value );
- return -EACCES_INCORRECT_TARGET_PASSWORD;
+ rc = -EACCES_INCORRECT_TARGET_PASSWORD;
+ goto err_response;
}
/* Mark session as authenticated */
iscsi->status |= ISCSI_STATUS_AUTH_REVERSE_OK;
- return 0;
+ err_response:
+ err_response_len:
+ err_decode:
+ free ( buf );
+ err_alloc:
+ err_chap_init:
+ return rc;
}
/** An iSCSI text string that we want to handle */