lib: tlv length buffer checks

This commit is contained in:
Dave Pate
2019-01-22 08:17:45 -08:00
committed by Klas Lindfors
parent afbe1b2670
commit 5113a5ed02
2 changed files with 22 additions and 2 deletions
+1
View File
@@ -193,6 +193,7 @@ ykpiv_rc _ykpiv_ensure_application_selected(ykpiv_state *state);
ykpiv_rc _ykpiv_select_application(ykpiv_state *state); ykpiv_rc _ykpiv_select_application(ykpiv_state *state);
unsigned int _ykpiv_set_length(unsigned char *buffer, size_t length); unsigned int _ykpiv_set_length(unsigned char *buffer, size_t length);
unsigned int _ykpiv_get_length(const unsigned char *buffer, size_t *len); unsigned int _ykpiv_get_length(const unsigned char *buffer, size_t *len);
bool _ykpiv_has_valid_length(const unsigned char* buffer, size_t len);
void* _ykpiv_alloc(ykpiv_state *state, size_t size); void* _ykpiv_alloc(ykpiv_state *state, size_t size);
void* _ykpiv_realloc(ykpiv_state *state, void *address, size_t size); void* _ykpiv_realloc(ykpiv_state *state, void *address, size_t size);
+21 -2
View File
@@ -186,6 +186,19 @@ unsigned int _ykpiv_get_length(const unsigned char *buffer, size_t *len) {
return 0; return 0;
} }
bool _ykpiv_has_valid_length(const unsigned char* buffer, size_t len) {
if ((buffer[0] < 0x81) && (len > 0)) {
return true;
}
else if (((*buffer & 0x7f) == 1) && (len > 1)) {
return true;
}
else if (((*buffer & 0x7f) == 2) && (len > 2)) {
return true;
}
return false;
}
static unsigned char *set_object(int object_id, unsigned char *buffer) { static unsigned char *set_object(int object_id, unsigned char *buffer) {
*buffer++ = 0x5c; *buffer++ = 0x5c;
if(object_id == YKPIV_OBJ_DISCOVERY) { if(object_id == YKPIV_OBJ_DISCOVERY) {
@@ -1514,8 +1527,14 @@ ykpiv_rc _ykpiv_fetch_object(ykpiv_state *state, int object_id,
} }
if(sw == SW_SUCCESS) { if(sw == SW_SUCCESS) {
size_t outlen; size_t outlen = 0;
unsigned int offs = _ykpiv_get_length(data + 1, &outlen); unsigned int offs = 0;
if ((*len < 2) || !_ykpiv_has_valid_length(data + 1, *len - 1)) {
return YKPIV_SIZE_ERROR;
}
offs = _ykpiv_get_length(data + 1, &outlen);
if(offs == 0) { if(offs == 0) {
return YKPIV_SIZE_ERROR; return YKPIV_SIZE_ERROR;
} }