def pack_delete(request):
    pack_id = ReqParams.one(request, 'pack_id')

    # delete fw_files_storage
    # delete fw_files
    # delete pack_files_storage
    # delete pack_files

    file_list = FwFileDO.search_files_of_pack(pack_id)
    for file in file_list:
        FwFilesStorage.delete(file['file_id'])

    # if len(file_list) > 0:
    FwFileDO.delete_many_of_pack(pack_id)

    pack_info = PackFileDO.fetch_pack(pack_id)
    PackFilesStorage.delete(pack_info['file_id'])

    PackFileDO.delete(pack_id)

    # 保存操作日志
    LogRecords.save('',
                    category='statistics',
                    action='删除固件包',
                    desc='删除指定固件包(ID=%s)的信息,' % pack_id)

    return sys_app_ok_p([])
예제 #2
0
    def remove_virtual_pack(pack_id):
        # 获取该固件包关联的所有文件 ID
        files_list = FwFileDO.get_files_of_pack(pack_id)
        file_id_list = [file_item['file_id'] for file_item in files_list]
        # 移除存储桶中的文件内容
        FwFilesStorage.delete_many(file_id_list)

        # 移除该固件包关联的所有文件记录
        FwFileDO.delete_many_of_pack(pack_id)

        # 移除固件包记录
        PackFileDO.delete(pack_id)
def pack_edit(request):
    pack_id, manufacturer, model, version = ReqParams.many(
        request, ['pack_id', 'manufacturer', 'model', 'version'],
        protocol='POST')

    PackFileDO.save_manufacturer(pack_id, manufacturer, model, version)

    # 保存操作日志
    LogRecords.save('',
                    category='statistics',
                    action='编辑指定固件包信息',
                    desc='编辑指定固件包信息 厂商 型号(ID=%s)的信息' % pack_id)

    return sys_app_ok_p([])
    def cfg_all_exec_bin_files(self, pack_id, task_id):
        # 获取本固件包所有的二进制可执行文件记录
        bin_files_list = FwFileDO.search_files_of_pack(pack_id,
                                                       FileType.EXEC_FILE)

        # 枚举每个文件,读出其文件数据,校验
        total_count = len(bin_files_list)
        for index, file_item in enumerate(bin_files_list):
            # 检查任务状态
            if MyTask.is_task_stopped(task_id):
                break

            # 保存任务执行百分比
            self._save_task_percentage(task_id, index, total_count)

            # 注意:此处一定要设置覆写,否则判定的是旧文件数据,造成判定结果错误
            file_id = file_item['file_id']
            file_path = FwFilesStorage.export(file_item['file_id'],
                                              file_name=task_id,
                                              override=True)

            is_cfg = CfgAnalyzeService.has_cfg_analyze(file_id)
            if not is_cfg:

                try:
                    # 通过 project 快速解析文件
                    angr_proj = AngrProj(file_id,
                                         progress_callback=self.run_percent_cb,
                                         task_id=task_id,
                                         cfg_mode='cfg_fast')

                    # 从 project 中提取函数列表
                    functions = FunctionParse.functions_extract(angr_proj.proj)

                    # 保存 函数列表到数据库
                    FileCacheDAO.save_functions(file_id, functions)

                    arch = str(angr_proj.proj.arch)
                    # 设置文件已完成 CFG 分析的标记
                    FwFileDO.set_cfg_analyzed(file_id, 1, arch)
                    PackFileDO.updateArch(pack_id, arch)

                except Exception as e:
                    print(e)

        # 保存任务完成状态
        MyTask.save_exec_info(task_id, 100.0)
        # 包分析完成标志
        PackFileDO.analyze_complet(pack_id, 1)
    def summary_info(content, firmware_name, firmware_md5, firmware_size,
                     pack_id, firmware_file_num, execute_file_num):

        Graphs.draw_con(content, '1 固件分析综述',
                        Graphs.text_type(18, 30, colors.black, 0))

        pack = PackFileDO.fetch_pack(pack_id)
        pack_filesystem = pack.get('filesystem')
        pack_arch = pack.get('arch')
        pack_arch = str(pack_arch).replace("<", '').replace(">", '')

        content.append(Graphs.draw_text('固件名称:' + firmware_name, '0'))
        if len(firmware_md5) > 0:
            content.append(Graphs.draw_text('固件 MD5:' + firmware_md5, '0'))
        if len(firmware_size) > 0:
            content.append(Graphs.draw_text('固件大小:' + firmware_size, '0'))
        if len(pack_filesystem) > 0:
            content.append(Graphs.draw_text('文件系统:' + pack_filesystem, '0'))
        if len(pack_arch) > 0:
            content.append(Graphs.draw_text('架构:' + pack_arch, '0'))
        content.append(
            Graphs.draw_text('固件中共有' + str(firmware_file_num) + '个文件', '0'))
        content.append(
            Graphs.draw_text('固件中共有' + str(execute_file_num) + '个可执行文件', '0'))

        content.append(Spacer(300, 10))  # 添加空白,长度300,宽10
    def fs_image_extract(self, pack_id, task_id):
        self.task_id = task_id

        image, image_file_name, fs = self.open_image()
        PackFileDO.savefs(self.pack_id, fs)

        # 任务关联文件名
        MyTask.save_exec_info_name(task_id, image_file_name)

        # 在主进程或任务中,采用预订的文件系统抽取文件
        if image.extract_files(extract_func=self.save_proc):
            # 正常处理完毕后,保存任务完成状态
            MyTask.save_exec_info(task_id, 100.0)

            # 完成抽取后,启动任务检验该包中所有可执行二进制文件的验证
            PackFiles.start_exec_bin_verify_task(self.pack_id, image_file_name)
예제 #7
0
    def remove_all_packs_by_type(pack_type):
        packs_list = PackFileDO.all_packs_type(pack_type)
        if len(packs_list) == 0:
            # 返回空任务列表
            return []

        # 固件包 ID 列表
        # pack_id_list = [pack_item['pack_id'] for pack_item in packs_list]
        tasks_list = []
        for pack_item in packs_list:
            pack_id = pack_item['pack_id']
            pack_type = pack_item['pack_type']

            # 停止所有当前包的运行任务
            PackProcessService.stop_running_tasks_of_pack(pack_id)

            if pack_type == PackType.REAL:
                # 启动移除实体固件包的任务
                task_id = PackProcessService.start_remove_packs_task(pack_id)
                tasks_list.append(task_id)
            elif pack_type == PackType.VIRTUAL:
                # 虚拟包不需要后台任务
                PackProcessService.remove_virtual_pack(pack_id)

        # 返回所有任务的列表
        return tasks_list
def check_component(pack_id, task_id):

    MyRedis.set('running_check_com_flag', True)

    # 获取本固件包所有的二进制可执行文件记录
    fw_files_list = FwFileDO.search_files_of_pack(pack_id, FileType.EXEC_FILE)
    pack_item = PackFileDO.fetch_pack(pack_id)
    process_file_name = pack_item.get('name')  # pack_item['name']
    MyTask.save_exec_info_name(task_id, process_file_name)

    # 枚举每个文件,根据文件名检索组件库(make),校验
    total_count = len(fw_files_list)
    for index, file_item in enumerate(fw_files_list):
        percentage = round(index * 100 / total_count, 1)
        MyTask.save_exec_info(task_id, percentage)

        componentinfo = MakeCOMFileDO.search_component_name(
            file_item['file_name'])
        if componentinfo is None:
            continue
        FwFileDO.set_component(file_item['file_id'], 1)
        # 相似度匹配计算,标记漏洞(version / edbid)
        fw_file_id = file_item['file_id']
        component_file_id = componentinfo['file_id']

        print(SysUtils.get_now_time())
        # 计算相似度 比较耗时 openssl计算大约两分钟
        similarity = assembly.calc_cosine_algorithm(fw_file_id,
                                                    component_file_id)
        print(SysUtils.get_now_time())

        # 相似度阈值设定: 0-100
        if similarity < utils.sys.config.g_similarity:
            print(similarity)
            continue
        # 相似度大于阈值 标记漏洞(version / edbid)
        com_file_info = PackCOMFileDO.fetch_pack(componentinfo['pack_id'])
        version = com_file_info['version']
        name = com_file_info['name']
        edb_id = com_file_info['edb_id']
        FwFileDO.set_component_extra_props(
            fw_file_id, {
                'version': version,
                'name': name,
                'edb_id': edb_id,
                'similarity': similarity
            })

    MyRedis.set('running_check_com_flag', False)

    # 保存任务完成状态
    MyTask.save_exec_info(task_id, 100.0)

    return
예제 #9
0
def _save_pack_db(fw_download_url, path_file_name, download_info, task_id):
    # todo file_type
    file_type, contents = check_file_type(path_file_name)
    file_type = FileType.PACK
    file_name = os.path.basename(path_file_name)

    # 新建或保存文件记录
    # 新的 pack ID
    pack_id = StrUtils.uuid_str()
    # 新的 pack 文件 UUID
    file_id = StrUtils.uuid_str()
    # 读取包文件内容
    contents = MyFile.read(path_file_name)
    # 保存文件记录
    PackFileDO.save(pack_id, file_id, name=file_name, file_type=file_type)
    # 保存文件内容
    PackFilesStorage.save(file_id, file_name, FileType.PACK, contents)

    # 返回固件包ID,文件ID
    return pack_id, file_id
예제 #10
0
    def _save_pack(pack_index, pack_name):
        # 获取 pack 文件的路径
        file_path = LoadDefaultPack._get_fw_file_path(pack_index)
        if file_path is None:
            return None, None

        # 文件类型
        file_type = LoadDefaultPack._get_file_type(pack_index)

        # 新建或保存文件记录
        # 新的 pack ID
        pack_id = StrUtils.uuid_str()
        # 新的 pack 文件 UUID
        file_id = StrUtils.uuid_str()
        # 读取包文件内容
        contents = MyFile.read(file_path)
        # 保存文件记录
        PackFileDO.save(pack_id, file_id, name=pack_name, file_type=file_type)
        # 保存文件内容
        PackFilesStorage.save(file_id, pack_name, file_type, contents)

        return pack_id, file_id
예제 #11
0
    def add_single_exec(file_name, file_data):
        # 新的 pack ID
        pack_id = StrUtils.uuid_str()
        # 保存虚拟包记录
        PackFileDO.save(pack_id,
                        '',
                        name=file_name,
                        pack_type=PackType.VIRTUAL,
                        file_type=FileType.PACK)

        # 新的 pack 文件 UUID
        exec_file_id = StrUtils.uuid_str()
        # 保存文件记录
        FwFileDO.save_file_item(pack_id, exec_file_id, file_name,
                                FileType.EXEC_FILE)

        # 在存储桶中保存文件数据
        # 保存文件内容
        FwFilesStorage.save(exec_file_id, file_name, file_name,
                            FileType.EXEC_FILE, file_data)

        return pack_id, exec_file_id
예제 #12
0
    def remove_pack_proc(self, pack_id, task_id):
        # 获取该固件包关联的所有文件 ID
        files_list = FwFileDO.get_files_of_pack(pack_id)
        file_id_list = [file_item['file_id'] for file_item in files_list]

        # 第一步,总进度条的 0-80%
        # 移除存储桶中,该固件包关联的所有文件
        total_count = len(file_id_list)
        for index, file_id in enumerate(file_id_list):
            if MyTask.is_task_stopped(task_id):
                return
            self._save_task_percentage(task_id, index, total_count, 80.0)
            FwFilesStorage.delete(file_id)

            # print('delete {} of {}'.format(index, total_count))
            # time.sleep(2)
        # FwFilesStorage.delete_many(file_id_list)

        # 第二步,总进度条的 80-85%
        # 移除存储桶中,固件包自身文件
        MyTask.save_task_percentage(task_id, 80.0)
        pack_item = PackFileDO.fetch_pack(pack_id)
        pack_file_id = pack_item['file_id']
        PackFilesStorage.delete(pack_file_id)

        # 第三步,总进度条的 85-95%
        # 移除该固件包关联的所有文件记录
        MyTask.save_task_percentage(task_id, 85.0)
        FwFileDO.delete_many_of_pack(pack_id)

        # 第四步,总进度条的 95-100%
        # 移除该固件包自身记录
        MyTask.save_task_percentage(task_id, 95.0)
        PackFileDO.delete(pack_id)

        # 完成任务
        MyTask.save_task_percentage(task_id, 100.0)
def all_packs_info(request):
    # 所有包的基本信息
    packs_list = PackFileDO.all_packs()
    info_list = []
    for pack in packs_list:
        # 各个包的所含文件信息
        # 各个包的提取任务和分析任务状态
        pack_id = pack['pack_id']
        pack_service = PackInfoService(pack_id, pack)
        pack = pack_service.pack_summary()

        info_list.append(pack)

    # 保存操作日志
    LogRecords.save('',
                    category='statistics',
                    action='查询所有包信息',
                    desc='查询所有固件包的信息,统计其文件数量,查询任务信息')

    return sys_app_ok_p(info_list)
예제 #14
0
 def __init__(self, pack_id, pack_info=None):
     self.pack_id = pack_id
     if pack_info is None:
         pack_info = PackFileDO.fetch_pack(pack_id)
     self.pack_info = pack_info