@@ -1085,6 +1085,22 @@ static inline u8 has_new_bits(u8* virgin_map) {
10851085}
10861086
10871087
1088+ /* A combination of classify_counts and has_new_bits. If 0 is returned, then the
1089+ * trace bits are kept as-is. Otherwise, the trace bits are overwritten with
1090+ * classified values.
1091+ *
1092+ * This accelerates the processing: in most cases, no interesting behavior
1093+ * happen, and the trace bits will be discarded soon. This function optimizes
1094+ * for such cases: one-pass scan on trace bits without modifying anything. Only
1095+ * on rare cases it fall backs to the slow path: classify_counts() first, then
1096+ * return has_new_bits(). */
1097+
1098+ static inline u8 has_new_bits_unclassified (u8 * virgin_map ) {
1099+ classify_counts (trace_bits ); // TODO
1100+ return has_new_bits (virgin_map );
1101+ }
1102+
1103+
10881104/* Get rid of shared memory (atexit handler). */
10891105
10901106static void remove_shm (void ) {
@@ -2318,7 +2334,6 @@ static u8 run_target(char** argv, u32 timeout) {
23182334 MEM_BARRIER ();
23192335
23202336 tb4 = * (u32 * )trace_bits ;
2321- classify_counts (trace_bits );
23222337
23232338 prev_timed_out = child_timed_out ;
23242339
@@ -2475,6 +2490,7 @@ static u8 calibrate_case(char** argv, struct queue_entry* q, u8* use_mem,
24752490 write_to_testcase (use_mem , q -> len );
24762491
24772492 fault = run_target (argv , use_tmout );
2493+ classify_counts (trace_bits );
24782494
24792495 /* stop_soon is set by the handler for Ctrl+C. When it's pressed,
24802496 we want to bail out quickly. */
@@ -3013,24 +3029,26 @@ static void write_crash_readme(void) {
30133029
30143030/* Check if the result of an execve() during routine fuzzing is interesting,
30153031 save or queue the input test case for further analysis if so. Returns 1 if
3016- entry is saved, 0 otherwise. */
3032+ entry is saved, 0 otherwise. When invoking this function, trace bits should
3033+ not be classified. */
30173034
30183035static u8 save_if_interesting (char * * argv , void * mem , u32 len , u8 fault ) {
30193036
30203037 u8 * fn = "" ;
30213038 u8 hnb ;
30223039 s32 fd ;
3023- u8 keeping = 0 , res ;
3040+ u8 keeping = 0 , res , classified = 0 ;
30243041
30253042 if (fault == crash_mode ) {
30263043
30273044 /* Keep only if there are new bits in the map, add to queue for
30283045 future fuzzing, etc. */
30293046
3030- if (!(hnb = has_new_bits (virgin_bits ))) {
3047+ if (!(hnb = has_new_bits_unclassified (virgin_bits ))) {
30313048 if (crash_mode ) total_crashes ++ ;
30323049 return 0 ;
30333050 }
3051+ classified = hnb ;
30343052
30353053#ifndef SIMPLE_FILES
30363054
@@ -3084,6 +3102,11 @@ static u8 save_if_interesting(char** argv, void* mem, u32 len, u8 fault) {
30843102
30853103 if (!dumb_mode ) {
30863104
3105+ if (!classified ) {
3106+ classify_counts (trace_bits );
3107+ classified = 1 ;
3108+ }
3109+
30873110 simplify_trace (trace_bits );
30883111 if (!has_new_bits (virgin_tmout )) return keeping ;
30893112
@@ -3100,6 +3123,7 @@ static u8 save_if_interesting(char** argv, void* mem, u32 len, u8 fault) {
31003123 u8 new_fault ;
31013124 write_to_testcase (mem , len );
31023125 new_fault = run_target (argv , hang_tmout );
3126+ classify_counts (trace_bits );
31033127
31043128 /* A corner case that one user reported bumping into: increasing the
31053129 timeout actually uncovers a crash. Make sure we don't discard it if
@@ -3143,6 +3167,11 @@ static u8 save_if_interesting(char** argv, void* mem, u32 len, u8 fault) {
31433167
31443168 if (!dumb_mode ) {
31453169
3170+ if (!classified ) {
3171+ classify_counts (trace_bits );
3172+ classified = 1 ;
3173+ }
3174+
31463175 simplify_trace (trace_bits );
31473176 if (!has_new_bits (virgin_crash )) return keeping ;
31483177
@@ -4413,6 +4442,7 @@ static u8 trim_case(char** argv, struct queue_entry* q, u8* in_buf) {
44134442 write_with_gap (in_buf , q -> len , remove_pos , trim_avail );
44144443
44154444 fault = run_target (argv , exec_tmout );
4445+ classify_counts (trace_bits );
44164446 trim_execs ++ ;
44174447
44184448 if (stop_soon || fault == FAULT_ERROR ) goto abort_trimming ;
@@ -4505,6 +4535,7 @@ EXP_ST u8 common_fuzz_stuff(char** argv, u8* out_buf, u32 len) {
45054535
45064536 write_to_testcase (out_buf , len );
45074537
4538+ /* Don't classify counts, leave the job to save_if_interesting. */
45084539 fault = run_target (argv , exec_tmout );
45094540
45104541 if (stop_soon ) return 1 ;
@@ -6641,6 +6672,7 @@ static void sync_fuzzers(char** argv) {
66416672 write_to_testcase (mem , st .st_size );
66426673
66436674 fault = run_target (argv , exec_tmout );
6675+ /* Don't classify counts, leave the job to save_if_interesting. */
66446676
66456677 if (stop_soon ) return ;
66466678
0 commit comments