You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何检查大二进制文件是否连续包含小文件?求代码修复方案

看起来你的朴素字符串匹配逻辑存在几个可能导致误判的问题,我来帮你分析并修复:

可能的误判原因

  1. 有符号字符的比较问题:二进制文件中包含0x80到0xFF的字节时,用signed char存储会被解析为负数,和病毒签名中的字节(如果是无符号读取的)比较时可能出现错误的相等判断,反之亦然,导致错误匹配。
  2. 内存越界访问:原循环条件是i < len,当i接近len时,即使剩下的字符数不足virusLen,循环仍会继续,可能访问到currentFileString数组之外的内存区域。如果这些越界内存的内容刚好和病毒签名的剩余部分匹配,就会误判为true。
  3. 匹配逻辑的回溯混淆:原代码中部分匹配失败后直接重置counter为0,虽然逻辑本身没问题,但结合越界问题时更容易触发误判,且代码可读性较差。

修复后的代码

#include <stdbool.h>

bool checkIfInfected(const unsigned char* virusSignature, const unsigned char* currentFileString, size_t fileLen, size_t virusLen) {
    // 边界条件处理:签名为空或文件比签名短,直接返回false
    if (virusLen == 0 || fileLen < virusLen) {
        return false;
    }

    // 优化循环范围:只遍历到有足够字符匹配签名的位置
    for (size_t i = 0; i <= fileLen - virusLen; i++) {
        size_t matchCount = 0;
        // 检查从当前位置开始的连续字节是否完全匹配签名
        while (matchCount < virusLen && currentFileString[i + matchCount] == virusSignature[matchCount]) {
            matchCount++;
        }
        if (matchCount == virusLen) {
            return true;
        }
    }
    return false;
}

关键修复点说明

  • 改用无符号字符:将char替换为unsigned char,确保二进制字节的比较基于原始0-255的数值范围,彻底避免有符号扩展带来的错误比较。
  • 添加边界检查:提前过滤掉不可能匹配的情况(签名为空、文件过短),减少无效计算。
  • 优化循环范围:将循环上限设为fileLen - virusLen,保证每个起始位置后都有足够字符完成匹配,既提升效率,又彻底杜绝越界访问的风险。
  • 简化匹配逻辑:对每个起始位置单独检查后续字节,逻辑更清晰,也避免了原代码中counter状态残留导致的潜在问题。

额外建议

读取文件时一定要用二进制模式(比如C语言中用"rb"打开),避免文本模式下的换行符转换等操作修改文件原始二进制内容;同时要确保传递的fileLen和virusLen是文件的实际字节数,不要传递数组的总容量(如果数组有预留空间的话)。

内容的提问来源于stack exchange,提问作者alon nahmias

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.28 10:09:58