afl-fuzz.c 6000-6500

pull/16/head
Satori5ama 8 months ago
parent 79066db7bb
commit 4d13553f82

@ -6090,476 +6090,376 @@ skip_user_extras:
new_hit_cnt = queued_paths + unique_crashes;
stage_finds[STAGE_EXTRAS_AO] += new_hit_cnt - orig_hit_cnt;
stage_cycles[STAGE_EXTRAS_AO] += stage_max;
stage_finds[STAGE_EXTRAS_AO] += new_hit_cnt - orig_hit_cnt; // 更新STAGE_EXTRAS_AO阶段的发现计数
stage_cycles[STAGE_EXTRAS_AO] += stage_max; // 更新STAGE_EXTRAS_AO阶段的循环计数
skip_extras:
skip_extras: // 跳过额外的处理步骤
/* If we made this to here without jumping to havoc_stage or abandon_entry,
we're properly done with deterministic steps and can mark it as such
in the .state/ directory. */
in the .state/ directory. */ // 如果程序执行到这里而没有跳转到havoc_stage或abandon_entry说明我们已经完成了确定性步骤可以在.state/目录中标记为已完成
if (!queue_cur->passed_det) mark_as_det_done(queue_cur);
if (!queue_cur->passed_det) mark_as_det_done(queue_cur); // 如果当前队列项尚未标记为完成确定性步骤,则标记为完成
/****************
* RANDOM HAVOC *
****************/
****************/ // 随机破坏阶段
havoc_stage:
havoc_stage: // 随机破坏阶段的标签
stage_cur_byte = -1;
stage_cur_byte = -1; // 初始化当前字节位置为-1
/* The havoc stage mutation code is also invoked when splicing files; if the
splice_cycle variable is set, generate different descriptions and such. */
splice_cycle variable is set, generate different descriptions and such. */ // 当拼接文件时也会调用随机破坏阶段的变异代码如果splice_cycle变量被设置生成不同的描述等
if (!splice_cycle) {
if (!splice_cycle) { // 如果没有进行文件拼接
stage_name = "havoc";
stage_short = "havoc";
stage_name = "havoc"; // 设置阶段名称为"havoc"
stage_short = "havoc"; // 设置阶段简称为"havoc"
stage_max = (doing_det ? HAVOC_CYCLES_INIT : HAVOC_CYCLES) *
perf_score / havoc_div / 100;
perf_score / havoc_div / 100; // 根据是否进行确定性测试和性能评分计算最大阶段循环次数
} else {
static u8 tmp[32];
} else { // 如果进行文件拼接
perf_score = orig_perf;
static u8 tmp[32]; // 定义一个静态的32字节缓冲区
sprintf(tmp, "splice %u", splice_cycle);
stage_name = tmp;
stage_short = "splice";
stage_max = SPLICE_HAVOC * perf_score / havoc_div / 100;
perf_score = orig_perf; // 恢复原始性能评分
sprintf(tmp, "splice %u", splice_cycle); // 格式化拼接周期的描述
stage_name = tmp; // 设置阶段名称为拼接周期的描述
stage_short = "splice"; // 设置阶段简称为"splice"
stage_max = SPLICE_HAVOC * perf_score / havoc_div / 100; // 根据拼接周期的性能评分计算最大阶段循环次数
}
if (stage_max < HAVOC_MIN) stage_max = HAVOC_MIN;
if (stage_max < HAVOC_MIN) stage_max = HAVOC_MIN; // 如果最大阶段循环次数小于HAVOC_MIN则将其设置为HAVOC_MIN
temp_len = len;
temp_len = len; // 将临时长度设置为输入缓冲区的长度
orig_hit_cnt = queued_paths + unique_crashes;
orig_hit_cnt = queued_paths + unique_crashes; // 记录当前已排队的路径和唯一崩溃的总数
havoc_queued = queued_paths;
havoc_queued = queued_paths; // 记录当前已排队的路径数
/* We essentially just do several thousand runs (depending on perf_score)
where we take the input file and make random stacked tweaks. */
where we take the input file and make random stacked tweaks. */ // 我们基本上会进行数千次运行(取决于性能评分),对输入文件进行随机的堆叠调整
for (stage_cur = 0; stage_cur < stage_max; stage_cur++) {
for (stage_cur = 0; stage_cur < stage_max; stage_cur++) { // 遍历最大阶段循环次数
u32 use_stacking = 1 << (1 + UR(HAVOC_STACK_POW2));
u32 use_stacking = 1 << (1 + UR(HAVOC_STACK_POW2)); // 随机生成一个堆叠次数,用于决定每次循环中进行多少次变异
stage_cur_val = use_stacking;
for (i = 0; i < use_stacking; i++) {
stage_cur_val = use_stacking; // 记录当前堆叠次数
switch (UR(15 + ((extras_cnt + a_extras_cnt) ? 2 : 0))) {
for (i = 0; i < use_stacking; i++) { // 遍历堆叠次数
case 0:
switch (UR(15 + ((extras_cnt + a_extras_cnt) ? 2 : 0))) { // 随机选择一个变异操作
/* Flip a single bit somewhere. Spooky! */
case 0: // 操作0翻转一个随机位
FLIP_BIT(out_buf, UR(temp_len << 3));
/* Flip a single bit somewhere. Spooky! */ // 翻转某个随机位
FLIP_BIT(out_buf, UR(temp_len << 3)); // 在输出缓冲区中随机翻转一个位
break;
case 1:
/* Set byte to interesting value. */
case 1: // 操作1将随机字节设置为一个有趣的值
out_buf[UR(temp_len)] = interesting_8[UR(sizeof(interesting_8))];
/* Set byte to interesting value. */ // 将随机字节设置为一个有趣的值
out_buf[UR(temp_len)] = interesting_8[UR(sizeof(interesting_8))]; // 从interesting_8数组中随机选择一个值并设置到随机位置
break;
case 2:
/* Set word to interesting value, randomly choosing endian. */
case 2: // 操作2将随机字设置为一个有趣的值随机选择字节序
if (temp_len < 2) break;
if (UR(2)) {
*(u16*)(out_buf + UR(temp_len - 1)) =
interesting_16[UR(sizeof(interesting_16) >> 1)];
/* Set word to interesting value, randomly choosing endian. */ // 将随机字设置为一个有趣的值,随机选择字节序
if (temp_len < 2) break; // 如果缓冲区长度小于2跳过
if (UR(2)) { // 随机选择字节序
*(u16*)(out_buf + UR(temp_len - 1)) = interesting_16[UR(sizeof(interesting_16) >> 1)]; // 使用小端序设置值
} else {
*(u16*)(out_buf + UR(temp_len - 1)) = SWAP16(
interesting_16[UR(sizeof(interesting_16) >> 1)]);
*(u16*)(out_buf + UR(temp_len - 1)) = SWAP16(interesting_16[UR(sizeof(interesting_16) >> 1)]); // 使用大端序设置值
}
break;
case 3:
/* Set dword to interesting value, randomly choosing endian. */
case 3: // 操作3将随机双字设置为一个有趣的值随机选择字节序
if (temp_len < 4) break;
if (UR(2)) {
*(u32*)(out_buf + UR(temp_len - 3)) =
interesting_32[UR(sizeof(interesting_32) >> 2)];
/* Set dword to interesting value, randomly choosing endian. */ // 将随机双字设置为一个有趣的值,随机选择字节序
if (temp_len < 4) break; // 如果缓冲区长度小于4跳过
if (UR(2)) { // 随机选择字节序
*(u32*)(out_buf + UR(temp_len - 3)) = interesting_32[UR(sizeof(interesting_32) >> 2)]; // 使用小端序设置值
} else {
*(u32*)(out_buf + UR(temp_len - 3)) = SWAP32(
interesting_32[UR(sizeof(interesting_32) >> 2)]);
*(u32*)(out_buf + UR(temp_len - 3)) = SWAP32(interesting_32[UR(sizeof(interesting_32) >> 2)]); // 使用大端序设置值
}
break;
case 4:
/* Randomly subtract from byte. */
case 4: // 操作4随机减少一个字节的值
out_buf[UR(temp_len)] -= 1 + UR(ARITH_MAX);
/* Randomly subtract from byte. */ // 随机减少一个字节的值
out_buf[UR(temp_len)] -= 1 + UR(ARITH_MAX); // 随机减少一个字节的值
break;
case 5:
/* Randomly add to byte. */
case 5: // 操作5随机增加一个字节的值
out_buf[UR(temp_len)] += 1 + UR(ARITH_MAX);
/* Randomly add to byte. */ // 随机增加一个字节的值
out_buf[UR(temp_len)] += 1 + UR(ARITH_MAX); // 随机增加一个字节的值
break;
case 6:
case 6: // 操作6随机减少一个字的值随机选择字节序
/* Randomly subtract from word, random endian. */
if (temp_len < 2) break;
if (UR(2)) {
u32 pos = UR(temp_len - 1);
*(u16*)(out_buf + pos) -= 1 + UR(ARITH_MAX);
/* Randomly subtract from word, random endian. */ // 随机减少一个字的值,随机选择字节序
if (temp_len < 2) break; // 如果缓冲区长度小于2跳过
if (UR(2)) { // 随机选择字节序
u32 pos = UR(temp_len - 1); // 随机选择位置
*(u16*)(out_buf + pos) -= 1 + UR(ARITH_MAX); // 减少字的值
} else {
u32 pos = UR(temp_len - 1);
u16 num = 1 + UR(ARITH_MAX);
*(u16*)(out_buf + pos) =
SWAP16(SWAP16(*(u16*)(out_buf + pos)) - num);
u32 pos = UR(temp_len - 1); // 随机选择位置
u16 num = 1 + UR(ARITH_MAX); // 随机生成减少的值
*(u16*)(out_buf + pos) = SWAP16(SWAP16(*(u16*)(out_buf + pos)) - num); // 使用大端序减少字的值
}
break;
case 7:
/* Randomly add to word, random endian. */
if (temp_len < 2) break;
case 7: // 操作7随机增加一个字的值随机选择字节序
if (UR(2)) {
u32 pos = UR(temp_len - 1);
*(u16*)(out_buf + pos) += 1 + UR(ARITH_MAX);
/* Randomly add to word, random endian. */ // 随机增加一个字的值,随机选择字节序
if (temp_len < 2) break; // 如果缓冲区长度小于2跳过
if (UR(2)) { // 随机选择字节序
u32 pos = UR(temp_len - 1); // 随机选择位置
*(u16*)(out_buf + pos) += 1 + UR(ARITH_MAX); // 增加字的值
} else {
u32 pos = UR(temp_len - 1);
u16 num = 1 + UR(ARITH_MAX);
*(u16*)(out_buf + pos) =
SWAP16(SWAP16(*(u16*)(out_buf + pos)) + num);
u32 pos = UR(temp_len - 1); // 随机选择位置
u16 num = 1 + UR(ARITH_MAX); // 随机生成增加的值
*(u16*)(out_buf + pos) = SWAP16(SWAP16(*(u16*)(out_buf + pos)) + num); // 使用大端序增加字的值
}
break;
case 8:
/* Randomly subtract from dword, random endian. */
if (temp_len < 4) break;
if (UR(2)) {
case 8: // 操作8随机减少一个双字的值随机选择字节序
u32 pos = UR(temp_len - 3);
*(u32*)(out_buf + pos) -= 1 + UR(ARITH_MAX);
/* Randomly subtract from dword, random endian. */ // 随机减少一个双字的值,随机选择字节序
if (temp_len < 4) break; // 如果缓冲区长度小于4跳过
if (UR(2)) { // 随机选择字节序
u32 pos = UR(temp_len - 3); // 随机选择位置
*(u32*)(out_buf + pos) -= 1 + UR(ARITH_MAX); // 减少双字的值
} else {
u32 pos = UR(temp_len - 3);
u32 num = 1 + UR(ARITH_MAX);
*(u32*)(out_buf + pos) =
SWAP32(SWAP32(*(u32*)(out_buf + pos)) - num);
u32 pos = UR(temp_len - 3); // 随机选择位置
u32 num = 1 + UR(ARITH_MAX); // 随机生成减少的值
*(u32*)(out_buf + pos) = SWAP32(SWAP32(*(u32*)(out_buf + pos)) - num); // 使用大端序减少双字的值
}
break;
case 9:
/* Randomly add to dword, random endian. */
case 9: // 操作9随机增加一个双字的值随机选择字节序
if (temp_len < 4) break;
if (UR(2)) {
u32 pos = UR(temp_len - 3);
*(u32*)(out_buf + pos) += 1 + UR(ARITH_MAX);
/* Randomly add to dword, random endian. */ // 随机增加一个双字的值,随机选择字节序
if (temp_len < 4) break; // 如果缓冲区长度小于4跳过
if (UR(2)) { // 随机选择字节序
u32 pos = UR(temp_len - 3); // 随机选择位置
*(u32*)(out_buf + pos) += 1 + UR(ARITH_MAX); // 增加双字的值
} else {
u32 pos = UR(temp_len - 3);
u32 num = 1 + UR(ARITH_MAX);
*(u32*)(out_buf + pos) =
SWAP32(SWAP32(*(u32*)(out_buf + pos)) + num);
u32 pos = UR(temp_len - 3); // 随机选择位置
u32 num = 1 + UR(ARITH_MAX); // 随机生成增加的值
*(u32*)(out_buf + pos) = SWAP32(SWAP32(*(u32*)(out_buf + pos)) + num); // 使用大端序增加双字的值
}
break;
case 10:
case 10: // 操作10随机异或一个字节的值
/* Just set a random byte to a random value. Because,
why not. We use XOR with 1-255 to eliminate the
possibility of a no-op. */
out_buf[UR(temp_len)] ^= 1 + UR(255);
possibility of a no-op. */ // 随机异或一个字节的值,避免无操作
out_buf[UR(temp_len)] ^= 1 + UR(255); // 随机异或一个字节的值
break;
case 11 ... 12: {
case 11 ... 12: { // 操作11-12删除随机长度的字节
/* Delete bytes. We're making this a bit more likely
than insertion (the next option) in hopes of keeping
files reasonably small. */
u32 del_from, del_len;
if (temp_len < 2) break;
/* Don't delete too much. */
del_len = choose_block_len(temp_len - 1);
del_from = UR(temp_len - del_len + 1);
files reasonably small. */ // 删除字节,比插入操作更频繁,以保持文件大小合理
u32 del_from, del_len; // 定义删除的起始位置和长度
memmove(out_buf + del_from, out_buf + del_from + del_len,
temp_len - del_from - del_len);
if (temp_len < 2) break; // 如果缓冲区长度小于2跳过
temp_len -= del_len;
/* Don't delete too much. */ // 不要删除太多
del_len = choose_block_len(temp_len - 1); // 随机选择删除的长度
del_from = UR(temp_len - del_len + 1); // 随机选择删除的起始位置
memmove(out_buf + del_from, out_buf + del_from + del_len, temp_len - del_from - del_len); // 移动缓冲区内容以删除字节
temp_len -= del_len; // 更新缓冲区长度
break;
}
case 13:
if (temp_len + HAVOC_BLK_XL < MAX_FILE) {
/* Clone bytes (75%) or insert a block of constant bytes (25%). */
u8 actually_clone = UR(4);
u32 clone_from, clone_to, clone_len;
u8* new_buf;
if (actually_clone) {
clone_len = choose_block_len(temp_len);
clone_from = UR(temp_len - clone_len + 1);
case 13: // 操作13克隆或插入随机长度的字节
} else {
if (temp_len + HAVOC_BLK_XL < MAX_FILE) { // 如果缓冲区长度加上最大块长度小于最大文件大小
clone_len = choose_block_len(HAVOC_BLK_XL);
clone_from = 0;
/* Clone bytes (75%) or insert a block of constant bytes (25%). */ // 克隆字节75%或插入一个常量字节块25%
u8 actually_clone = UR(4); // 随机决定是否克隆
u32 clone_from, clone_to, clone_len; // 定义克隆的起始位置、目标位置和长度
u8* new_buf; // 定义新的缓冲区
if (actually_clone) { // 如果选择克隆
clone_len = choose_block_len(temp_len); // 随机选择克隆的长度
clone_from = UR(temp_len - clone_len + 1); // 随机选择克隆的起始位置
} else { // 如果选择插入常量字节块
clone_len = choose_block_len(HAVOC_BLK_XL); // 随机选择插入的长度
clone_from = 0; // 起始位置为0
}
clone_to = UR(temp_len);
clone_to = UR(temp_len); // 随机选择目标位置
new_buf = ck_alloc_nozero(temp_len + clone_len);
/* Head */
new_buf = ck_alloc_nozero(temp_len + clone_len); // 分配新的缓冲区
/* Head */ // 复制头部
memcpy(new_buf, out_buf, clone_to);
/* Inserted part */
/* Inserted part */ // 插入部分
if (actually_clone)
memcpy(new_buf + clone_to, out_buf + clone_from, clone_len);
memcpy(new_buf + clone_to, out_buf + clone_from, clone_len); // 克隆字节
else
memset(new_buf + clone_to,
UR(2) ? UR(256) : out_buf[UR(temp_len)], clone_len);
/* Tail */
memcpy(new_buf + clone_to + clone_len, out_buf + clone_to,
temp_len - clone_to);
memset(new_buf + clone_to, UR(2) ? UR(256) : out_buf[UR(temp_len)], clone_len); // 插入常量字节块
ck_free(out_buf);
out_buf = new_buf;
temp_len += clone_len;
/* Tail */ // 复制尾部
memcpy(new_buf + clone_to + clone_len, out_buf + clone_to, temp_len - clone_to);
ck_free(out_buf); // 释放旧的缓冲区
out_buf = new_buf; // 更新缓冲区指针
temp_len += clone_len; // 更新缓冲区长度
}
break;
case 14: {
case 14: { // 操作14覆盖随机长度的字节
/* Overwrite bytes with a randomly selected chunk (75%) or fixed
bytes (25%). */
u32 copy_from, copy_to, copy_len;
if (temp_len < 2) break;
bytes (25%). */ // 用随机选择的块75%或固定字节25%)覆盖字节
u32 copy_from, copy_to, copy_len; // 定义覆盖的起始位置、目标位置和长度
copy_len = choose_block_len(temp_len - 1);
if (temp_len < 2) break; // 如果缓冲区长度小于2跳过
copy_from = UR(temp_len - copy_len + 1);
copy_to = UR(temp_len - copy_len + 1);
if (UR(4)) {
copy_len = choose_block_len(temp_len - 1); // 随机选择覆盖的长度
copy_from = UR(temp_len - copy_len + 1); // 随机选择覆盖的起始位置
copy_to = UR(temp_len - copy_len + 1); // 随机选择目标位置
if (UR(4)) { // 75%的概率使用随机选择的块覆盖
if (copy_from != copy_to)
memmove(out_buf + copy_to, out_buf + copy_from, copy_len);
} else memset(out_buf + copy_to,
UR(2) ? UR(256) : out_buf[UR(temp_len)], copy_len);
memmove(out_buf + copy_to, out_buf + copy_from, copy_len); // 移动缓冲区内容以覆盖字节
} else { // 25%的概率使用固定字节覆盖
memset(out_buf + copy_to, UR(2) ? UR(256) : out_buf[UR(temp_len)], copy_len); // 使用固定字节覆盖
}
break;
}
/* Values 15 and 16 can be selected only if there are any extras
present in the dictionaries. */
case 15: {
present in the dictionaries. */ // 只有在字典中存在额外数据时才能选择操作15和16
/* Overwrite bytes with an extra. */
case 15: { // 操作15用额外数据覆盖字节
if (!extras_cnt || (a_extras_cnt && UR(2))) {
/* Overwrite bytes with an extra. */ // 用额外数据覆盖字节
if (!extras_cnt || (a_extras_cnt && UR(2))) { // 如果没有用户指定的额外数据,或者有自动检测的额外数据且随机选择
/* No user-specified extras or odds in our favor. Let's use an
auto-detected one. */
auto-detected one. */ // 使用自动检测的额外数据
u32 use_extra = UR(a_extras_cnt); // 随机选择一个自动检测的额外数据
u32 extra_len = a_extras[use_extra].len; // 获取额外数据的长度
u32 insert_at; // 定义插入位置
u32 use_extra = UR(a_extras_cnt);
u32 extra_len = a_extras[use_extra].len;
u32 insert_at;
if (extra_len > temp_len) break; // 如果额外数据长度大于缓冲区长度,跳过
if (extra_len > temp_len) break;
insert_at = UR(temp_len - extra_len + 1); // 随机选择插入位置
memcpy(out_buf + insert_at, a_extras[use_extra].data, extra_len); // 用额外数据覆盖字节
} else { // 如果有用户指定的额外数据且随机选择
insert_at = UR(temp_len - extra_len + 1);
memcpy(out_buf + insert_at, a_extras[use_extra].data, extra_len);
/* No auto extras or odds in our favor. Use the dictionary. */ // 使用用户指定的额外数据
u32 use_extra = UR(extras_cnt); // 随机选择一个用户指定的额外数据
u32 extra_len = extras[use_extra].len; // 获取额外数据的长度
u32 insert_at; // 定义插入位置
} else {
/* No auto extras or odds in our favor. Use the dictionary. */
u32 use_extra = UR(extras_cnt);
u32 extra_len = extras[use_extra].len;
u32 insert_at;
if (extra_len > temp_len) break;
insert_at = UR(temp_len - extra_len + 1);
memcpy(out_buf + insert_at, extras[use_extra].data, extra_len);
if (extra_len > temp_len) break; // 如果额外数据长度大于缓冲区长度,跳过
insert_at = UR(temp_len - extra_len + 1); // 随机选择插入位置
memcpy(out_buf + insert_at, extras[use_extra].data, extra_len); // 用额外数据覆盖字节
}
break;
}
case 16: {
case 16: { // 操作16插入额外数据
u32 use_extra, extra_len, insert_at = UR(temp_len + 1);
u8* new_buf;
u32 use_extra, extra_len, insert_at = UR(temp_len + 1); // 定义额外数据、长度和插入位置
u8* new_buf; // 定义新的缓冲区
/* Insert an extra. Do the same dice-rolling stuff as for the
previous case. */
if (!extras_cnt || (a_extras_cnt && UR(2))) {
previous case. */ // 插入额外数据与操作15类似
if (!extras_cnt || (a_extras_cnt && UR(2))) { // 如果没有用户指定的额外数据,或者有自动检测的额外数据且随机选择
use_extra = UR(a_extras_cnt);
extra_len = a_extras[use_extra].len;
use_extra = UR(a_extras_cnt); // 随机选择一个自动检测的额外数据
extra_len = a_extras[use_extra].len; // 获取额外数据的长度
if (temp_len + extra_len >= MAX_FILE) break;
if (temp_len + extra_len >= MAX_FILE) break; // 如果插入后缓冲区长度超过最大文件大小,跳过
new_buf = ck_alloc_nozero(temp_len + extra_len);
new_buf = ck_alloc_nozero(temp_len + extra_len); // 分配新的缓冲区
/* Head */
/* Head */ // 复制头部
memcpy(new_buf, out_buf, insert_at);
/* Inserted part */
memcpy(new_buf + insert_at, a_extras[use_extra].data, extra_len);
/* Inserted part */ // 插入部分
memcpy(new_buf + insert_at, a_extras[use_extra].data, extra_len); // 插入自动检测的额外数据
} else { // 如果有用户指定的额外数据且随机选择
} else {
use_extra = UR(extras_cnt); // 随机选择一个用户指定的额外数据
extra_len = extras[use_extra].len; // 获取额外数据的长度
use_extra = UR(extras_cnt);
extra_len = extras[use_extra].len;
if (temp_len + extra_len >= MAX_FILE) break; // 如果插入后缓冲区长度超过最大文件大小,跳过
if (temp_len + extra_len >= MAX_FILE) break;
new_buf = ck_alloc_nozero(temp_len + extra_len); // 分配新的缓冲区
new_buf = ck_alloc_nozero(temp_len + extra_len);
/* Head */
/* Head */ // 复制头部
memcpy(new_buf, out_buf, insert_at);
/* Inserted part */
memcpy(new_buf + insert_at, extras[use_extra].data, extra_len);
/* Inserted part */ // 插入部分
memcpy(new_buf + insert_at, extras[use_extra].data, extra_len); // 插入用户指定的额外数据
}
/* Tail */
memcpy(new_buf + insert_at + extra_len, out_buf + insert_at,
temp_len - insert_at);
ck_free(out_buf);
out_buf = new_buf;
temp_len += extra_len;
/* Tail */ // 复制尾部
memcpy(new_buf + insert_at + extra_len, out_buf + insert_at, temp_len - insert_at);
ck_free(out_buf); // 释放旧的缓冲区
out_buf = new_buf; // 更新缓冲区指针
temp_len += extra_len; // 更新缓冲区长度
break;
}
}
}
if (common_fuzz_stuff(argv, out_buf, temp_len))
goto abandon_entry;
if (common_fuzz_stuff(argv, out_buf, temp_len)) // 调用通用模糊测试函数处理当前缓冲区
goto abandon_entry; // 如果返回非零值跳转到abandon_entry
/* out_buf might have been mangled a bit, so let's restore it to its
original size and shape. */
if (temp_len < len) out_buf = ck_realloc(out_buf, len);
temp_len = len;
memcpy(out_buf, in_buf, len);
original size and shape. */ // out_buf可能已被修改因此将其恢复到原始大小和形状
if (temp_len < len) out_buf = ck_realloc(out_buf, len); // 如果缓冲区长度小于原始长度,重新分配内存
temp_len = len; // 恢复缓冲区长度
memcpy(out_buf, in_buf, len); // 将输入缓冲区内容复制回输出缓冲区
/* If we're finding new stuff, let's run for a bit longer, limits
permitting. */
if (queued_paths != havoc_queued) {
if (perf_score <= HAVOC_MAX_MULT * 100) {
stage_max *= 2;
perf_score *= 2;
permitting. */ // 如果发现了新的路径,允许在限制范围内运行更长时间
if (queued_paths != havoc_queued) { // 如果已排队的路径数发生变化
if (perf_score <= HAVOC_MAX_MULT * 100) { // 如果性能评分小于等于HAVOC_MAX_MULT * 100
stage_max *= 2; // 将最大阶段循环次数翻倍
perf_score *= 2; // 将性能评分翻倍
}
havoc_queued = queued_paths;
havoc_queued = queued_paths; // 更新已排队的路径数
}
}
new_hit_cnt = queued_paths + unique_crashes;
new_hit_cnt = queued_paths + unique_crashes; // 计算新的命中计数
if (!splice_cycle) {
stage_finds[STAGE_HAVOC] += new_hit_cnt - orig_hit_cnt;
stage_cycles[STAGE_HAVOC] += stage_max;
} else {
stage_finds[STAGE_SPLICE] += new_hit_cnt - orig_hit_cnt;
stage_cycles[STAGE_SPLICE] += stage_max;
if (!splice_cycle) { // 如果没有进行文件拼接
stage_finds[STAGE_HAVOC] += new_hit_cnt - orig_hit_cnt; // 更新HAVOC阶段的发现计数
stage_cycles[STAGE_HAVOC] += stage_max; // 更新HAVOC阶段的循环计数
} else { // 如果进行了文件拼接
stage_finds[STAGE_SPLICE] += new_hit_cnt - orig_hit_cnt; // 更新SPLICE阶段的发现计数
stage_cycles[STAGE_SPLICE] += stage_max; // 更新SPLICE阶段的循环计数
}
#ifndef IGNORE_FINDS
#ifndef IGNORE_FINDS // 如果没有定义IGNORE_FINDS
/************
* SPLICING *

Loading…
Cancel
Save