mirror of https://github.com/openssl/openssl.git
Add support for streams to the quic-client fuzzer
Enable the quic-client fuzzer to accept and create new streams Reviewed-by: Hugo Landau <hlandau@openssl.org> Reviewed-by: Tomas Mraz <tomas@openssl.org> (Merged from https://github.com/openssl/openssl/pull/22592)
This commit is contained in:
parent
d3dcf88cc5
commit
3fa274ca81
|
@ -43,13 +43,18 @@ int FuzzerInitialize(int *argc, char ***argv)
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
#define HANDSHAKING 0
|
#define HANDSHAKING 0
|
||||||
#define READING 1
|
#define READING 1
|
||||||
#define WRITING 2
|
#define WRITING 2
|
||||||
|
#define ACCEPTING_STREAM 3
|
||||||
|
#define CREATING_STREAM 4
|
||||||
|
#define SWAPPING_STREAM 5
|
||||||
|
|
||||||
int FuzzerTestOneInput(const uint8_t *buf, size_t len)
|
int FuzzerTestOneInput(const uint8_t *buf, size_t len)
|
||||||
{
|
{
|
||||||
SSL *client = NULL;
|
SSL *client = NULL, *stream = NULL;
|
||||||
|
SSL *allstreams[] = {NULL, NULL, NULL, NULL};
|
||||||
|
size_t i, thisstream = 0, numstreams = 1;
|
||||||
BIO *in;
|
BIO *in;
|
||||||
BIO *out;
|
BIO *out;
|
||||||
SSL_CTX *ctx;
|
SSL_CTX *ctx;
|
||||||
|
@ -57,6 +62,8 @@ int FuzzerTestOneInput(const uint8_t *buf, size_t len)
|
||||||
struct in_addr ina = {0};
|
struct in_addr ina = {0};
|
||||||
struct timeval tv;
|
struct timeval tv;
|
||||||
int state = HANDSHAKING;
|
int state = HANDSHAKING;
|
||||||
|
uint8_t tmp[1024];
|
||||||
|
int writelen = 0;
|
||||||
|
|
||||||
if (len == 0)
|
if (len == 0)
|
||||||
return 0;
|
return 0;
|
||||||
|
@ -104,13 +111,40 @@ int FuzzerTestOneInput(const uint8_t *buf, size_t len)
|
||||||
goto end;
|
goto end;
|
||||||
SSL_set_connect_state(client);
|
SSL_set_connect_state(client);
|
||||||
|
|
||||||
|
if (!SSL_set_incoming_stream_policy(client,
|
||||||
|
SSL_INCOMING_STREAM_POLICY_ACCEPT,
|
||||||
|
0))
|
||||||
|
goto end;
|
||||||
|
|
||||||
|
allstreams[0] = stream = client;
|
||||||
for (;;) {
|
for (;;) {
|
||||||
size_t size;
|
size_t size;
|
||||||
uint64_t nxtpktms = 0;
|
uint64_t nxtpktms = 0;
|
||||||
OSSL_TIME nxtpkt = ossl_time_zero(), nxttimeout;
|
OSSL_TIME nxtpkt = ossl_time_zero(), nxttimeout;
|
||||||
int isinf, ret;
|
int isinf, ret = 0;
|
||||||
|
|
||||||
if (len >= 2) {
|
if (len >= 2) {
|
||||||
|
if (len >= 5 && buf[0] == 0xff && buf[1] == 0xff) {
|
||||||
|
switch (buf[2]) {
|
||||||
|
case 0x00:
|
||||||
|
if (state == READING)
|
||||||
|
state = ACCEPTING_STREAM;
|
||||||
|
break;
|
||||||
|
case 0x01:
|
||||||
|
if (state == READING)
|
||||||
|
state = CREATING_STREAM;
|
||||||
|
break;
|
||||||
|
case 0x02:
|
||||||
|
if (state == READING)
|
||||||
|
state = SWAPPING_STREAM;
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
/*ignore*/
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
len -= 3;
|
||||||
|
buf += 3;
|
||||||
|
}
|
||||||
nxtpktms = buf[0] + (buf[1] << 8);
|
nxtpktms = buf[0] + (buf[1] << 8);
|
||||||
nxtpkt = ossl_time_add(fake_now, ossl_ms2time(nxtpktms));
|
nxtpkt = ossl_time_add(fake_now, ossl_ms2time(nxtpktms));
|
||||||
len -= 2;
|
len -= 2;
|
||||||
|
@ -118,32 +152,70 @@ int FuzzerTestOneInput(const uint8_t *buf, size_t len)
|
||||||
}
|
}
|
||||||
|
|
||||||
for (;;) {
|
for (;;) {
|
||||||
uint8_t tmp[1024];
|
|
||||||
int writelen = 0;
|
|
||||||
|
|
||||||
switch (state) {
|
switch (state) {
|
||||||
case HANDSHAKING:
|
case HANDSHAKING:
|
||||||
ret = SSL_do_handshake(client);
|
ret = SSL_do_handshake(stream);
|
||||||
if (ret == 1)
|
if (ret == 1)
|
||||||
state = READING;
|
state = READING;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case READING:
|
case READING:
|
||||||
ret = SSL_read(client, tmp, sizeof(tmp));
|
ret = SSL_read(stream, tmp, sizeof(tmp));
|
||||||
if (ret > 0) {
|
if (ret > 0) {
|
||||||
state = WRITING;
|
state = WRITING;
|
||||||
writelen = ret;
|
writelen = ret;
|
||||||
assert(writelen <= sizeof(tmp));
|
assert(writelen <= (int)sizeof(tmp));
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case WRITING:
|
case WRITING:
|
||||||
ret = SSL_write(client, tmp, writelen);
|
ret = SSL_write(stream, tmp, writelen);
|
||||||
if (ret > 0)
|
if (ret > 0)
|
||||||
state = READING;
|
state = READING;
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case ACCEPTING_STREAM:
|
||||||
|
state = READING;
|
||||||
|
ret = 1;
|
||||||
|
if (numstreams == OSSL_NELEM(allstreams)
|
||||||
|
|| SSL_get_accept_stream_queue_len(client) == 0)
|
||||||
|
break;
|
||||||
|
thisstream = numstreams;
|
||||||
|
stream = allstreams[numstreams++]
|
||||||
|
= SSL_accept_stream(client, 0);
|
||||||
|
if (stream == NULL)
|
||||||
|
goto end;
|
||||||
|
break;
|
||||||
|
|
||||||
|
case CREATING_STREAM:
|
||||||
|
state = READING;
|
||||||
|
ret = 1;
|
||||||
|
if (numstreams == OSSL_NELEM(allstreams))
|
||||||
|
break;
|
||||||
|
stream = SSL_new_stream(client, 0);
|
||||||
|
if (stream == NULL) {
|
||||||
|
/* Ignore, and go back to the previous stream */
|
||||||
|
stream = allstreams[thisstream];
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
thisstream = numstreams;
|
||||||
|
allstreams[numstreams++] = stream;
|
||||||
|
break;
|
||||||
|
|
||||||
|
case SWAPPING_STREAM:
|
||||||
|
state = READING;
|
||||||
|
ret = 1;
|
||||||
|
if (numstreams == 1)
|
||||||
|
break;
|
||||||
|
if (++thisstream == numstreams)
|
||||||
|
thisstream = 0;
|
||||||
|
stream = allstreams[thisstream];
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
assert(stream != NULL);
|
||||||
|
assert(thisstream < numstreams);
|
||||||
if (ret <= 0) {
|
if (ret <= 0) {
|
||||||
switch (SSL_get_error(client, ret)) {
|
switch (SSL_get_error(stream, ret)) {
|
||||||
case SSL_ERROR_WANT_READ:
|
case SSL_ERROR_WANT_READ:
|
||||||
case SSL_ERROR_WANT_WRITE:
|
case SSL_ERROR_WANT_WRITE:
|
||||||
break;
|
break;
|
||||||
|
@ -182,7 +254,8 @@ int FuzzerTestOneInput(const uint8_t *buf, size_t len)
|
||||||
buf += size + 2;
|
buf += size + 2;
|
||||||
}
|
}
|
||||||
end:
|
end:
|
||||||
SSL_free(client);
|
for (i = 0; i < numstreams; i++)
|
||||||
|
SSL_free(allstreams[i]);
|
||||||
ERR_clear_error();
|
ERR_clear_error();
|
||||||
SSL_CTX_free(ctx);
|
SSL_CTX_free(ctx);
|
||||||
BIO_ADDR_free(peer_addr);
|
BIO_ADDR_free(peer_addr);
|
||||||
|
|
Loading…
Reference in New Issue