diff --git a/libclamav/bytecode.c b/libclamav/bytecode.c index 22d752291..acfe1c88d 100644 --- a/libclamav/bytecode.c +++ b/libclamav/bytecode.c @@ -1747,9 +1747,9 @@ int cli_bytecode_runhook(cli_ctx *cctx, const struct cl_engine *engine, struct c return CL_CLEAN; } -int cli_bytecode_context_setpe(struct cli_bc_ctx *ctx, const struct cli_pe_hook_data *data) +int cli_bytecode_context_setpe(struct cli_bc_ctx *ctx, const struct cli_pe_hook_data *data, const struct cli_exe_section *sections) { - ctx->hooks.exeinfo = &data->exe_info; + ctx->sections = sections; ctx->hooks.pedata = data; return 0; } diff --git a/libclamav/bytecode.h b/libclamav/bytecode.h index f22966d0c..2f1b52c0c 100644 --- a/libclamav/bytecode.h +++ b/libclamav/bytecode.h @@ -75,6 +75,7 @@ struct cli_all_bc { }; struct cli_pe_hook_data; +struct cli_exe_section; struct cli_bc_ctx *cli_bytecode_context_alloc(void); /* FIXME: we can't include others.h because others.h includes us...*/ void cli_bytecode_context_setctx(struct cli_bc_ctx *ctx, void *cctx); @@ -82,7 +83,7 @@ int cli_bytecode_context_setfuncid(struct cli_bc_ctx *ctx, const struct cli_bc * int cli_bytecode_context_setparam_int(struct cli_bc_ctx *ctx, unsigned i, uint64_t c); int cli_bytecode_context_setparam_ptr(struct cli_bc_ctx *ctx, unsigned i, void *data, unsigned datalen); int cli_bytecode_context_setfile(struct cli_bc_ctx *ctx, fmap_t *map); -int cli_bytecode_context_setpe(struct cli_bc_ctx *ctx, const struct cli_pe_hook_data *data); +int cli_bytecode_context_setpe(struct cli_bc_ctx *ctx, const struct cli_pe_hook_data *data, const struct cli_exe_section *sections); int cli_bytecode_context_clear(struct cli_bc_ctx *ctx); /* returns file descriptor, sets tempfile. Caller takes ownership, and is * responsible for freeing/unlinking */ diff --git a/libclamav/bytecode_api.c b/libclamav/bytecode_api.c index 6a444e882..e60fc1a7a 100644 --- a/libclamav/bytecode_api.c +++ b/libclamav/bytecode_api.c @@ -42,11 +42,6 @@ #include "pe.h" #include "disasm.h" -uint32_t cli_bcapi_test0(struct cli_bc_ctx *ctx, struct foo* s, uint32_t u) -{ - return (s && s->nxt == s && u == 0xdeadbeef) ? 0x12345678 : 0x55; -} - uint32_t cli_bcapi_test1(struct cli_bc_ctx *ctx, uint32_t a, uint32_t b) { return (a==0xf00dbeef && b==0xbeeff00d) ? 0x12345678 : 0x55; @@ -273,7 +268,7 @@ uint32_t cli_bcapi_pe_rawaddr(struct cli_bc_ctx *ctx, uint32_t rva) uint32_t ret; int err = 0; const struct cli_pe_hook_data *pe = ctx->hooks.pedata; - ret = cli_rawaddr(rva, pe->exe_info.section, pe->exe_info.nsections, &err, + ret = cli_rawaddr(rva, ctx->sections, pe->nsections, &err, ctx->file_size, pe->hdr_size); if (err) return PE_INVALID_RVA; @@ -355,3 +350,11 @@ uint8_t* cli_bcapi_malloc(struct cli_bc_ctx *ctx, uint32_t size) #endif } +int32_t cli_bcapi_get_pe_section(struct cli_bc_ctx *ctx, struct cli_exe_section* section, uint32_t num) +{ + if (num < ctx->hooks.pedata->nsections) { + memcpy(section, &ctx->sections[num], sizeof(*section)); + return 0; + } + return -1; +} diff --git a/libclamav/bytecode_api.h b/libclamav/bytecode_api.h index 34ba4d717..88924538d 100644 --- a/libclamav/bytecode_api.h +++ b/libclamav/bytecode_api.h @@ -40,10 +40,6 @@ struct DISASM_RESULT; #endif -struct foo { - struct foo *nxt; -}; - /** Bytecode trigger kind */ enum BytecodeKind { /** generic bytecode, not tied a specific hook */ @@ -66,8 +62,6 @@ enum { PE_INVALID_RVA = 0xFFFFFFFF }; * access it. * */ extern const uint32_t __clambc_match_counts[64]; -/** Executable info, if this is a PE hook */ -extern const struct cli_exe_info __clambc_exeinfo; /** PE data, if this is a PE hook */ extern const struct cli_pe_hook_data __clambc_pedata; /** File size (max 4G) */ @@ -76,7 +70,6 @@ extern const uint32_t __clambc_filesize[1]; /** Kind of the bytecode */ const uint16_t __clambc_kind; -uint32_t test0(struct foo*, uint32_t); uint32_t test1(uint32_t, uint32_t); /** @@ -197,5 +190,7 @@ void* malloc(uint32_t size); uint32_t test2(uint32_t a); +int32_t get_pe_section(struct cli_exe_section *section, uint32_t num); + #endif #endif diff --git a/libclamav/bytecode_api_decl.c b/libclamav/bytecode_api_decl.c index 8ca0212a4..0837ab5d8 100644 --- a/libclamav/bytecode_api_decl.c +++ b/libclamav/bytecode_api_decl.c @@ -33,7 +33,6 @@ #include "bytecode_priv.h" #include -uint32_t cli_bcapi_test0(struct cli_bc_ctx *ctx, struct foo*, uint32_t); uint32_t cli_bcapi_test1(struct cli_bc_ctx *ctx, uint32_t, uint32_t); int32_t cli_bcapi_read(struct cli_bc_ctx *ctx, uint8_t*, int32_t); int32_t cli_bcapi_write(struct cli_bc_ctx *ctx, uint8_t*, int32_t); @@ -53,107 +52,90 @@ int32_t cli_bcapi_file_find(struct cli_bc_ctx *ctx, const uint8_t*, uint32_t); int32_t cli_bcapi_file_byteat(struct cli_bc_ctx *ctx, uint32_t); uint8_t* cli_bcapi_malloc(struct cli_bc_ctx *ctx, uint32_t); uint32_t cli_bcapi_test2(struct cli_bc_ctx *ctx, uint32_t); +int32_t cli_bcapi_get_pe_section(struct cli_bc_ctx *ctx, struct cli_exe_section*, uint32_t); const struct cli_apiglobal cli_globals[] = { /* Bytecode globals BEGIN */ {"__clambc_kind", GLOBAL_KIND, 16, ((char*)&((struct cli_bc_ctx*)0)->hooks.kind - (char*)NULL)}, - {"__clambc_match_counts", GLOBAL_MATCH_COUNTS, 84, + {"__clambc_match_counts", GLOBAL_MATCH_COUNTS, 76, ((char*)&((struct cli_bc_ctx*)0)->hooks.match_counts - (char*)NULL)}, - {"__clambc_filesize", GLOBAL_FILESIZE, 83, + {"__clambc_filesize", GLOBAL_FILESIZE, 75, ((char*)&((struct cli_bc_ctx*)0)->hooks.filesize - (char*)NULL)}, - {"__clambc_exeinfo", GLOBAL_EXEINFO, 79, - ((char*)&((struct cli_bc_ctx*)0)->hooks.exeinfo - (char*)NULL)}, {"__clambc_pedata", GLOBAL_PEDATA, 69, ((char*)&((struct cli_bc_ctx*)0)->hooks.pedata - (char*)NULL)} /* Bytecode globals END */ }; const unsigned cli_apicall_maxglobal = _LAST_GLOBAL-1; -static uint16_t cli_tmp0[]={79, 77, 75, 72, 70, 32, 32, 32, 32, 8, 65}; +static uint16_t cli_tmp0[]={32, 32, 16, 74, 73, 72, 70, 32, 32, 32, 32}; static uint16_t cli_tmp1[]={71}; static uint16_t cli_tmp2[]={32, 32}; -static uint16_t cli_tmp3[]={73}; -static uint16_t cli_tmp4[]={16, 8, 8, 32, 32, 32, 32, 32, 64, 32, 32, 16, 16, 16, 16, 16, 16, 32, 32, 32, 32, 16, 16, 64, 64, 64, 64, 32, 32, 74}; -static uint16_t cli_tmp5[]={71}; -static uint16_t cli_tmp6[]={76}; -static uint16_t cli_tmp7[]={16, 8, 8, 32, 32, 32, 32, 32, 32, 32, 32, 32, 16, 16, 16, 16, 16, 16, 32, 32, 32, 32, 16, 16, 32, 32, 32, 32, 32, 32, 74}; -static uint16_t cli_tmp8[]={78}; -static uint16_t cli_tmp9[]={32, 16, 16, 32, 32, 32, 16, 16}; -static uint16_t cli_tmp10[]={81, 32, 32, 16, 80}; -static uint16_t cli_tmp11[]={8}; -static uint16_t cli_tmp12[]={82}; -static uint16_t cli_tmp13[]={32, 32, 32, 32, 32, 32, 32, 32, 32}; -static uint16_t cli_tmp14[]={32}; -static uint16_t cli_tmp15[]={32}; -static uint16_t cli_tmp16[]={32, 32}; -static uint16_t cli_tmp17[]={65, 32}; -static uint16_t cli_tmp18[]={32, 65, 32}; -static uint16_t cli_tmp19[]={32, 89, 32}; -static uint16_t cli_tmp20[]={90}; -static uint16_t cli_tmp21[]={16, 8, 8, 8, 92, 91}; -static uint16_t cli_tmp22[]={8}; -static uint16_t cli_tmp23[]={93}; -static uint16_t cli_tmp24[]={8}; -static uint16_t cli_tmp25[]={32, 32, 32}; -static uint16_t cli_tmp26[]={32, 96, 32}; -static uint16_t cli_tmp27[]={97}; -static uint16_t cli_tmp28[]={96}; +static uint16_t cli_tmp3[]={16, 8, 8, 32, 32, 32, 32, 32, 64, 32, 32, 16, 16, 16, 16, 16, 16, 32, 32, 32, 32, 16, 16, 64, 64, 64, 64, 32, 32, 70}; +static uint16_t cli_tmp4[]={16, 8, 8, 32, 32, 32, 32, 32, 32, 32, 32, 32, 16, 16, 16, 16, 16, 16, 32, 32, 32, 32, 16, 16, 32, 32, 32, 32, 32, 32, 70}; +static uint16_t cli_tmp5[]={32, 16, 16, 32, 32, 32, 16, 16}; +static uint16_t cli_tmp6[]={32}; +static uint16_t cli_tmp7[]={32}; +static uint16_t cli_tmp8[]={32, 78, 32}; +static uint16_t cli_tmp9[]={79}; +static uint16_t cli_tmp10[]={32, 32, 32, 32, 32, 32, 32, 32, 32}; +static uint16_t cli_tmp11[]={32, 32}; +static uint16_t cli_tmp12[]={65, 32}; +static uint16_t cli_tmp13[]={32, 65, 32}; +static uint16_t cli_tmp14[]={32, 84, 32}; +static uint16_t cli_tmp15[]={85}; +static uint16_t cli_tmp16[]={16, 8, 8, 8, 87, 86}; +static uint16_t cli_tmp17[]={8}; +static uint16_t cli_tmp18[]={88}; +static uint16_t cli_tmp19[]={8}; +static uint16_t cli_tmp20[]={32, 32, 32}; const struct cli_bc_type cli_apicall_types[]={ {DStructType, cli_tmp0, 11, 0, 0}, - {DPointerType, cli_tmp1, 1, 0, 0}, + {DArrayType, cli_tmp1, 16, 0, 0}, {DStructType, cli_tmp2, 2, 0, 0}, - {DPointerType, cli_tmp3, 1, 0, 0}, - {DStructType, cli_tmp4, 30, 0, 0}, - {DArrayType, cli_tmp5, 16, 0, 0}, - {DPointerType, cli_tmp6, 1, 0, 0}, - {DStructType, cli_tmp7, 31, 0, 0}, - {DPointerType, cli_tmp8, 1, 0, 0}, - {DStructType, cli_tmp9, 8, 0, 0}, - {DStructType, cli_tmp10, 5, 0, 0}, - {DPointerType, cli_tmp11, 1, 0, 0}, - {DPointerType, cli_tmp12, 1, 0, 0}, - {DStructType, cli_tmp13, 9, 0, 0}, - {DArrayType, cli_tmp14, 1, 0, 0}, - {DArrayType, cli_tmp15, 64, 0, 0}, - {DFunctionType, cli_tmp16, 2, 0, 0}, - {DFunctionType, cli_tmp17, 2, 0, 0}, - {DFunctionType, cli_tmp18, 3, 0, 0}, - {DFunctionType, cli_tmp19, 3, 0, 0}, - {DPointerType, cli_tmp20, 1, 0, 0}, - {DStructType, cli_tmp21, 6, 0, 0}, - {DArrayType, cli_tmp22, 29, 0, 0}, - {DArrayType, cli_tmp23, 3, 0, 0}, - {DArrayType, cli_tmp24, 10, 0, 0}, - {DFunctionType, cli_tmp25, 3, 0, 0}, - {DFunctionType, cli_tmp26, 3, 0, 0}, - {DPointerType, cli_tmp27, 1, 0, 0}, - {DStructType, cli_tmp28, 1, 0, 0} + {DStructType, cli_tmp3, 30, 0, 0}, + {DStructType, cli_tmp4, 31, 0, 0}, + {DStructType, cli_tmp5, 8, 0, 0}, + {DArrayType, cli_tmp6, 1, 0, 0}, + {DArrayType, cli_tmp7, 64, 0, 0}, + {DFunctionType, cli_tmp8, 3, 0, 0}, + {DPointerType, cli_tmp9, 1, 0, 0}, + {DStructType, cli_tmp10, 9, 0, 0}, + {DFunctionType, cli_tmp11, 2, 0, 0}, + {DFunctionType, cli_tmp12, 2, 0, 0}, + {DFunctionType, cli_tmp13, 3, 0, 0}, + {DFunctionType, cli_tmp14, 3, 0, 0}, + {DPointerType, cli_tmp15, 1, 0, 0}, + {DStructType, cli_tmp16, 6, 0, 0}, + {DArrayType, cli_tmp17, 29, 0, 0}, + {DArrayType, cli_tmp18, 3, 0, 0}, + {DArrayType, cli_tmp19, 10, 0, 0}, + {DFunctionType, cli_tmp20, 3, 0, 0} }; const unsigned cli_apicall_maxtypes=sizeof(cli_apicall_types)/sizeof(cli_apicall_types[0]); const struct cli_apicall cli_apicalls[]={ /* Bytecode APIcalls BEGIN */ - {"test0", 26, 0, 1}, - {"test1", 25, 0, 0}, - {"read", 18, 1, 1}, - {"write", 18, 2, 1}, - {"seek", 25, 1, 0}, - {"setvirusname", 18, 3, 1}, - {"debug_print_str", 18, 4, 1}, - {"debug_print_uint", 16, 0, 2}, - {"disasm_x86", 19, 5, 1}, - {"trace_directory", 18, 6, 1}, - {"trace_scope", 18, 7, 1}, - {"trace_source", 18, 8, 1}, - {"trace_op", 18, 9, 1}, - {"trace_value", 18, 10, 1}, - {"trace_ptr", 18, 11, 1}, - {"pe_rawaddr", 16, 1, 2}, - {"file_find", 18, 12, 1}, - {"file_byteat", 16, 2, 2}, - {"malloc", 17, 0, 3}, - {"test2", 16, 3, 2} + {"test1", 20, 0, 0}, + {"read", 13, 0, 1}, + {"write", 13, 1, 1}, + {"seek", 20, 1, 0}, + {"setvirusname", 13, 2, 1}, + {"debug_print_str", 13, 3, 1}, + {"debug_print_uint", 11, 0, 2}, + {"disasm_x86", 14, 4, 1}, + {"trace_directory", 13, 5, 1}, + {"trace_scope", 13, 6, 1}, + {"trace_source", 13, 7, 1}, + {"trace_op", 13, 8, 1}, + {"trace_value", 13, 9, 1}, + {"trace_ptr", 13, 10, 1}, + {"pe_rawaddr", 11, 1, 2}, + {"file_find", 13, 11, 1}, + {"file_byteat", 11, 2, 2}, + {"malloc", 12, 0, 3}, + {"test2", 11, 3, 2}, + {"get_pe_section", 8, 12, 1} /* Bytecode APIcalls END */ }; const cli_apicall_int2 cli_apicalls0[] = { @@ -161,7 +143,6 @@ const cli_apicall_int2 cli_apicalls0[] = { (cli_apicall_int2)cli_bcapi_seek }; const cli_apicall_pointer cli_apicalls1[] = { - (cli_apicall_pointer)cli_bcapi_test0, (cli_apicall_pointer)cli_bcapi_read, (cli_apicall_pointer)cli_bcapi_write, (cli_apicall_pointer)cli_bcapi_setvirusname, @@ -173,7 +154,8 @@ const cli_apicall_pointer cli_apicalls1[] = { (cli_apicall_pointer)cli_bcapi_trace_op, (cli_apicall_pointer)cli_bcapi_trace_value, (cli_apicall_pointer)cli_bcapi_trace_ptr, - (cli_apicall_pointer)cli_bcapi_file_find + (cli_apicall_pointer)cli_bcapi_file_find, + (cli_apicall_pointer)cli_bcapi_get_pe_section }; const cli_apicall_int1 cli_apicalls2[] = { (cli_apicall_int1)cli_bcapi_debug_print_uint, diff --git a/libclamav/bytecode_api_impl.h b/libclamav/bytecode_api_impl.h index 159dc29bd..a7ef6f371 100644 --- a/libclamav/bytecode_api_impl.h +++ b/libclamav/bytecode_api_impl.h @@ -30,7 +30,6 @@ #define BYTECODE_API_IMPL_H struct cli_bc_bctx; -uint32_t cli_bcapi_test0(struct cli_bc_ctx *ctx, struct foo*, uint32_t); uint32_t cli_bcapi_test1(struct cli_bc_ctx *ctx, uint32_t, uint32_t); int32_t cli_bcapi_read(struct cli_bc_ctx *ctx, uint8_t*, int32_t); int32_t cli_bcapi_write(struct cli_bc_ctx *ctx, uint8_t*, int32_t); @@ -50,5 +49,6 @@ int32_t cli_bcapi_file_find(struct cli_bc_ctx *ctx, const uint8_t*, uint32_t); int32_t cli_bcapi_file_byteat(struct cli_bc_ctx *ctx, uint32_t); uint8_t* cli_bcapi_malloc(struct cli_bc_ctx *ctx, uint32_t); uint32_t cli_bcapi_test2(struct cli_bc_ctx *ctx, uint32_t); +int32_t cli_bcapi_get_pe_section(struct cli_bc_ctx *ctx, struct cli_exe_section*, uint32_t); #endif diff --git a/libclamav/bytecode_hooks.h b/libclamav/bytecode_hooks.h index 113ede798..3417e907c 100644 --- a/libclamav/bytecode_hooks.h +++ b/libclamav/bytecode_hooks.h @@ -33,7 +33,6 @@ struct cli_bc_hooks { const uint16_t* kind; const uint32_t* match_counts; const uint32_t* filesize; - const struct cli_exe_info* exeinfo; const struct cli_pe_hook_data* pedata; }; #endif diff --git a/libclamav/bytecode_priv.h b/libclamav/bytecode_priv.h index 2d6294d74..d0d37d7f7 100644 --- a/libclamav/bytecode_priv.h +++ b/libclamav/bytecode_priv.h @@ -130,6 +130,7 @@ struct cli_bc_ctx { fmap_t *fmap; const char *virname; struct cli_bc_hooks hooks; + const struct cli_exe_section *sections; int outfd; char *tempfile; void *ctx; diff --git a/libclamav/c++/bytecode2llvm.cpp b/libclamav/c++/bytecode2llvm.cpp index 24919c1e6..afdc28afa 100644 --- a/libclamav/c++/bytecode2llvm.cpp +++ b/libclamav/c++/bytecode2llvm.cpp @@ -453,23 +453,20 @@ private: Constant *buildConstant(const Type *Ty, uint64_t *components, unsigned &c) { if (const PointerType *PTy = dyn_cast(Ty)) { - Value *idxs[2] = { - ConstantInt::get(Type::getInt32Ty(Context), 0), - ConstantInt::get(Type::getInt32Ty(Context), components[c++]) + + Value *idxs[1] = { + ConstantInt::get(Type::getInt64Ty(Context), components[c++]) }; unsigned idx = components[c++]; if (!idx) return ConstantPointerNull::get(PTy); assert(idx < globals.size()); GlobalVariable *GV = cast(globals[idx]); - const Type *GTy = GetElementPtrInst::getIndexedType(GV->getType(), idxs, 2); - if (!GTy) { - errs() << "Type mismatch for GEP: " << *PTy->getElementType() << - "; base is " << *GV << "\n"; - llvm_report_error("(libclamav) Type mismatch converting constant"); - } + const Type *IP8Ty = PointerType::getUnqual(Type::getInt8Ty(Ty->getContext())); + Constant *C = ConstantExpr::getPointerCast(GV, IP8Ty); + //TODO: check constant bounds here return ConstantExpr::getPointerCast( - ConstantExpr::getInBoundsGetElementPtr(GV, idxs, 2), + ConstantExpr::getInBoundsGetElementPtr(C, idxs, 1), PTy); } if (isa(Ty)) { @@ -520,7 +517,9 @@ public: << " expected type: " << *ETy; if (Ty) errs() << " actual type: " << *Ty; - errs() << " base: " << *Base << " indices: "; + errs() << " base: " << *Base << ";"; + Base->getType()->dump(); + errs() << "\n indices: "; for (InputIterator I=Start; I != End; I++) { errs() << **I << ", "; } @@ -649,6 +648,7 @@ public: Functions[j]->setCallingConv(CallingConv::Fast); } const Type *I32Ty = Type::getInt32Ty(Context); + const Type *I64Ty = Type::getInt64Ty(Context); for (unsigned j=0;jnum_func;j++) { PrettyStackTraceString CrashInfo("Generate LLVM IR"); const struct cli_bc_func *func = &bc->funcs[j]; @@ -696,18 +696,21 @@ public: Ty = PointerType::getUnqual(PointerType::getUnqual(Ty)); Value *Cast = Builder.CreateBitCast(GEP, Ty); Value *SpecialGV = Builder.CreateLoad(Cast); + const Type *IP8Ty = Type::getInt8Ty(Context); + IP8Ty = PointerType::getUnqual(IP8Ty); + SpecialGV = Builder.CreateBitCast(SpecialGV, IP8Ty); SpecialGV->setName("g"+Twine(g-_FIRST_GLOBAL)+"_"); Value *C[] = { - ConstantInt::get(Type::getInt32Ty(Context), 0), ConstantInt::get(Type::getInt32Ty(Context), bc->globals[i][0]) }; - globals[i] = createGEP(SpecialGV, 0, C, C+2); + globals[i] = createGEP(SpecialGV, 0, C, C+1); if (!globals[i]) { errs() << i << ":" << g << ":" << bc->globals[i][0] <<"\n"; Ty->dump(); llvm_report_error("(libclamav) unable to create fake global"); } - else if(GetElementPtrInst *GI = dyn_cast(globals[i])) { + globals[i] = Builder.CreateBitCast(globals[i], Ty); + if(GetElementPtrInst *GI = dyn_cast(globals[i])) { GI->setIsInBounds(true); GI->setName("geped"+Twine(i)+"_"); } @@ -948,7 +951,8 @@ public: { const Type *SrcTy = mapType(inst->u.three[0]); Value *V = convertOperand(func, SrcTy, inst->u.three[1]); - Value *Op = convertOperand(func, I32Ty, inst->u.three[2]); + Value *Op = convertOperand(func, I64Ty, inst->u.three[2]); + Op = Builder.CreateTrunc(Op, I32Ty); if (!createGEP(inst->dest, V, &Op, &Op+1)) return false; break; @@ -959,7 +963,8 @@ public: Ops[0] = ConstantInt::get(Type::getInt32Ty(Context), 0); const Type *SrcTy = mapType(inst->u.three[0]); Value *V = convertOperand(func, SrcTy, inst->u.three[1]); - Ops[1] = convertOperand(func, I32Ty, inst->u.three[2]); + Ops[1] = convertOperand(func, I64Ty, inst->u.three[2]); + Ops[1] = Builder.CreateTrunc(Ops[1], I32Ty); if (!createGEP(inst->dest, V, Ops, Ops+2)) return false; break; @@ -970,8 +975,11 @@ public: assert(inst->u.ops.numOps > 2); const Type *SrcTy = mapType(inst->u.ops.ops[0]); Value *V = convertOperand(func, SrcTy, inst->u.ops.ops[1]); - for (unsigned a=2;au.ops.numOps;a++) - Idxs.push_back(convertOperand(func, I32Ty, inst->u.ops.ops[a])); + for (unsigned a=2;au.ops.numOps;a++) { + Value *Op = convertOperand(func, I64Ty, inst->u.ops.ops[a]); + Op = Builder.CreateTrunc(Op, I32Ty); + Idxs.push_back(Op); + } if (!createGEP(inst->dest, V, Idxs.begin(), Idxs.end())) return false; break; diff --git a/libclamav/clambc.h b/libclamav/clambc.h index 0fd643655..8b4200c69 100644 --- a/libclamav/clambc.h +++ b/libclamav/clambc.h @@ -31,7 +31,7 @@ struct bytecode_metadata { unsigned targetExclude; }; -#define BC_FUNC_LEVEL 5 +#define BC_FUNC_LEVEL 6 #define BC_HEADER "ClamBC" enum bc_opcode { @@ -121,7 +121,6 @@ enum bc_global { GLOBAL_MATCH_COUNTS = 0x8000, GLOBAL_KIND, GLOBAL_VIRUSNAMES, - GLOBAL_EXEINFO, GLOBAL_PEDATA, GLOBAL_FILESIZE, _LAST_GLOBAL diff --git a/libclamav/pe.c b/libclamav/pe.c index 899c6afcc..a49819e22 100644 --- a/libclamav/pe.c +++ b/libclamav/pe.c @@ -2236,19 +2236,18 @@ int cli_scanpe(cli_ctx *ctx, icon_groupset *iconset) cli_errmsg("cli_scanpe: can't allocate memory for bc_ctx\n"); return CL_EMEM; } - pedata.exe_info.section = exe_sections; - pedata.exe_info.nsections = nsections; - pedata.exe_info.ep = ep; - pedata.exe_info.offset = 0; - pedata.file_hdr = &file_hdr; - pedata.opt32 = &pe_opt.opt32; - pedata.opt64 = &pe_opt.opt64; - pedata.dirs = dirs; + pedata.nsections = nsections; + pedata.ep = ep; + pedata.offset = 0; + memcpy(&pedata.file_hdr, &file_hdr, sizeof(file_hdr)); + memcpy(&pedata.opt32, &pe_opt.opt32, sizeof(pe_opt.opt32)); + memcpy(&pedata.opt64, &pe_opt.opt64, sizeof(pe_opt.opt64)); + memcpy(&pedata.dirs, dirs, sizeof(pedata.dirs)); pedata.e_lfanew = e_lfanew; pedata.overlays = overlays; pedata.overlays_sz = fsize - overlays; pedata.hdr_size = hdr_size; - cli_bytecode_context_setpe(bc_ctx, &pedata); + cli_bytecode_context_setpe(bc_ctx, &pedata, exe_sections); cli_bytecode_context_setctx(bc_ctx, ctx); ret = cli_bytecode_runhook(ctx, ctx->engine, bc_ctx, BC_PE_UNPACKER, map, ctx->virname); switch (ret) { diff --git a/libclamav/pe.h b/libclamav/pe.h index 261cfadf1..87aec1b13 100644 --- a/libclamav/pe.h +++ b/libclamav/pe.h @@ -137,18 +137,17 @@ struct pe_image_section_hdr { /** Data for the bytecode PE hook */ struct cli_pe_hook_data { - struct cli_exe_info exe_info; - struct pe_image_file_hdr *file_hdr; - struct pe_image_optional_hdr32 *opt32; - struct pe_image_optional_hdr64 *opt64; - struct pe_image_data_dir *dirs; - uint32_t e_lfanew;/**< address of new exe header */ - uint32_t overlays;/**< number of overlays */ - int32_t overlays_sz;/**< size of overlays */ - uint32_t hdr_size;/**< internally needed by rawaddr */ - /* FIXME: these should not be necessary (they are for now) */ - uint8_t dummyn; - uint8_t *dummy EBOUNDS(dummyn); + uint32_t offset; + uint32_t ep; + uint16_t nsections; + struct pe_image_file_hdr file_hdr; + struct pe_image_optional_hdr32 opt32; + struct pe_image_optional_hdr64 opt64; + struct pe_image_data_dir dirs[16]; + uint32_t e_lfanew;/**< address of new exe header */ + uint32_t overlays;/**< number of overlays */ + int32_t overlays_sz;/**< size of overlays */ + uint32_t hdr_size;/**< internally needed by rawaddr */ }; int cli_scanpe(cli_ctx *ctx, icon_groupset *set); diff --git a/unit_tests/input/apicalls.cbc b/unit_tests/input/apicalls.cbc index f41bb1619..d86499f07 100644 --- a/unit_tests/input/apicalls.cbc +++ b/unit_tests/input/apicalls.cbc @@ -1,10 +1,10 @@ -ClamBCae`|``````|`agafp`clamcoincidencejb:82 +ClamBCafh`lifegkd|afefdfggifnf```````|bgacflfafmfbfcfmb`cnb`cacmbicmbgfafeficfcgcecff``agafp`clamcoincidencejb:82 Tedaaa`aacb`bb`bb`b -Eabaaabbfd|afdgefcgdgac`` +Eaaaaaabfd|afdgefcgdgac`` G`aa`@` A`b`bLacb`b`aa`b`b`Fadaa -Bb`b`abbabHonnkm``odHm``oonnkdaaaaeab`b`Hhgfedcbadb`baboaaaDm``odDmjnmdTcab`babE +Bb`b`abbaaHonnkm``odHm``oonnkdaaaaeab`b`Hhgfedcbadb`baboaaaDm``odDmjnmdTcab`babE Aab`bLabah`aa`b`b`Facaa Baaaaeaah`Bgaab`baboaaaDm``odDmjnmdTcab`babE Aab`bLabb`a`aa`b`b`Facaa @@ -17,3 +17,8 @@ Abb`bLacah`b`a`aa`aa`b`b`Fafac Baaabeaah`BhbaTaaabaaab Baaaceab`aaaDdcbabb`badoaacDm``odDmjnmdTcab`bad BTcab`bDmjnmdE +Sifnfdg`befnfdgbgig`gofifnfdghbibSkgSbgefdgegbgnf`bdgefcgdgachb`chgff`c`cdfbfefeffflb`b`chgbfefefffff`c`cdfib`bmcmc`b`chgacbcccdcecfcgchc`boc`b`chgff`c`cdf`bjc`b`chgdfefafdfkc +mgSifnfdg`bffofofachbegifnfdghcoedg`bafibSkgSbgefdgegbgnf`baf`bmcmc`b`chgacgc`boc`b`chgff`c`cdf`bjc`b`chgdfefafdfkcSmgSifnfdg`bffofofbchbegifnfdgacfcoedg`bafibSkgSbgefdgegbgnf`baf`bmcmc`b`chgacgcbchc`boc`b`chgff`c`cdf`bjc`b`chgdfefafdfkc +mgSifnfdg`bffofofcchbegifnfdgccbcoedg`bafibSkgSbgefdgegbgnf`baf`bmcmc`b`chgacgcbchcccic`boc`b`chgff`c`cdf`bjc`b`chgdfefafdfkcSmgSifnfdg`bffofofdchbegifnfdgfcdcoedg`bafib +kgSbgefdgegbgnf`baf`bmcmc`b`chgacgcbchcccicdc`cecacfcbcgccc`boc`b`chgff`c`cdf`bjc`b`chgdfefafdfkcSmgSifnfdg`bffofofechbegifnfdghcoedg`baflb`begifnfdgacfcoedg`bbfib +kgSbgefdgegbgnf`bhbaf`bmcmc`b`chgbchc`bfbfb`bbf`bmcmc`b`chgacbcccdcib`boc`b`chgff`c`cdf`bjc`b`chgdfefafdfkcSmgSS \ No newline at end of file diff --git a/unit_tests/input/apicalls2.cbc b/unit_tests/input/apicalls2.cbc index bedb0ca56..3354d67c7 100644 --- a/unit_tests/input/apicalls2.cbc +++ b/unit_tests/input/apicalls2.cbc @@ -1,14 +1,11 @@ -ClamBCae`|``````|`amafp`clamcoincidencejb:92 +ClamBCafh`lifegkd|afefdfggifnf```````|bgacflfafmfbfcfmb`cnb`cacmbicmbgfafeficfcgcecff``ahafp`clamcoincidencejb:66 -Tedcaabfdebedebfdaaa`aabbadb`baabb`bb`baacb`bbfdb`baacb`bb`bb`b -Ebdaadbcabid|agmfaflflfofcf``bdabjd|afdgefcgdgbc``aabkd|afdgefcgdg`c``abbld|afdgefcgdgac`` +Tedaaa`aabb`bb`baacb`bb`bb`b +Ebcaabbcabfd|afdgefcgdgbc``aabgd|afdgefcgdgac`` G`aa`@` -A`b`bLalbedabgd```b`b`aa`b`b`aa`b`b`aa`bad`aa`b`b`Fbaaaf -Bbgdaadbbfd`@d``fb`aab`bacabbabHonnkm``odHm``oonnkdaaadeab`bacHhgfedcbadTaaadaaae -Bb`baeabbaa`Honnkmjnmdaaafeab`baeHhgfedcbadTaaafabae -Bb`bagababdaDm``odaaaheab`bagDo``mdTaaahacae -BbadaiababcaAadaaajeabadai@`Taaajaead -Bb`bakabbaaai@dTcab`bDm``od +A`b`bLaeb`b`aa`b`b`aa`b`b`Fahac +Bb`b`abbaaHonnkm``odHm``oonnkdaaaaeab`b`HhgfedcbadTaaaaaaab +Bb`babababcaDm``odaaaceab`babDo``mdb`badoaacDm``odDmjnmdTcab`bad BTcab`bDmjnmdE Aab`bLabah`aa`b`b`Facaa Baaaaeaah`Bgaab`baboaaaDm``odDmjnmdTcab`babE @@ -22,3 +19,9 @@ Abb`bLacah`b`a`aa`aa`b`b`Fafac Baaabeaah`BhbaTaaabaaab Baaaceab`aaaDdcbabb`badoaacDm``odDmjnmdTcab`bad BTcab`bDmjnmdE +Sifnfdg`befnfdgbgig`gofifnfdghbibSkgScfhfafbg`bjbhgkcSifff`bhbdgefcgdgachb`chgff`c`cdfbfefeffflb`b`chgbfefefffff`c`cdfib`babmc`b`chgacbcccdcecfcgchcibSbgefdgegbgnf`b`chgdfefafdfkc +ifff`bhbdgefcgdgbchb`chgff`c`cdfib`babmc`b`chgdf`c`cffibSbgefdgegbgnf`b`chgdfefafdfkcShg`bmc`bmfaflflfofcfhbacibkcSifff`bhbabhgibSbgefdgegbgnf`b`chgdfefafdfkcSbgefdgegbgnf`b`chgff`c`cdfkc +mgSifnfdg`bffofofachbegifnfdghcoedg`bafibSkgSbgefdgegbgnf`baf`bmcmc`b`chgacgc`boc`b`chgff`c`cdf`bjc`b`chgdfefafdfkcSmgSifnfdg`bffofofbchbegifnfdgacfcoedg`bafibSkgSbgefdgegbgnf`baf`bmcmc`b`chgacgcbchc`boc`b`chgff`c`cdf`bjc`b`chgdfefafdfkc +mgSifnfdg`bffofofcchbegifnfdgccbcoedg`bafibSkgSbgefdgegbgnf`baf`bmcmc`b`chgacgcbchcccic`boc`b`chgff`c`cdf`bjc`b`chgdfefafdfkcSmgSifnfdg`bffofofdchbegifnfdgfcdcoedg`bafib +kgSbgefdgegbgnf`baf`bmcmc`b`chgacgcbchcccicdc`cecacfcbcgccc`boc`b`chgff`c`cdf`bjc`b`chgdfefafdfkcSmgSifnfdg`bffofofechbegifnfdghcoedg`baflb`begifnfdgacfcoedg`bbfib +kgSbgefdgegbgnf`bhbaf`bmcmc`b`chgbchc`bfbfb`bbf`bmcmc`b`chgacbcccdcib`boc`b`chgff`c`cdf`bjc`b`chgdfefafdfkcSmgSS \ No newline at end of file diff --git a/unit_tests/input/arith.cbc b/unit_tests/input/arith.cbc index ed846909c..8a1b1c9a9 100644 --- a/unit_tests/input/arith.cbc +++ b/unit_tests/input/arith.cbc @@ -1,4 +1,4 @@ -ClamBCae`|``````|`afbbep`clamcoincidencejb:418 +ClamBCaeh`babgfkd|afefdfggifnf```````|bgacflfafmfbfcfmb`cnb`cacmbfcmbgfacccfffc`ccfcc``afbbep`clamcoincidencejb:418 Tedaaa` E`` diff --git a/unit_tests/input/div0.cbc b/unit_tests/input/div0.cbc index fe129f288..df55748fd 100644 --- a/unit_tests/input/div0.cbc +++ b/unit_tests/input/div0.cbc @@ -1,4 +1,4 @@ -ClamBCae`|``````|`afabp`clamcoincidencejb:23 +ClamBCafh`lifegkd|afefdfggifnf```````|bgacflfafmfbfcfmb`cnb`cacmbicmbgfafeficfcgcecff``afabp`clamcoincidencejb:23 Tedaaa` E`` @@ -7,3 +7,4 @@ A`b`bLaab`b`Fabaa Bb`b``baab@dTcab`b`E Aab`bLaab`b`b`b`Fabaa Bb`baae`Aad`Tcab`baaE +Sifnfdg`bdfiffg`chbifnfdg`bhgibSkgSbgefdgegbgnf`bacobhgkcSmgSifnfdg`befnfdgbgig`gofifnfdghbfgofifdfibSkgSbgefdgegbgnf`bdfiffg`chb`cibkcSmgSS \ No newline at end of file diff --git a/unit_tests/input/lsig.cbc b/unit_tests/input/lsig.cbc index b7494110f..5d7b33873 100644 --- a/unit_tests/input/lsig.cbc +++ b/unit_tests/input/lsig.cbc @@ -1,11 +1,23 @@ -ClamBCae`|``````|`bjaabp`clamcoincidencejb:318 -Trojan.Foo.{A,B};Target:1;(((0|1|2)=42,2)|(3=10));EP+0:aabb;ffff;aaccee;f00d;dead -Tedebieebheebgeebfeebeeebdeebbeebaeebadebcdaaa`aacb`bbadb`bdb`db`bcajbadbcebadbcebadbcebadbcebadbcecaab`bdagahdaeahdajahdabbaddabahdakah -Eafaaafb`e|amcgefdgfgifbgegcgnfafmfef`` -Gd```hbha`@`bieBdeBbgBofBjfBafBnfBnbBfdBofBof@`bheBad@`bheBbd@`bge@Ab@Ac`b`aAa`bfeBedB`eBkbB`cBjcBafBafBbfBbf@`beeBffBffBffBff@`beeBffB`cB`cBdf@`bdeBafBafBcfBcfBefBef@`beeBdfBefBafBdf@`bbe@Af@@AgAa@AhAc@AiAb@AjAd`bad@Ab`bad@Ac`bad@Af`bad@Ag`bad@Ah`bad@Ai`bad@Aj`bcdAdD```h`bcdAcD```h`bcdAbD```h`bcdAaD```h`bcd@D```h` +ClamBCafh`lifegkd|afefdfggifnf```c``a```|bgacflfafmfbfcfmb`cnb`cacmbicmbgfafeficfcgcecff``bhaabp`clamcoincidencejb:313 +Test.{A,B};Target:1;(((0|1|2)=42,2)|(3=10));EP+0:aabb;ffff;aaccee;f00d;dead +Tedebgeebfeebeeebdeebceebbeeb`eebadebcdaaa`aacb`bbadb`bcajahbaeahbaeahbaeahbaeahbaecaab`bdb`db`bdagahdajahdabbaddabahdaeah +Eaeaaaebod|amcgefdgfgifbgegcgnfafmfef`` +Gd```hbka`@`bgeBdeBefBcgBdg@`bfeBad@`bfeBbd@`bee@Ab@Ac`b`aAa`bdeBedB`eBkbB`cBjcBafBafBbfBbf@`bgeBffBffBffBff@`bgeBffB`cB`cBdf@`bceBafBafBcfBcfBefBef@`bgeBdfBefBafBdf@`b`aC``a`b`e@@@Aa@Ac@Ab@Ad`bad@Ab`bad@Ab`bad@Ac`bad@Ac`bad@Af`bad@Ag`bad@Ah`bad@Ai`bad@Aj`bcdB`aD```h`bcdAlD```h`bcdAhD```h`bcdAdD```h`bcd@D```h` A`b`bLaeb`b`aa`aa`bad`b`b`Fahac -Bb`b`gbBca`aaaagab`b`AadTaaaaaaab -Baaabeab`b`AbdbadacoaabAl`Am`b`badabbafac@dTcab`b@d +Bb`b`gbBfa`aaaagab`b`AadTaaaaaaab +Baaabeab`b`AbdbadacoaabAn`B`a`b`badabbaeac@dTcab`b@d BTcab`b@dE A`aaLbcab`b`b`b`b`b`b`b`b`b`aa`aa`aa`aa`b`b`b`b`b`b`b`b`b`b`aa`aa`b`b`aa`aa`Fbdaaa -Bb`b`gbBga`b`baagbBfa`b`babgbBea`b`baca`aa`b`bada`acabaaaeeab`badBjbdaaaffab`bab@daaagfab`baa@daaahfab`b`@db`bai`aafb`baj`aagb`bak`aahb`bala`ajakb`bama`alaiaaaneab`bamAbdaaaok`anaeb`bb`agbBda`aabaaeab`bb`aAjdaabbal`aobaaTcaaabbaE +Bb`b`gbBja`b`baagbBia`b`babgbBha`b`baca`aa`b`bada`acabaaaeeab`badBjbdaaaffab`bab@daaagfab`baa@daaahfab`b`@db`bai`aafb`baj`aagb`bak`aahb`bala`ajakb`bama`alaiaaaneab`bamAbdaaaok`anaeb`bb`agbBga`aabaaeab`bb`aAjdaabbal`aobaaTcaaabbaE +Sobjb`bieofeg`bafbgef`bofnflfig`baflflfofggefdf`bdgof`bcgefdg`bdghfefcgef`bfgifbgegcgnfafmfefcg`bafcg`bffofegnfdf`bjbobSfeidbeeecendadmdedoe`ebeedfdidhehbbbdeefcgdgbbib +feidbeeecendadmdedcehbbbadbblb`bbbbdbbibSdeadbegdeddehbacibSceidgdndaddeeebeedceoeddedcdldoebdedgdidndSddedcdldadbeedoeceidgdndaddeeebeedhbmfafgfifcfibSddedcdldadbeedoeceidgdndaddeeebeedhbjgefbgofib +ddedcdldadbeedoeceidgdndaddeeebeedhbcfhfefcfkfibSddedcdldadbeedoeceidgdndaddeeebeedhbffiffgefdgofdgefnfibSddedcdldadbeedoeceidgdndaddeeebeedhbcfhfefcfkfbcibSceidgdndaddeeebeedceoeddedcdldoeednddd +ceidgdndaddeeebeedceoeddedfdoebdedgdidndSddedfdidndedoeceidgdndaddeeebeedhbmfafgfifcflb`bbbed`ekb`cjcafafbfbfbbibSddedfdidndedoeceidgdndaddeeebeedhbjgefbgoflb`bbbffffffffbbib +ddedfdidndedoeceidgdndaddeeebeedhbffiffgefdgofdgefnflb`bbbafafcfcfefefbbibSddedfdidndedoeceidgdndaddeeebeedhbcfhfefcfkflb`bbbff`c`cdfbbibSddedfdidndedoeceidgdndaddeeebeedhbcfhfefcfkfbclb`bbbdfefafdfbbib +ceidgdndaddeeebeedceoeedndddSbfofoflf`blfofgfifcfaflfoedgbgifgfgfefbghbfgofifdfibSkgSegnfcgifgfnfefdf`bcgegmfoemfafdgcfhfefcg`bmc`bcfofegnfdgoemfafdgcfhfhbceifgfnfafdgegbgefcgnbmfafgfifcfibkb +cfofegnfdgoemfafdgcfhfhbceifgfnfafdgegbgefcgnbjgefbgofib`bkb`bcfofegnfdgoemfafdgcfhfhbceifgfnfafdgegbgefcgnbffiffgefdgofdgefnfibkcSegnfcgifgfnfefdf`begnfifagegefoemfafdgcfhfefcg`bmc`bmfafdgcfhfefcghbceifgfnfafdgegbgefcgnbmfafgfifcfibkb +mfafdgcfhfefcghbceifgfnfafdgegbgefcgnbjgefbgofibkb`bmfafdgcfhfefcghbceifgfnfafdgegbgefcgnbffiffgefdgofdgefnfibkcSifff`bhbcgegmfoemfafdgcfhfefcg`bmcmc`bdcbc`bfbfb`begnfifagegefoemfafdgcfhfefcg`bmcmc`bbcib`bkg +obob`bdehfef`bafbfoffgef`bcc`bcgifgfnfafdgegbgefcg`bhfaffgef`bmfafdgcfhfefdf`baf`bdgofdgaflf`bofff`bdcbc`bdgifmfefcglb`bafnfdf`bafdg`blfefafcgdgSobob`bbc`bofff`bdghfefmf`bhfaffgef`bmfafdgcfhfefdf +bgefdgegbgnf`bdgbgegefkcSmgSobob`bidff`bdghfef`bcfhfefcfkf`bcgifgfnfafdgegbgef`bmfafdgcfhfefcg`bac`c`bdgifmfefcg`bggef`bcgdgiflflf`bhfaffgef`baf`bmfafdgcfhfSifff`bhbcfofegnfdgoemfafdgcfhfhbceifgfnfafdgegbgefcgnbcfhfefcfkfib`bmcmc`bac`cib +bgefdgegbgnf`bdgbgegefkcSobob`bndof`bmfafdgcfhfSbgefdgegbgnf`bffaflfcgefkcSmgSifnfdg`befnfdgbgig`gofifnfdghbfgofifdfibSkgSegnfcgifgfnfefdf`bcfofegnfdg`bmc`bcfofegnfdgoemfafdgcfhfhbceifgfnfafdgegbgefcgnbcfhfefcfkfbcibkc +ifff`bhbcfofegnfdg`bncmc`bbcibSffofegnfdffeifbgegcghbcfofegnfdg`bmcmc`bbc`boc`bbbadbb`bjc`bbbbdbbibkcSbgefdgegbgnf`b`ckcSmgSS \ No newline at end of file diff --git a/unit_tests/input/retmagic.cbc b/unit_tests/input/retmagic.cbc index d3074adfa..4aef02aa9 100644 --- a/unit_tests/input/retmagic.cbc +++ b/unit_tests/input/retmagic.cbc @@ -1,7 +1,8 @@ -ClamBCae`|``````|`afaap`clamcoincidencejb:20 +ClamBCafh`lifegkd|afefdfggifnf```````|bgacflfafmfbfcfmb`cnb`cacmbicmbgfafeficfcgcecff``afaap`clamcoincidencejb:20 Tedaaa` E`` G`aa`@` A`b`bL`Faaaa BTcab`bHm``odcbadE +Sifnfdg`befnfdgbgig`gofifnfdghbfgofifdfibSkgSbgefdgegbgnf`b`chgacbcccdcff`c`cdfkcSmgSS \ No newline at end of file