forked from openssl/openssl
-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Reviewed-by: Emilia Käsper <[email protected]>
- Loading branch information
Showing
13 changed files
with
765 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,47 @@ | ||
# I Can Haz Fuzz? | ||
|
||
Or, how to fuzz OpenSSL with libfuzzer. | ||
|
||
Starting from a vanilla+OpenSSH server Ubuntu install. | ||
|
||
Use Chrome's handy recent build of clang. Older versions may also work. | ||
|
||
$ sudo apt-get install git | ||
$ mkdir git-work | ||
$ git clone https://chromium.googlesource.com/chromium/src/tools/clang | ||
$ clang/scripts/update.py | ||
|
||
You may want to git pull and re-run the update from time to time. | ||
|
||
Update your path: | ||
|
||
$ PATH=~/third_party/llvm-build/Release+Asserts/bin/:$PATH | ||
|
||
Get and build libFuzzer (there is a git mirror at | ||
https://github.com/llvm-mirror/llvm/tree/master/lib/Fuzzer if you prefer): | ||
|
||
$ cd | ||
$ sudo apt-get install subversion | ||
$ mkdir svn-work | ||
$ cd svn-work | ||
$ svn co http://llvm.org/svn/llvm-project/llvm/trunk/lib/Fuzzer | ||
$ cd Fuzzer | ||
$ clang++ -c -g -O2 -std=c++11 *.cpp | ||
$ ar r libFuzzer.a *.o | ||
$ ranlib libFuzzer.a | ||
|
||
Configure for fuzzing: | ||
|
||
$ CC=clang ./config enable-fuzz enable-asan enable-ubsan no-shared | ||
$ sudo apt-get install make | ||
$ LDCMD=clang++ make -j | ||
$ fuzz/helper.py <fuzzer> <arguments> | ||
|
||
Where `<fuzzer>` is one of the executables in `fuzz/`. Most fuzzers do not | ||
need any command line arguments, but, for example, `asn1` needs the name of a | ||
data type. | ||
|
||
If you get a crash, you should find a corresponding input file in | ||
`fuzz/corpora/<fuzzer>-crash/`. You can reproduce the crash with | ||
|
||
$ fuzz/<fuzzer> <crashfile> |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,86 @@ | ||
/* | ||
* Copyright 2016 The OpenSSL Project Authors. All Rights Reserved. | ||
* | ||
* Licensed under the OpenSSL licenses, (the "License"); | ||
* you may not use this file except in compliance with the License. | ||
* You may obtain a copy of the License at | ||
* https://www.openssl.org/source/license.html | ||
* or in the file LICENSE in the source distribution. | ||
*/ | ||
|
||
/* | ||
* Fuzz ASN.1 parsing for various data structures. Specify which on the | ||
* command line: | ||
* | ||
* asn1 <data structure> | ||
*/ | ||
|
||
#include <stdio.h> | ||
#include <string.h> | ||
#include <openssl/asn1.h> | ||
#include <openssl/asn1t.h> | ||
#include <openssl/ec.h> | ||
#include <openssl/ocsp.h> | ||
#include <openssl/pkcs12.h> | ||
#include <openssl/ts.h> | ||
#include <openssl/x509v3.h> | ||
#include "fuzzer.h" | ||
|
||
static const ASN1_ITEM *item_type; | ||
|
||
int LLVMFuzzerInitialize(int *argc, char ***argv) { | ||
const char *cmd; | ||
OPENSSL_assert(*argc > 1); | ||
|
||
cmd = (*argv)[1]; | ||
(*argv)[1] = (*argv)[0]; | ||
++*argv; | ||
--*argc; | ||
|
||
// TODO: make this work like d2i_test.c does, once its decided what the | ||
// common scheme is! | ||
#define Y(t) if (!strcmp(cmd, #t)) item_type = ASN1_ITEM_rptr(t) | ||
#define X(t) else Y(t) | ||
|
||
Y(ASN1_SEQUENCE); | ||
X(AUTHORITY_INFO_ACCESS); | ||
X(BIGNUM); | ||
X(ECPARAMETERS); | ||
X(ECPKPARAMETERS); | ||
X(GENERAL_NAME); | ||
X(GENERAL_SUBTREE); | ||
X(NAME_CONSTRAINTS); | ||
X(OCSP_BASICRESP); | ||
X(OCSP_RESPONSE); | ||
X(PKCS12); | ||
X(PKCS12_AUTHSAFES); | ||
X(PKCS12_SAFEBAGS); | ||
X(PKCS7); | ||
X(PKCS7_ATTR_SIGN); | ||
X(PKCS7_ATTR_VERIFY); | ||
X(PKCS7_DIGEST); | ||
X(PKCS7_ENC_CONTENT); | ||
X(PKCS7_ENCRYPT); | ||
X(PKCS7_ENVELOPE); | ||
X(PKCS7_RECIP_INFO); | ||
X(PKCS7_SIGN_ENVELOPE); | ||
X(PKCS7_SIGNED); | ||
X(PKCS7_SIGNER_INFO); | ||
X(POLICY_CONSTRAINTS); | ||
X(POLICY_MAPPINGS); | ||
X(SXNET); | ||
//X(TS_RESP); want to do this, but type is hidden, however d2i exists... | ||
X(X509); | ||
X(X509_CRL); | ||
else | ||
OPENSSL_assert(!"Bad type"); | ||
|
||
return 0; | ||
} | ||
|
||
int LLVMFuzzerTestOneInput(const uint8_t *buf, size_t len) { | ||
const uint8_t *b = buf; | ||
ASN1_VALUE *o = ASN1_item_d2i(NULL, &b, len, item_type); | ||
ASN1_item_free(o, item_type); | ||
return 0; | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,29 @@ | ||
/* | ||
* Copyright 2016 The OpenSSL Project Authors. All Rights Reserved. | ||
* | ||
* Licensed under the OpenSSL licenses, (the "License"); | ||
* you may not use this file except in compliance with the License. | ||
* You may obtain a copy of the License at | ||
* https://www.openssl.org/source/license.html | ||
* or in the file LICENSE in the source distribution. | ||
*/ | ||
|
||
/* | ||
* Fuzz the parser used for dumping ASN.1 using "openssl asn1parse". | ||
*/ | ||
|
||
#include <stdio.h> | ||
#include <openssl/asn1.h> | ||
#include <openssl/x509.h> | ||
#include <openssl/x509v3.h> | ||
#include "fuzzer.h" | ||
|
||
int LLVMFuzzerTestOneInput(const uint8_t *buf, size_t len) { | ||
static BIO *bio_out; | ||
|
||
if (bio_out == NULL) | ||
bio_out = BIO_new_file("/dev/null", "w"); | ||
|
||
(void)ASN1_parse_dump(bio_out, buf, len, 0, 0); | ||
return 0; | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,91 @@ | ||
/* | ||
* Copyright 2016 The OpenSSL Project Authors. All Rights Reserved. | ||
* | ||
* Licensed under the OpenSSL licenses, (the "License"); | ||
* you may not use this file except in compliance with the License. | ||
* You may obtain a copy of the License at | ||
* https://www.openssl.org/source/license.html | ||
* or in the file LICENSE in the source distribution. | ||
*/ | ||
|
||
/* | ||
* Confirm that a^b mod c agrees when calculated cleverly vs naively, for | ||
* random a, b and c. | ||
*/ | ||
|
||
#include <stdio.h> | ||
#include <openssl/bn.h> | ||
#include "fuzzer.h" | ||
|
||
int LLVMFuzzerTestOneInput(const uint8_t *buf, size_t len) { | ||
int success = 0; | ||
static BN_CTX *ctx; | ||
static BN_MONT_CTX *mont; | ||
static BIGNUM *b1; | ||
static BIGNUM *b2; | ||
static BIGNUM *b3; | ||
static BIGNUM *b4; | ||
static BIGNUM *b5; | ||
|
||
if (ctx == NULL) { | ||
b1 = BN_new(); | ||
b2 = BN_new(); | ||
b3 = BN_new(); | ||
b4 = BN_new(); | ||
b5 = BN_new(); | ||
ctx = BN_CTX_new(); | ||
mont = BN_MONT_CTX_new(); | ||
} | ||
// Divide the input into three parts, using the values of the first two | ||
// bytes to choose lengths, which generate b1, b2 and b3. Use three bits | ||
// of the third byte to choose signs for the three numbers. | ||
size_t l1 = 0, l2 = 0, l3 = 0; | ||
int s1 = 0, s2 = 0, s3 = 0; | ||
if (len > 2) { | ||
len -= 3; | ||
l1 = (buf[0] * len) / 255; | ||
++buf; | ||
l2 = (buf[0] * (len - l1)) / 255; | ||
++buf; | ||
l3 = len - l1 - l2; | ||
|
||
s1 = buf[0] & 1; | ||
s2 = buf[0] & 2; | ||
s3 = buf[0] & 4; | ||
++buf; | ||
} | ||
OPENSSL_assert(BN_bin2bn(buf, l1, b1) == b1); | ||
BN_set_negative(b1, s1); | ||
OPENSSL_assert(BN_bin2bn(buf + l1, l2, b2) == b2); | ||
BN_set_negative(b2, s2); | ||
OPENSSL_assert(BN_bin2bn(buf + l1 + l2, l3, b3) == b3); | ||
BN_set_negative(b3, s3); | ||
|
||
// mod 0 is undefined | ||
if (BN_is_zero(b3)) { | ||
success = 1; | ||
goto done; | ||
} | ||
|
||
OPENSSL_assert(BN_mod_exp(b4, b1, b2, b3, ctx)); | ||
OPENSSL_assert(BN_mod_exp_simple(b5, b1, b2, b3, ctx)); | ||
|
||
success = BN_cmp(b4, b5) == 0; | ||
if (!success) { | ||
BN_print_fp(stdout, b1); | ||
putchar('\n'); | ||
BN_print_fp(stdout, b2); | ||
putchar('\n'); | ||
BN_print_fp(stdout, b3); | ||
putchar('\n'); | ||
BN_print_fp(stdout, b4); | ||
putchar('\n'); | ||
BN_print_fp(stdout, b5); | ||
putchar('\n'); | ||
} | ||
|
||
done: | ||
OPENSSL_assert(success); | ||
|
||
return 0; | ||
} |
Oops, something went wrong.