2020-01-26 19:12:11 -03:00
// Copyright (c) 2020 The Bitcoin Core developers
// Distributed under the MIT software license, see the accompanying
// file COPYING or http://www.opensource.org/licenses/mit-license.php.
# include <test/fuzz/FuzzedDataProvider.h>
# include <test/fuzz/fuzz.h>
# include <tinyformat.h>
# include <util/strencodings.h>
2020-05-10 08:32:54 -04:00
# include <util/translation.h>
2020-01-26 19:12:11 -03:00
# include <algorithm>
# include <cstdint>
# include <string>
# include <vector>
void test_one_input ( const std : : vector < uint8_t > & buffer )
{
FuzzedDataProvider fuzzed_data_provider ( buffer . data ( ) , buffer . size ( ) ) ;
const std : : string format_string = fuzzed_data_provider . ConsumeRandomLengthString ( 64 ) ;
2020-05-10 08:32:54 -04:00
const bilingual_str bilingual_string { format_string , format_string } ;
2020-01-26 19:12:11 -03:00
const int digits_in_format_specifier = std : : count_if ( format_string . begin ( ) , format_string . end ( ) , IsDigit ) ;
// Avoid triggering the following crash bug:
// * strprintf("%987654321000000:", 1);
//
// Avoid triggering the following OOM bug:
// * strprintf("%.222222200000000$", 1.1);
//
// Upstream bug report: https://github.com/c42f/tinyformat/issues/70
2020-02-10 13:59:05 -03:00
if ( format_string . find ( ' % ' ) ! = std : : string : : npos & & digits_in_format_specifier > = 7 ) {
2020-01-26 19:12:11 -03:00
return ;
}
// Avoid triggering the following crash bug:
// * strprintf("%1$*1$*", -11111111);
//
// Upstream bug report: https://github.com/c42f/tinyformat/issues/70
2020-02-10 13:59:05 -03:00
if ( format_string . find ( ' % ' ) ! = std : : string : : npos & & format_string . find ( ' $ ' ) ! = std : : string : : npos & & format_string . find ( ' * ' ) ! = std : : string : : npos & & digits_in_format_specifier > 0 ) {
2020-01-26 19:12:11 -03:00
return ;
}
// Avoid triggering the following crash bug:
// * strprintf("%.1s", (char*)nullptr);
//
// (void)strprintf(format_string, (char*)nullptr);
//
// Upstream bug report: https://github.com/c42f/tinyformat/issues/70
try {
( void ) strprintf ( format_string , ( signed char * ) nullptr ) ;
2020-05-10 08:32:54 -04:00
( void ) tinyformat : : format ( bilingual_string , ( signed char * ) nullptr ) ;
2020-01-26 19:12:11 -03:00
} catch ( const tinyformat : : format_error & ) {
}
try {
( void ) strprintf ( format_string , ( unsigned char * ) nullptr ) ;
2020-05-10 08:32:54 -04:00
( void ) tinyformat : : format ( bilingual_string , ( unsigned char * ) nullptr ) ;
2020-01-26 19:12:11 -03:00
} catch ( const tinyformat : : format_error & ) {
}
try {
( void ) strprintf ( format_string , ( void * ) nullptr ) ;
2020-05-10 08:32:54 -04:00
( void ) tinyformat : : format ( bilingual_string , ( void * ) nullptr ) ;
2020-01-26 19:12:11 -03:00
} catch ( const tinyformat : : format_error & ) {
}
try {
( void ) strprintf ( format_string , ( bool * ) nullptr ) ;
2020-05-10 08:32:54 -04:00
( void ) tinyformat : : format ( bilingual_string , ( bool * ) nullptr ) ;
2020-01-26 19:12:11 -03:00
} catch ( const tinyformat : : format_error & ) {
}
try {
( void ) strprintf ( format_string , ( float * ) nullptr ) ;
2020-05-10 08:32:54 -04:00
( void ) tinyformat : : format ( bilingual_string , ( float * ) nullptr ) ;
2020-01-26 19:12:11 -03:00
} catch ( const tinyformat : : format_error & ) {
}
try {
( void ) strprintf ( format_string , ( double * ) nullptr ) ;
2020-05-10 08:32:54 -04:00
( void ) tinyformat : : format ( bilingual_string , ( double * ) nullptr ) ;
2020-01-26 19:12:11 -03:00
} catch ( const tinyformat : : format_error & ) {
}
try {
( void ) strprintf ( format_string , ( int16_t * ) nullptr ) ;
2020-05-10 08:32:54 -04:00
( void ) tinyformat : : format ( bilingual_string , ( int16_t * ) nullptr ) ;
2020-01-26 19:12:11 -03:00
} catch ( const tinyformat : : format_error & ) {
}
try {
( void ) strprintf ( format_string , ( uint16_t * ) nullptr ) ;
2020-05-10 08:32:54 -04:00
( void ) tinyformat : : format ( bilingual_string , ( uint16_t * ) nullptr ) ;
2020-01-26 19:12:11 -03:00
} catch ( const tinyformat : : format_error & ) {
}
try {
( void ) strprintf ( format_string , ( int32_t * ) nullptr ) ;
2020-05-10 08:32:54 -04:00
( void ) tinyformat : : format ( bilingual_string , ( int32_t * ) nullptr ) ;
2020-01-26 19:12:11 -03:00
} catch ( const tinyformat : : format_error & ) {
}
try {
( void ) strprintf ( format_string , ( uint32_t * ) nullptr ) ;
2020-05-10 08:32:54 -04:00
( void ) tinyformat : : format ( bilingual_string , ( uint32_t * ) nullptr ) ;
2020-01-26 19:12:11 -03:00
} catch ( const tinyformat : : format_error & ) {
}
try {
( void ) strprintf ( format_string , ( int64_t * ) nullptr ) ;
2020-05-10 08:32:54 -04:00
( void ) tinyformat : : format ( bilingual_string , ( int64_t * ) nullptr ) ;
2020-01-26 19:12:11 -03:00
} catch ( const tinyformat : : format_error & ) {
}
try {
( void ) strprintf ( format_string , ( uint64_t * ) nullptr ) ;
2020-05-10 08:32:54 -04:00
( void ) tinyformat : : format ( bilingual_string , ( uint64_t * ) nullptr ) ;
2020-01-26 19:12:11 -03:00
} catch ( const tinyformat : : format_error & ) {
}
try {
2020-02-10 13:59:05 -03:00
switch ( fuzzed_data_provider . ConsumeIntegralInRange ( 0 , 5 ) ) {
2020-01-26 19:12:11 -03:00
case 0 :
( void ) strprintf ( format_string , fuzzed_data_provider . ConsumeRandomLengthString ( 32 ) ) ;
2020-05-10 08:32:54 -04:00
( void ) tinyformat : : format ( bilingual_string , fuzzed_data_provider . ConsumeRandomLengthString ( 32 ) ) ;
2020-01-26 19:12:11 -03:00
break ;
case 1 :
( void ) strprintf ( format_string , fuzzed_data_provider . ConsumeRandomLengthString ( 32 ) . c_str ( ) ) ;
2020-05-10 08:32:54 -04:00
( void ) tinyformat : : format ( bilingual_string , fuzzed_data_provider . ConsumeRandomLengthString ( 32 ) . c_str ( ) ) ;
2020-01-26 19:12:11 -03:00
break ;
case 2 :
( void ) strprintf ( format_string , fuzzed_data_provider . ConsumeIntegral < signed char > ( ) ) ;
2020-05-10 08:32:54 -04:00
( void ) tinyformat : : format ( bilingual_string , fuzzed_data_provider . ConsumeIntegral < signed char > ( ) ) ;
2020-01-26 19:12:11 -03:00
break ;
case 3 :
( void ) strprintf ( format_string , fuzzed_data_provider . ConsumeIntegral < unsigned char > ( ) ) ;
2020-05-10 08:32:54 -04:00
( void ) tinyformat : : format ( bilingual_string , fuzzed_data_provider . ConsumeIntegral < unsigned char > ( ) ) ;
2020-01-26 19:12:11 -03:00
break ;
case 4 :
( void ) strprintf ( format_string , fuzzed_data_provider . ConsumeIntegral < char > ( ) ) ;
2020-05-10 08:32:54 -04:00
( void ) tinyformat : : format ( bilingual_string , fuzzed_data_provider . ConsumeIntegral < char > ( ) ) ;
2020-01-26 19:12:11 -03:00
break ;
case 5 :
( void ) strprintf ( format_string , fuzzed_data_provider . ConsumeBool ( ) ) ;
2020-05-10 08:32:54 -04:00
( void ) tinyformat : : format ( bilingual_string , fuzzed_data_provider . ConsumeBool ( ) ) ;
2020-01-26 19:12:11 -03:00
break ;
2020-02-10 13:59:05 -03:00
}
} catch ( const tinyformat : : format_error & ) {
}
if ( format_string . find ( ' % ' ) ! = std : : string : : npos & & format_string . find ( ' c ' ) ! = std : : string : : npos ) {
// Avoid triggering the following:
// * strprintf("%c", 1.31783e+38);
// tinyformat.h:244:36: runtime error: 1.31783e+38 is outside the range of representable values of type 'char'
return ;
}
if ( format_string . find ( ' % ' ) ! = std : : string : : npos & & format_string . find ( ' * ' ) ! = std : : string : : npos ) {
// Avoid triggering the following:
// * strprintf("%*", -2.33527e+38);
// tinyformat.h:283:65: runtime error: -2.33527e+38 is outside the range of representable values of type 'int'
// * strprintf("%*", -2147483648);
// tinyformat.h:763:25: runtime error: negation of -2147483648 cannot be represented in type 'int'; cast to an unsigned type to negate this value to itself
return ;
}
try {
switch ( fuzzed_data_provider . ConsumeIntegralInRange ( 0 , 7 ) ) {
case 0 :
2020-01-26 19:12:11 -03:00
( void ) strprintf ( format_string , fuzzed_data_provider . ConsumeFloatingPoint < float > ( ) ) ;
2020-05-10 08:32:54 -04:00
( void ) tinyformat : : format ( bilingual_string , fuzzed_data_provider . ConsumeFloatingPoint < float > ( ) ) ;
2020-01-26 19:12:11 -03:00
break ;
2020-02-10 13:59:05 -03:00
case 1 :
2020-01-26 19:12:11 -03:00
( void ) strprintf ( format_string , fuzzed_data_provider . ConsumeFloatingPoint < double > ( ) ) ;
2020-05-10 08:32:54 -04:00
( void ) tinyformat : : format ( bilingual_string , fuzzed_data_provider . ConsumeFloatingPoint < double > ( ) ) ;
2020-01-26 19:12:11 -03:00
break ;
2020-02-10 13:59:05 -03:00
case 2 :
2020-01-26 19:12:11 -03:00
( void ) strprintf ( format_string , fuzzed_data_provider . ConsumeIntegral < int16_t > ( ) ) ;
2020-05-10 08:32:54 -04:00
( void ) tinyformat : : format ( bilingual_string , fuzzed_data_provider . ConsumeIntegral < int16_t > ( ) ) ;
2020-01-26 19:12:11 -03:00
break ;
2020-02-10 13:59:05 -03:00
case 3 :
2020-01-26 19:12:11 -03:00
( void ) strprintf ( format_string , fuzzed_data_provider . ConsumeIntegral < uint16_t > ( ) ) ;
2020-05-10 08:32:54 -04:00
( void ) tinyformat : : format ( bilingual_string , fuzzed_data_provider . ConsumeIntegral < uint16_t > ( ) ) ;
2020-01-26 19:12:11 -03:00
break ;
2020-02-10 13:59:05 -03:00
case 4 :
2020-01-26 19:12:11 -03:00
( void ) strprintf ( format_string , fuzzed_data_provider . ConsumeIntegral < int32_t > ( ) ) ;
2020-05-10 08:32:54 -04:00
( void ) tinyformat : : format ( bilingual_string , fuzzed_data_provider . ConsumeIntegral < int32_t > ( ) ) ;
2020-01-26 19:12:11 -03:00
break ;
2020-02-10 13:59:05 -03:00
case 5 :
2020-01-26 19:12:11 -03:00
( void ) strprintf ( format_string , fuzzed_data_provider . ConsumeIntegral < uint32_t > ( ) ) ;
2020-05-10 08:32:54 -04:00
( void ) tinyformat : : format ( bilingual_string , fuzzed_data_provider . ConsumeIntegral < uint32_t > ( ) ) ;
2020-01-26 19:12:11 -03:00
break ;
2020-02-10 13:59:05 -03:00
case 6 :
2020-01-26 19:12:11 -03:00
( void ) strprintf ( format_string , fuzzed_data_provider . ConsumeIntegral < int64_t > ( ) ) ;
2020-05-10 08:32:54 -04:00
( void ) tinyformat : : format ( bilingual_string , fuzzed_data_provider . ConsumeIntegral < int64_t > ( ) ) ;
2020-01-26 19:12:11 -03:00
break ;
2020-02-10 13:59:05 -03:00
case 7 :
2020-01-26 19:12:11 -03:00
( void ) strprintf ( format_string , fuzzed_data_provider . ConsumeIntegral < uint64_t > ( ) ) ;
2020-05-10 08:32:54 -04:00
( void ) tinyformat : : format ( bilingual_string , fuzzed_data_provider . ConsumeIntegral < uint64_t > ( ) ) ;
2020-01-26 19:12:11 -03:00
break ;
}
} catch ( const tinyformat : : format_error & ) {
}
}