├── .github └── workflows │ ├── cifuzz.yml │ └── python-publish.yml ├── .gitignore ├── .travis.yml ├── AUTHORS.TXT ├── Brewfile ├── CMakeLists.txt ├── COPYING ├── COPYING.LGPL2 ├── COPYING_GLIB ├── CREDITS.TXT ├── ChangeLog ├── Makefile ├── README.md ├── bindings ├── Makefile ├── README ├── const_generator.py ├── dotnet │ ├── README.md │ ├── UnicornDotNet.sln │ ├── UnicornManaged │ │ ├── AssemblyInfo.fs │ │ ├── Binding │ │ │ ├── BindingFactory.fs │ │ │ ├── IBinding.fs │ │ │ ├── MockBinding.fs │ │ │ └── NativeBinding.fs │ │ ├── Const │ │ │ ├── Arm.fs │ │ │ ├── Arm64.fs │ │ │ ├── Common.fs │ │ │ ├── M68k.fs │ │ │ ├── Mips.fs │ │ │ ├── Sparc.fs │ │ │ └── X86.fs │ │ ├── ConvertUtility.fs │ │ ├── InternalHooks.fs │ │ ├── Unicorn.fs │ │ ├── UnicornEngineException.fs │ │ └── UnicornManaged.fsproj │ └── UnicornSamples │ │ ├── App.config │ │ ├── Gee.External.Capstone.Proxy.dll │ │ ├── Program.cs │ │ ├── Properties │ │ └── AssemblyInfo.cs │ │ ├── ShellcodeSample.cs │ │ ├── UnicornSamples.csproj │ │ ├── Utils.cs │ │ ├── X86Sample32.cs │ │ ├── capstone.dll │ │ └── packages.config ├── go │ ├── Makefile │ ├── README.md │ ├── sample.go │ └── unicorn │ │ ├── arm64_const.go │ │ ├── arm_const.go │ │ ├── context.go │ │ ├── context_test.go │ │ ├── hook.c │ │ ├── hook.go │ │ ├── hook.h │ │ ├── m68k_const.go │ │ ├── mips_const.go │ │ ├── reg_batch.go │ │ ├── sparc_const.go │ │ ├── uc.c │ │ ├── uc.h │ │ ├── unicorn.go │ │ ├── unicorn_const.go │ │ ├── unicorn_test.go │ │ ├── x86.go │ │ ├── x86_const.go │ │ └── x86_test.go ├── haskell │ ├── .gitignore │ ├── README.TXT │ ├── Setup.hs │ ├── samples │ │ ├── SampleArm.hs │ │ ├── SampleArm64.hs │ │ ├── SampleBatchReg.hs │ │ ├── SampleM68k.hs │ │ ├── SampleMips.hs │ │ ├── SampleSparc.hs │ │ ├── SampleX86.hs │ │ └── Shellcode.hs │ ├── src │ │ ├── Unicorn.hs │ │ ├── Unicorn │ │ │ ├── CPU │ │ │ │ ├── Arm.chs │ │ │ │ ├── Arm64.chs │ │ │ │ ├── M68k.chs │ │ │ │ ├── Mips.chs │ │ │ │ ├── Sparc.chs │ │ │ │ └── X86.chs │ │ │ ├── Hook.hs │ │ │ └── Internal │ │ │ │ ├── Core.chs │ │ │ │ ├── Hook.chs │ │ │ │ ├── Unicorn.chs │ │ │ │ └── Util.hs │ │ ├── cbits │ │ │ └── unicorn_wrapper.c │ │ └── include │ │ │ └── unicorn_wrapper.h │ └── unicorn.cabal ├── java │ ├── Makefile │ ├── Makefile.build │ ├── README.TXT │ ├── khash.h │ ├── pom.xml │ ├── src │ │ ├── main │ │ │ ├── java │ │ │ │ └── unicorn │ │ │ │ │ ├── Arm64Const.java │ │ │ │ │ ├── ArmConst.java │ │ │ │ │ ├── BlockHook.java │ │ │ │ │ ├── CodeHook.java │ │ │ │ │ ├── DebugHook.java │ │ │ │ │ ├── EventMemHook.java │ │ │ │ │ ├── Hook.java │ │ │ │ │ ├── InHook.java │ │ │ │ │ ├── InterruptHook.java │ │ │ │ │ ├── M68kConst.java │ │ │ │ │ ├── MemHook.java │ │ │ │ │ ├── MemRegion.java │ │ │ │ │ ├── MipsConst.java │ │ │ │ │ ├── OutHook.java │ │ │ │ │ ├── ReadHook.java │ │ │ │ │ ├── SparcConst.java │ │ │ │ │ ├── SyscallHook.java │ │ │ │ │ ├── Unicorn.java │ │ │ │ │ ├── UnicornConst.java │ │ │ │ │ ├── UnicornException.java │ │ │ │ │ ├── WriteHook.java │ │ │ │ │ ├── X86Const.java │ │ │ │ │ └── X86_MMR.java │ │ │ └── resources │ │ │ │ └── natives │ │ │ │ ├── linux_64 │ │ │ │ └── libunicorn_java.so │ │ │ │ ├── linux_arm64 │ │ │ │ └── libunicorn_java.so │ │ │ │ ├── osx_64 │ │ │ │ └── libunicorn_java.dylib │ │ │ │ ├── osx_arm64 │ │ │ │ └── libunicorn_java.dylib │ │ │ │ ├── windows_32 │ │ │ │ └── unicorn_java.dll │ │ │ │ └── windows_64 │ │ │ │ └── unicorn_java.dll │ │ └── test │ │ │ └── java │ │ │ └── samples │ │ │ ├── SampleNetworkAuditing.java │ │ │ ├── Sample_arm.java │ │ │ ├── Sample_arm64.java │ │ │ ├── Sample_m68k.java │ │ │ ├── Sample_mips.java │ │ │ ├── Sample_sparc.java │ │ │ ├── Sample_x86.java │ │ │ ├── Sample_x86_mmr.java │ │ │ └── Shellcode.java │ ├── unicorn_Unicorn.c │ ├── unicorn_Unicorn.h │ ├── unicorn_Unicorn_NewHook.h │ ├── unicorn_Unicorn_Tuple.h │ └── unicorn_Unicorn_UnHook.h ├── pascal │ ├── LICENSE │ ├── README.md │ ├── examples │ │ ├── x86.lpi │ │ ├── x86.lpr │ │ └── x86.lps │ └── unicorn │ │ ├── Arm64Const.pas │ │ ├── ArmConst.pas │ │ ├── M68kConst.pas │ │ ├── MipsConst.pas │ │ ├── SparcConst.pas │ │ ├── UnicornConst.pas │ │ ├── Unicorn_dyn.pas │ │ └── X86Const.pas ├── python │ ├── MANIFEST.in │ ├── Makefile │ ├── README.TXT │ ├── build_wheel.sh │ ├── prebuilt │ │ └── .gitkeep │ ├── sample_all.sh │ ├── sample_arm.py │ ├── sample_arm64.py │ ├── sample_arm64eb.py │ ├── sample_armeb.py │ ├── sample_m68k.py │ ├── sample_mips.py │ ├── sample_network_auditing.py │ ├── sample_sparc.py │ ├── sample_x86.py │ ├── setup.cfg │ ├── setup.py │ ├── shellcode.py │ └── unicorn │ │ ├── __init__.py │ │ ├── arm64_const.py │ │ ├── arm_const.py │ │ ├── m68k_const.py │ │ ├── mips_const.py │ │ ├── sparc_const.py │ │ ├── unicorn.py │ │ ├── unicorn_const.py │ │ └── x86_const.py ├── ruby │ ├── Makefile │ ├── README.md │ ├── sample_arm.rb │ ├── sample_arm64.rb │ ├── sample_m68k.rb │ ├── sample_mips.rb │ ├── sample_sparc.rb │ ├── sample_x86.rb │ ├── sample_x86_gdt.rb │ ├── test_hook_gc.rb │ └── unicorn_gem │ │ ├── Gemfile │ │ ├── Rakefile │ │ ├── ext │ │ ├── extconf.rb │ │ ├── types.h │ │ ├── unicorn.c │ │ └── unicorn.h │ │ ├── lib │ │ └── unicorn_engine │ │ │ ├── arm64_const.rb │ │ │ ├── arm_const.rb │ │ │ ├── m68k_const.rb │ │ │ ├── mips_const.rb │ │ │ ├── sparc_const.rb │ │ │ ├── unicorn_const.rb │ │ │ ├── version.rb │ │ │ └── x86_const.rb │ │ ├── pkg │ │ └── .gitignore │ │ └── unicorn-engine.gemspec └── vb6 │ ├── .gitattributes │ ├── CMemRegion.cls │ ├── Form1.frm │ ├── Project1.vbp │ ├── Project1.vbw │ ├── README.txt │ ├── example_output.txt │ ├── main.cpp │ ├── misc.bas │ ├── msvbvm60.tlh │ ├── msvbvm60.tli │ ├── screenshot.png │ ├── ucIntel32.cls │ ├── uc_def.bas │ ├── ucvbshim.sln │ └── ucvbshim.vcproj ├── cmake.sh ├── config.mk ├── docs ├── BHUSA2015-unicorn.pdf ├── COMPILE-CMAKE.md ├── COMPILE-NIX.md ├── COMPILE-WINDOWS.md ├── COMPILE.md ├── Micro Unicorn-Engine API Documentation │ ├── API_Doc_Pic │ │ ├── ABkexFCfphu3zIg.png │ │ ├── DkztJcigHCdmnRp.png │ │ ├── F3rSByYuNTGDtC1.png │ │ ├── I25E9sWcJpGyax7.png │ │ ├── IZhyWrGebA5tT4i.png │ │ ├── K4HMijIVt6lofvT.png │ │ ├── MbZk8KjQFqJOxmd.png │ │ ├── NExsavSgu4yMbBQ.png │ │ ├── OVaHwelNQ4tcLmo.png │ │ ├── YCMNcEVyX8GHoPb.png │ │ ├── ZtRKvUoaPTlshJ4.png │ │ ├── aU1lbmxMjXA5g3K.png │ │ ├── bpu4r8hgzUvO7Pm.png │ │ ├── dqKBwAWUL7XvypE.png │ │ ├── fOnNpSKvjYyc7QB.png │ │ ├── iyodlNFY7hHEOgS.png │ │ ├── juNPWvwGUlraKRh.png │ │ ├── kbrF7NdV6LDxnYI.png │ │ ├── l1AhdxgKE2U3tZB.png │ │ ├── l4HhgDzcJIVvFNU.png │ │ └── q3JtOQRPl5xTFKp.png │ └── Micro Unicorn-Engine API Documentation.md ├── OPENBSD-NOTES.md ├── README.md ├── unicorn-logo.png └── unicorn-logo.txt ├── include ├── list.h ├── qemu.h ├── uc_priv.h └── unicorn │ ├── arm.h │ ├── arm64.h │ ├── m68k.h │ ├── mips.h │ ├── platform.h │ ├── sparc.h │ ├── unicorn.h │ └── x86.h ├── install-cmocka-linux.sh ├── list.c ├── make.sh ├── msvc.bat ├── msvc ├── .gitignore ├── README.TXT ├── samples │ ├── mem_apis │ │ ├── mem_apis.vcxproj │ │ └── mem_apis.vcxproj.filters │ ├── sample_arm │ │ ├── sample_arm.vcxproj │ │ └── sample_arm.vcxproj.filters │ ├── sample_arm64 │ │ ├── sample_arm64.vcxproj │ │ └── sample_arm64.vcxproj.filters │ ├── sample_arm64eb │ │ ├── sample_arm64eb.vcxproj │ │ └── sample_arm64eb.vcxproj.filters │ ├── sample_armeb │ │ ├── sample_armeb.vcxproj │ │ └── sample_armeb.vcxproj.filters │ ├── sample_batch_reg │ │ ├── sample_batch_reg.vcxproj │ │ └── sample_batch_reg.vcxproj.filters │ ├── sample_m68k │ │ ├── sample_m68k.vcxproj │ │ └── sample_m68k.vcxproj.filters │ ├── sample_mips │ │ ├── sample_mips.vcxproj │ │ └── sample_mips.vcxproj.filters │ ├── sample_sparc │ │ ├── sample_sparc.vcxproj │ │ └── sample_sparc.vcxproj.filters │ ├── sample_x86 │ │ ├── sample_x86.vcxproj │ │ └── sample_x86.vcxproj.filters │ ├── sample_x86_32_gdt_and_seg_regs │ │ ├── sample_x86_32_gdt_and_seg_regs.vcxproj │ │ └── sample_x86_32_gdt_and_seg_regs.vcxproj.filters │ └── shellcode │ │ ├── shellcode.vcxproj │ │ └── shellcode.vcxproj.filters ├── unicorn.sln └── unicorn │ ├── aarch64-softmmu │ ├── aarch64-softmmu.vcxproj │ ├── aarch64-softmmu.vcxproj.filters │ └── config-target.h │ ├── aarch64eb-softmmu │ ├── aarch64eb-softmmu.vcxproj │ ├── aarch64eb-softmmu.vcxproj.filters │ └── config-target.h │ ├── arm-softmmu │ ├── arm-softmmu.vcxproj │ ├── arm-softmmu.vcxproj.filters │ └── config-target.h │ ├── armeb-softmmu │ ├── armeb-softmmu.vcxproj │ ├── armeb-softmmu.vcxproj.filters │ └── config-target.h │ ├── config-host.h │ ├── m68k-softmmu │ ├── config-target.h │ ├── m68k-softmmu.vcxproj │ └── m68k-softmmu.vcxproj.filters │ ├── mips-softmmu │ ├── config-target.h │ ├── mips-softmmu.vcxproj │ └── mips-softmmu.vcxproj.filters │ ├── mips64-softmmu │ ├── config-target.h │ ├── mips64-softmmu.vcxproj │ └── mips64-softmmu.vcxproj.filters │ ├── mips64el-softmmu │ ├── config-target.h │ ├── mips64el-softmmu.vcxproj │ └── mips64el-softmmu.vcxproj.filters │ ├── mipsel-softmmu │ ├── config-target.h │ ├── mipsel-softmmu.vcxproj │ └── mipsel-softmmu.vcxproj.filters │ ├── prebuild_script.bat │ ├── qapi-types.c │ ├── qapi-types.h │ ├── qapi-visit.c │ ├── qapi-visit.h │ ├── sparc-softmmu │ ├── config-target.h │ ├── sparc-softmmu.vcxproj │ └── sparc-softmmu.vcxproj.filters │ ├── sparc64-softmmu │ ├── config-target.h │ ├── sparc64-softmmu.vcxproj │ └── sparc64-softmmu.vcxproj.filters │ ├── unicorn │ ├── dllmain.cpp │ ├── unicorn.vcxproj │ └── unicorn.vcxproj.filters │ ├── unicorn_static │ ├── unicorn_static.vcxproj │ └── unicorn_static.vcxproj.filters │ └── x86_64-softmmu │ ├── config-target.h │ ├── x86_64-softmmu.vcxproj │ └── x86_64-softmmu.vcxproj.filters ├── nmake.bat ├── pkgconfig.mk ├── qemu ├── CODING_STYLE ├── COPYING ├── COPYING.LIB ├── HACKING ├── LICENSE ├── Makefile ├── Makefile.objs ├── Makefile.target ├── VERSION ├── aarch64.h ├── aarch64eb.h ├── accel.c ├── arm.h ├── armeb.h ├── configure ├── cpu-exec.c ├── cpus.c ├── cputlb.c ├── default-configs │ ├── aarch64-softmmu.mak │ ├── aarch64eb-softmmu.mak │ ├── arm-softmmu.mak │ ├── armeb-softmmu.mak │ ├── m68k-softmmu.mak │ ├── mips-softmmu.mak │ ├── mips64-softmmu.mak │ ├── mips64el-softmmu.mak │ ├── mipsel-softmmu.mak │ ├── sparc-softmmu.mak │ ├── sparc64-softmmu.mak │ └── x86_64-softmmu.mak ├── docs │ └── memory.txt ├── exec.c ├── fpu │ ├── softfloat-macros.h │ ├── softfloat-specialize.h │ └── softfloat.c ├── gen_all_header.sh ├── glib_compat.c ├── header_gen.py ├── hw │ ├── Makefile.objs │ ├── arm │ │ ├── Makefile.objs │ │ ├── tosa.c │ │ └── virt.c │ ├── core │ │ ├── Makefile.objs │ │ ├── machine.c │ │ └── qdev.c │ ├── i386 │ │ ├── Makefile.objs │ │ ├── pc.c │ │ └── pc_piix.c │ ├── intc │ │ ├── Makefile.objs │ │ ├── apic.c │ │ └── apic_common.c │ ├── m68k │ │ ├── Makefile.objs │ │ └── dummy_m68k.c │ ├── mips │ │ ├── Makefile.objs │ │ ├── addr.c │ │ ├── cputimer.c │ │ └── mips_r4k.c │ ├── sparc │ │ ├── Makefile.objs │ │ └── leon3.c │ └── sparc64 │ │ ├── Makefile.objs │ │ └── sun4u.c ├── include │ ├── config.h │ ├── elf.h │ ├── exec │ │ ├── address-spaces.h │ │ ├── cpu-all.h │ │ ├── cpu-common.h │ │ ├── cpu-defs.h │ │ ├── cpu_ldst.h │ │ ├── cpu_ldst_template.h │ │ ├── cputlb.h │ │ ├── exec-all.h │ │ ├── gen-icount.h │ │ ├── helper-gen.h │ │ ├── helper-head.h │ │ ├── helper-proto.h │ │ ├── helper-tcg.h │ │ ├── hwaddr.h │ │ ├── ioport.h │ │ ├── memory-internal.h │ │ ├── memory.h │ │ └── ram_addr.h │ ├── fpu │ │ └── softfloat.h │ ├── glib_compat.h │ ├── hw │ │ ├── arm │ │ │ └── arm.h │ │ ├── boards.h │ │ ├── cpu │ │ │ └── icc_bus.h │ │ ├── hw.h │ │ ├── i386 │ │ │ ├── apic.h │ │ │ ├── apic_internal.h │ │ │ └── pc.h │ │ ├── m68k │ │ │ └── m68k.h │ │ ├── mips │ │ │ ├── cpudevs.h │ │ │ └── mips.h │ │ ├── qdev-core.h │ │ ├── qdev.h │ │ └── sparc │ │ │ └── sparc.h │ ├── qapi │ │ ├── dealloc-visitor.h │ │ ├── error.h │ │ ├── qmp-input-visitor.h │ │ ├── qmp-output-visitor.h │ │ ├── qmp │ │ │ ├── qbool.h │ │ │ ├── qdict.h │ │ │ ├── qerror.h │ │ │ ├── qfloat.h │ │ │ ├── qint.h │ │ │ ├── qjson.h │ │ │ ├── qlist.h │ │ │ ├── qobject.h │ │ │ ├── qstring.h │ │ │ └── types.h │ │ ├── string-input-visitor.h │ │ ├── visitor-impl.h │ │ └── visitor.h │ ├── qemu-common.h │ ├── qemu │ │ ├── aes.h │ │ ├── atomic.h │ │ ├── bitmap.h │ │ ├── bitops.h │ │ ├── bswap.h │ │ ├── compiler.h │ │ ├── crc32c.h │ │ ├── host-utils.h │ │ ├── int128.h │ │ ├── log.h │ │ ├── module.h │ │ ├── osdep.h │ │ ├── queue.h │ │ ├── range.h │ │ ├── thread-posix.h │ │ ├── thread-win32.h │ │ ├── thread.h │ │ ├── timer.h │ │ └── typedefs.h │ ├── qom │ │ ├── cpu.h │ │ ├── object.h │ │ └── qom-qobject.h │ └── sysemu │ │ ├── accel.h │ │ ├── cpus.h │ │ ├── memory_mapping.h │ │ ├── os-win32.h │ │ └── sysemu.h ├── ioport.c ├── m68k.h ├── memory.c ├── memory_mapping.c ├── mips.h ├── mips64.h ├── mips64el.h ├── mipsel.h ├── qapi-types.c ├── qapi-types.h ├── qapi-visit.c ├── qapi-visit.h ├── qapi │ ├── Makefile.objs │ ├── qapi-dealloc-visitor.c │ ├── qapi-visit-core.c │ ├── qmp-input-visitor.c │ ├── qmp-output-visitor.c │ └── string-input-visitor.c ├── qemu-log.c ├── qemu-timer.c ├── qobject │ ├── Makefile.objs │ ├── qbool.c │ ├── qdict.c │ ├── qerror.c │ ├── qfloat.c │ ├── qint.c │ ├── qlist.c │ └── qstring.c ├── qom │ ├── Makefile.objs │ ├── container.c │ ├── cpu.c │ ├── object.c │ └── qom-qobject.c ├── rules.mak ├── scripts │ ├── create_config │ ├── ordereddict.py │ ├── qapi-build.sh │ ├── qapi-schema.json │ ├── qapi-types.py │ ├── qapi-visit.py │ ├── qapi.py │ └── qapi │ │ └── common.json ├── softmmu_template.h ├── sparc.h ├── sparc64.h ├── target-arm │ ├── Makefile.objs │ ├── arm_ldst.h │ ├── cpu-qom.h │ ├── cpu.c │ ├── cpu.h │ ├── cpu64.c │ ├── crypto_helper.c │ ├── helper-a64.c │ ├── helper-a64.h │ ├── helper.c │ ├── helper.h │ ├── internals.h │ ├── iwmmxt_helper.c │ ├── kvm-consts.h │ ├── neon_helper.c │ ├── op_addsub.h │ ├── op_helper.c │ ├── psci.c │ ├── translate-a64.c │ ├── translate.c │ ├── translate.h │ ├── unicorn.h │ ├── unicorn_aarch64.c │ └── unicorn_arm.c ├── target-i386 │ ├── Makefile.objs │ ├── TODO │ ├── arch_memory_mapping.c │ ├── cc_helper.c │ ├── cc_helper_template.h │ ├── cpu-qom.h │ ├── cpu.c │ ├── cpu.h │ ├── excp_helper.c │ ├── fpu_helper.c │ ├── helper.c │ ├── helper.h │ ├── int_helper.c │ ├── mem_helper.c │ ├── misc_helper.c │ ├── ops_sse.h │ ├── ops_sse_header.h │ ├── seg_helper.c │ ├── shift_helper_template.h │ ├── smm_helper.c │ ├── svm.h │ ├── svm_helper.c │ ├── topology.h │ ├── translate.c │ ├── unicorn.c │ └── unicorn.h ├── target-m68k │ ├── Makefile.objs │ ├── cpu-qom.h │ ├── cpu.c │ ├── cpu.h │ ├── helper.c │ ├── helper.h │ ├── m68k-qreg.h │ ├── op_helper.c │ ├── qregs.def │ ├── translate.c │ ├── unicorn.c │ └── unicorn.h ├── target-mips │ ├── Makefile.objs │ ├── TODO │ ├── cpu-qom.h │ ├── cpu.c │ ├── cpu.h │ ├── dsp_helper.c │ ├── helper.c │ ├── helper.h │ ├── lmi_helper.c │ ├── mips-defs.h │ ├── msa_helper.c │ ├── op_helper.c │ ├── translate.c │ ├── translate_init.c │ ├── unicorn.c │ └── unicorn.h ├── target-sparc │ ├── Makefile.objs │ ├── TODO │ ├── cc_helper.c │ ├── cpu-qom.h │ ├── cpu.c │ ├── cpu.h │ ├── fop_helper.c │ ├── helper.c │ ├── helper.h │ ├── int32_helper.c │ ├── int64_helper.c │ ├── ldst_helper.c │ ├── mmu_helper.c │ ├── translate.c │ ├── unicorn.c │ ├── unicorn.h │ ├── unicorn64.c │ ├── vis_helper.c │ └── win_helper.c ├── tcg-runtime.c ├── tcg │ ├── LICENSE │ ├── README │ ├── TODO │ ├── aarch64 │ │ ├── tcg-target.c │ │ └── tcg-target.h │ ├── arm │ │ ├── tcg-target.c │ │ └── tcg-target.h │ ├── i386 │ │ ├── tcg-target.c │ │ └── tcg-target.h │ ├── ia64 │ │ ├── tcg-target.c │ │ └── tcg-target.h │ ├── mips │ │ ├── tcg-target.c │ │ └── tcg-target.h │ ├── optimize.c │ ├── ppc │ │ ├── tcg-target.c │ │ └── tcg-target.h │ ├── s390 │ │ ├── tcg-target.c │ │ └── tcg-target.h │ ├── sparc │ │ ├── tcg-target.c │ │ └── tcg-target.h │ ├── tcg-be-ldst.h │ ├── tcg-be-null.h │ ├── tcg-op.h │ ├── tcg-opc.h │ ├── tcg-runtime.h │ ├── tcg.c │ └── tcg.h ├── translate-all.c ├── translate-all.h ├── unicorn_common.h ├── util │ ├── Makefile.objs │ ├── aes.c │ ├── bitmap.c │ ├── bitops.c │ ├── crc32c.c │ ├── cutils.c │ ├── error.c │ ├── getauxval.c │ ├── host-utils.c │ ├── module.c │ ├── oslib-posix.c │ ├── oslib-win32.c │ ├── qemu-error.c │ ├── qemu-thread-posix.c │ ├── qemu-thread-win32.c │ ├── qemu-timer-common.c │ └── setjmp-wrapper-win32.asm ├── vl.c ├── vl.h └── x86_64.h ├── samples ├── .gitignore ├── Makefile ├── mem_apis.c ├── sample_all.sh ├── sample_arm.c ├── sample_arm64.c ├── sample_arm64eb.c ├── sample_armeb.c ├── sample_batch_reg.c ├── sample_m68k.c ├── sample_mips.c ├── sample_sparc.c ├── sample_x86.c ├── sample_x86_32_gdt_and_seg_regs.c └── shellcode.c ├── tests ├── fuzz │ ├── Makefile │ ├── dlcorpus.sh │ ├── fuzz_emu.options │ ├── fuzz_emu_arm64_arm.c │ ├── fuzz_emu_arm64_armbe.c │ ├── fuzz_emu_arm_arm.c │ ├── fuzz_emu_arm_armbe.c │ ├── fuzz_emu_arm_thumb.c │ ├── fuzz_emu_m68k_be.c │ ├── fuzz_emu_mips_32be.c │ ├── fuzz_emu_mips_32le.c │ ├── fuzz_emu_sparc_32be.c │ ├── fuzz_emu_x86_16.c │ ├── fuzz_emu_x86_32.c │ ├── fuzz_emu_x86_64.c │ ├── gentargets.sh │ ├── onedir.c │ └── onefile.c ├── regress │ ├── .gitignore │ ├── 001-bad_condition_code_0xe.c │ ├── 002-qemu__fatal__unimplemented_control_register_write_0xffb___0x0.c │ ├── 003-qemu__fatal__wdebug_not_implemented.c │ ├── 004-segmentation_fault_1.c │ ├── 005-qemu__fatal__illegal_instruction__0000___00000404.c │ ├── 006-qemu__fatal__illegal_instruction__0421___00040026.c │ ├── 00opcode_uc_crash.c │ ├── LICENSE │ ├── Makefile │ ├── arm64_reg_rw_w0_w30.py │ ├── arm_apsr_access.py │ ├── arm_bx_unmapped.py │ ├── arm_bxeq_hang.py │ ├── arm_enable_vfp.c │ ├── arm_fp_vfp_disabled.py │ ├── arm_init_input_crash.py │ ├── arm_movr12_hang.py │ ├── arm_vldr_invalid.py │ ├── bad_ram.py │ ├── block_test.c │ ├── callback-pc.py │ ├── crash_tb.py │ ├── deadlock_1.py │ ├── eflags_noset.c │ ├── eflags_nosync.c │ ├── emu_clear_errors.c │ ├── emu_clear_errors.py │ ├── emu_stop_in_hook_overrun.c │ ├── emu_stop_segfault.py │ ├── ensure_typedef_consts_generated.py │ ├── fpu_ip.py │ ├── fpu_mem_write.py │ ├── hang.py │ ├── hook_add_crash.py │ ├── hook_code_add_del.py │ ├── hook_code_stop_emu.py │ ├── hook_extrainvoke.c │ ├── hook_readonly_write_local.py │ ├── init.py │ ├── invalid_read_in_cpu_tb_exec.c │ ├── invalid_read_in_tb_flush_x86_64.c │ ├── invalid_write.py │ ├── invalid_write_in_cpu_tb_exec_x86_64.c │ ├── jmp_ebx_hang.py │ ├── jumping.py │ ├── leaked_refs.py │ ├── map_crash.c │ ├── map_write.c │ ├── mem_64_c.c │ ├── mem_double_unmap.c │ ├── mem_exec.c │ ├── mem_fuzz.c │ ├── mem_map_0x100000000.c │ ├── mem_map_large.c │ ├── mem_nofree.c │ ├── mem_protect.c │ ├── mem_unmap.c │ ├── memleak_arm.c │ ├── memleak_arm64.c │ ├── memleak_m68k.c │ ├── memleak_mips.c │ ├── memleak_sparc.c │ ├── memleak_x86.c │ ├── memmap.py │ ├── memmap_segfault.py │ ├── mips_branch_delay.py │ ├── mips_branch_likely_issue.c │ ├── mips_delay_slot_code_hook.c │ ├── mips_except.py │ ├── mips_invalid_read_of_size_4_when_tracing.c │ ├── mips_kernel_mmu.py │ ├── mips_kseg0_1.c │ ├── mips_single_step_sp.py │ ├── mips_syscall_pc.py │ ├── mov_gs_eax.py │ ├── movsd.py │ ├── nr_mem_test.c │ ├── osx_qemu_thread_create_crash.py │ ├── potential_memory_leak.py │ ├── pshufb.py │ ├── reg_write_sign_extension.py │ ├── regress.py │ ├── regress.sh │ ├── rep_hook.py │ ├── rep_movsb.c │ ├── ro_mem_test.c │ ├── run_across_bb.py │ ├── rw_hookstack.c │ ├── segfault_on_stop.py │ ├── sigill.c │ ├── sigill2.c │ ├── sparc64.py │ ├── sparc_jump_to_zero.c │ ├── sparc_reg.py │ ├── sysenter_hook_x86.c │ ├── tcg_liveness_analysis_bug_issue-287.py │ ├── threaded_emu_start.c │ ├── timeout_segfault.c │ ├── translator_buffer.py │ ├── vld.py │ ├── write_before_map.py │ ├── wrong_rip.py │ ├── wrong_rip_arm.py │ ├── wrong_sp_arm.py │ ├── x86_16_segfault.c │ ├── x86_64_conditional_jump.py │ ├── x86_64_eflags.py │ ├── x86_64_msr.py │ ├── x86_eflags.py │ ├── x86_fldt_fsqrt.py │ ├── x86_gdt.py │ ├── x86_self_modifying.elf │ ├── x86_self_modifying.py │ ├── x86_self_modifying.s │ └── x86_vex.c └── unit │ ├── .gitignore │ ├── Makefile │ ├── gdt_idx.s │ ├── high_address.s │ ├── pc_change.s │ ├── tb_x86.s │ ├── test_gdt_idt_x86.c │ ├── test_hang.c │ ├── test_hookcounts.c │ ├── test_mem_high.c │ ├── test_mem_map.c │ ├── test_mem_map_ptr.c │ ├── test_multihook.c │ ├── test_pc_change.c │ ├── test_sanity.c │ ├── test_tb_x86.c │ ├── test_x86.c │ ├── test_x86_rip_bug.c │ ├── test_x86_shl_enter_leave.c │ ├── test_x86_soft_paging.c │ ├── unicorn_test.h │ └── x86_soft_paging_low.s ├── uc.c └── windows_export.bat /.github/workflows/cifuzz.yml: -------------------------------------------------------------------------------- 1 | name: CIFuzz 2 | on: [pull_request] 3 | jobs: 4 | Fuzzing: 5 | runs-on: ubuntu-latest 6 | steps: 7 | - name: Build Fuzzers 8 | uses: google/oss-fuzz/infra/cifuzz/actions/build_fuzzers@master 9 | with: 10 | oss-fuzz-project-name: 'unicorn' 11 | dry-run: false 12 | - name: Run Fuzzers 13 | uses: google/oss-fuzz/infra/cifuzz/actions/run_fuzzers@master 14 | with: 15 | oss-fuzz-project-name: 'unicorn' 16 | fuzz-seconds: 600 17 | dry-run: false 18 | - name: Upload Crash 19 | uses: actions/upload-artifact@v1 20 | if: failure() 21 | with: 22 | name: artifacts 23 | path: ./out/artifacts 24 | -------------------------------------------------------------------------------- /AUTHORS.TXT: -------------------------------------------------------------------------------- 1 | Nguyen Anh Quynh 2 | Dang Hoang Vu 3 | -------------------------------------------------------------------------------- /Brewfile: -------------------------------------------------------------------------------- 1 | # Travis CI setup for MacOS Brew 2 | 3 | # used for testing framework 4 | brew "cmocka" 5 | # used for cross assembly of code for testing 6 | brew "crosstool-ng" 7 | -------------------------------------------------------------------------------- /bindings/Makefile: -------------------------------------------------------------------------------- 1 | # Unicorn Engine 2 | # By Nguyen Anh Quynh & Dang Hoang Vu, 2015 3 | DIFF = diff 4 | 5 | SAMPLE_SOURCE = $(wildcard ../samples/*.c) 6 | SAMPLE = $(SAMPLE_SOURCE:../samples/%.c=%) 7 | SAMPLE := $(SAMPLE:mem_apis=) 8 | SAMPLE := $(SAMPLE:sample_batch_reg=) 9 | SAMPLE := $(SAMPLE:sample_x86_32_gdt_and_seg_regs=) 10 | SAMPLE := $(SAMPLE:shellcode=) 11 | 12 | UNAME_S := $(shell uname -s) 13 | ifeq ($(UNAME_S), Linux) 14 | ENV_VARS = LD_PRELOAD=librt.so LD_LIBRARY_PATH=../ DYLD_LIBRARY_PATH=../ 15 | else 16 | ENV_VARS = LD_LIBRARY_PATH=../ DYLD_LIBRARY_PATH=../ LIBUNICORN_PATH=$(TRAVIS_BUILD_DIR) 17 | endif 18 | 19 | 20 | .PHONY: build install python c clean check test 21 | 22 | build: 23 | $(MAKE) -C python gen_const 24 | $(MAKE) -C go gen_const 25 | $(MAKE) -C java gen_const 26 | $(MAKE) -C ruby gen_const 27 | python const_generator.py dotnet 28 | python const_generator.py pascal 29 | 30 | install: build 31 | $(MAKE) -C python install 32 | $(MAKE) -C java install 33 | 34 | test: $(SAMPLE:%=%.py.test) 35 | 36 | c: 37 | $(MAKE) -C ../samples 38 | python: 39 | $(MAKE) -C python 40 | %.c.txt: c 41 | $(ENV_VARS) ../samples/$(@:%.c.txt=%) > $@ 42 | %.py.txt: python 43 | $(ENV_VARS) python python/$(@:%.txt=%) > $@ 44 | 45 | %.py.test: %.c.txt %.py.txt 46 | $(DIFF) -u $(@:%.py.test=%.c.txt) $(@:%.py.test=%.py.txt) 47 | 48 | clean: 49 | # rm -rf *.txt 50 | $(MAKE) -C python clean 51 | $(MAKE) -C java clean 52 | 53 | check: 54 | make -C python check 55 | -------------------------------------------------------------------------------- /bindings/README: -------------------------------------------------------------------------------- 1 | This directory contains bindings & test code for Python, Java, Go and .NET. 2 | See /README or /README.TXT or /README.md for how to install each binding. 3 | 4 | The following bindings are contributed by community. 5 | 6 | - Java binding: by Chris Eagle. 7 | - Go binding: by Ryan Hileman. 8 | - .NET binding: by Antonio Parata. 9 | - Ruby binding: by Sascha Schirra 10 | - Haskell binding: by Adrian Herrera. 11 | - VB6 binding: David Zimmer. 12 | - FreePascal/Delphi binding: Mohamed Osama. 13 | 14 | More bindings created & maintained externally by community are available as follows. 15 | 16 | - UnicornPascal: Delphi/Free Pascal binding (by Stievie). 17 | https://github.com/stievie/UnicornPascal 18 | 19 | - Unicorn-Rs: Rust binding (by Sébastien Duquette) 20 | https://github.com/ekse/unicorn-rs 21 | 22 | - UnicornEngine: Perl binding (by Vikas Naresh Kumar) 23 | https://metacpan.org/pod/UnicornEngine 24 | 25 | - Unicorn.CR: Crystal binding (by Benoit Côté-Jodoin) 26 | https://github.com/Becojo/unicorn.cr 27 | 28 | - Deimos/unicorn: D binding (by Vladimir Panteleev) 29 | https://github.com/D-Programming-Deimos/unicorn 30 | 31 | - Unicorn-Lua: Lua binding (by Diego Argueta) 32 | https://github.com/dargueta/unicorn-lua 33 | 34 | - pharo-unicorn: Pharo binding (by Guille Polito) 35 | https://github.com/guillep/pharo-unicorn 36 | -------------------------------------------------------------------------------- /bindings/dotnet/README.md: -------------------------------------------------------------------------------- 1 | This documentation explains how to use the .NET binding for Unicorn 2 | from source. 3 | 4 | 0. Install the core engine as a dependency 5 | 6 | Follow README in the root directory to compile & install the core. 7 | 8 | 1. Compile the code 9 | 10 | [Windows] 11 | To compile the code open the UnicornSln.sln with Microsoft Visual 12 | Studio 12 or with a newer version and just press Ctrl+Shift+B to build 13 | the solution. 14 | 15 | You need to have installed at least version 4.5 of the .NET framework. 16 | 17 | [Linux] 18 | TODO 19 | 20 | 2. Usage 21 | 22 | The solution includes the testing project UnicornTests with examples 23 | of usage. 24 | 25 | In order to use the library in your project just add a reference to 26 | the .NET library and be sure to copy the unmanaged unicorn.dll 27 | library in the output directory. 28 | 29 | The naming convention used is the Upper Camel Case, this mean that to 30 | invoke the uc_mem_read method you have to search for the MemRead method. 31 | -------------------------------------------------------------------------------- /bindings/dotnet/UnicornManaged/Binding/BindingFactory.fs: -------------------------------------------------------------------------------- 1 | namespace UnicornManaged.Binding 2 | 3 | open System 4 | 5 | module BindingFactory = 6 | let mutable _instance = NativeBinding.instance 7 | 8 | let setDefaultBinding(binding: IBinding) = 9 | _instance <- binding 10 | 11 | let getDefault() = 12 | _instance 13 | 14 | -------------------------------------------------------------------------------- /bindings/dotnet/UnicornManaged/Const/M68k.fs: -------------------------------------------------------------------------------- 1 | // For Unicorn Engine. AUTO-GENERATED FILE, DO NOT EDIT 2 | 3 | namespace UnicornManaged.Const 4 | 5 | open System 6 | 7 | [] 8 | module M68k = 9 | 10 | // M68K registers 11 | 12 | let UC_M68K_REG_INVALID = 0 13 | let UC_M68K_REG_A0 = 1 14 | let UC_M68K_REG_A1 = 2 15 | let UC_M68K_REG_A2 = 3 16 | let UC_M68K_REG_A3 = 4 17 | let UC_M68K_REG_A4 = 5 18 | let UC_M68K_REG_A5 = 6 19 | let UC_M68K_REG_A6 = 7 20 | let UC_M68K_REG_A7 = 8 21 | let UC_M68K_REG_D0 = 9 22 | let UC_M68K_REG_D1 = 10 23 | let UC_M68K_REG_D2 = 11 24 | let UC_M68K_REG_D3 = 12 25 | let UC_M68K_REG_D4 = 13 26 | let UC_M68K_REG_D5 = 14 27 | let UC_M68K_REG_D6 = 15 28 | let UC_M68K_REG_D7 = 16 29 | let UC_M68K_REG_SR = 17 30 | let UC_M68K_REG_PC = 18 31 | let UC_M68K_REG_ENDING = 19 32 | 33 | -------------------------------------------------------------------------------- /bindings/dotnet/UnicornManaged/ConvertUtility.fs: -------------------------------------------------------------------------------- 1 | namespace UnicornManaged 2 | 3 | open System 4 | 5 | [] 6 | module internal ConvertUtility = 7 | 8 | let int64ToBytes(v: Int64) = 9 | let res = Array.zeroCreate 8 10 | let mutable uv = uint64 v 11 | for i = 0 to res.Length-1 do 12 | res.[i] <- byte (uv &&& uint64 0xFF) 13 | uv <- uv >>> 8 14 | res 15 | 16 | let bytesToInt64(v: Byte array) = 17 | let mutable res = uint64 0 18 | for i = 0 to v.Length-1 do 19 | let tmpV = v.[i] &&& byte 0xFF 20 | res <- res + (uint64 tmpV <<< (i * 8)) 21 | int64 res -------------------------------------------------------------------------------- /bindings/dotnet/UnicornManaged/UnicornEngineException.fs: -------------------------------------------------------------------------------- 1 | namespace UnicornManaged 2 | 3 | open System 4 | 5 | type UnicornEngineException(errNo: Int32, msg: String) = 6 | inherit ApplicationException(msg) 7 | 8 | member this.ErrorNo = errNo 9 | 10 | -------------------------------------------------------------------------------- /bindings/dotnet/UnicornSamples/App.config: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | -------------------------------------------------------------------------------- /bindings/dotnet/UnicornSamples/Gee.External.Capstone.Proxy.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/bindings/dotnet/UnicornSamples/Gee.External.Capstone.Proxy.dll -------------------------------------------------------------------------------- /bindings/dotnet/UnicornSamples/Program.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | 3 | namespace UnicornSamples 4 | { 5 | class Program 6 | { 7 | static void Main(string[] args) 8 | { 9 | // X86 tests 32bit 10 | X86Sample32.X86Code32(); 11 | X86Sample32.X86Code32InvalidMemRead(); 12 | X86Sample32.X86Code32InvalidMemWriteWithRuntimeFix(); 13 | X86Sample32.X86Code32InOut(); 14 | 15 | // Run all shellcode tests 16 | ShellcodeSample.X86Code32Self(); 17 | ShellcodeSample.X86Code32(); 18 | 19 | Console.Write("Tests completed"); 20 | Console.ReadLine(); 21 | } 22 | } 23 | } 24 | -------------------------------------------------------------------------------- /bindings/dotnet/UnicornSamples/capstone.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/bindings/dotnet/UnicornSamples/capstone.dll -------------------------------------------------------------------------------- /bindings/dotnet/UnicornSamples/packages.config: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | -------------------------------------------------------------------------------- /bindings/go/Makefile: -------------------------------------------------------------------------------- 1 | # Go binding for Unicorn engine. Ryan Hileman 2 | 3 | .PHONY: all gen_const test 4 | 5 | all: gen_const 6 | cd unicorn && go build 7 | 8 | gen_const: 9 | cd .. && python const_generator.py go 10 | 11 | test: all 12 | cd unicorn && LD_LIBRARY_PATH=../../../ DYLD_LIBRARY_PATH=../../../ go test 13 | -------------------------------------------------------------------------------- /bindings/go/README.md: -------------------------------------------------------------------------------- 1 | To download/update the Unicorn Go bindings, run: 2 | 3 | go get -u github.com/unicorn-engine/unicorn/bindings/go 4 | 5 | A very basic usage example follows 6 | 7 | _(Does not handle most errors for brevity. Please see sample.go for a more hygenic example):_ 8 | 9 | package main 10 | 11 | import ( 12 | "fmt" 13 | uc "github.com/unicorn-engine/unicorn/bindings/go/unicorn" 14 | ) 15 | 16 | func main() { 17 | mu, _ := uc.NewUnicorn(uc.ARCH_X86, uc.MODE_32) 18 | // mov eax, 1234 19 | code := []byte{184, 210, 4, 0, 0} 20 | mu.MemMap(0x1000, 0x1000) 21 | mu.MemWrite(0x1000, code) 22 | if err := mu.Start(0x1000, 0x1000+uint64(len(code))); err != nil { 23 | panic(err) 24 | } 25 | eax, _ := mu.RegRead(uc.X86_REG_EAX) 26 | fmt.Printf("EAX is now: %d\n", eax) 27 | } 28 | 29 | An example program exercising far more Unicorn functionality and error handling can be found in sample.go. 30 | -------------------------------------------------------------------------------- /bindings/go/unicorn/context.go: -------------------------------------------------------------------------------- 1 | package unicorn 2 | 3 | import ( 4 | "runtime" 5 | "unsafe" 6 | ) 7 | 8 | // #include 9 | import "C" 10 | 11 | type Context **C.uc_context 12 | 13 | func (u *uc) ContextSave(reuse Context) (Context, error) { 14 | ctx := reuse 15 | if ctx == nil { 16 | ctx = new(*C.uc_context) 17 | } 18 | if err := errReturn(C.uc_context_alloc(u.handle, ctx)); err != nil { 19 | return nil, err 20 | } 21 | runtime.SetFinalizer(ctx, func(p Context) { C.uc_free(unsafe.Pointer(*p)) }) 22 | if err := errReturn(C.uc_context_save(u.handle, *ctx)); err != nil { 23 | } 24 | return ctx, nil 25 | } 26 | 27 | func (u *uc) ContextRestore(ctx Context) error { 28 | return errReturn(C.uc_context_restore(u.handle, *ctx)) 29 | } 30 | -------------------------------------------------------------------------------- /bindings/go/unicorn/context_test.go: -------------------------------------------------------------------------------- 1 | package unicorn 2 | 3 | import ( 4 | "testing" 5 | ) 6 | 7 | func TestContext(t *testing.T) { 8 | u, err := NewUnicorn(ARCH_X86, MODE_32) 9 | if err != nil { 10 | t.Fatal(err) 11 | } 12 | u.RegWrite(X86_REG_EBP, 100) 13 | ctx, err := u.ContextSave(nil) 14 | if err != nil { 15 | t.Fatal(err) 16 | } 17 | u.RegWrite(X86_REG_EBP, 200) 18 | err = u.ContextRestore(ctx) 19 | if err != nil { 20 | t.Fatal(err) 21 | } 22 | val, _ := u.RegRead(X86_REG_EBP) 23 | if val != 100 { 24 | t.Fatal("context restore failed") 25 | } 26 | } 27 | -------------------------------------------------------------------------------- /bindings/go/unicorn/hook.h: -------------------------------------------------------------------------------- 1 | uc_err uc_hook_add_wrap(uc_engine *handle, uc_hook *h2, uc_hook_type type, void *callback, uintptr_t user, uint64_t begin, uint64_t end); 2 | uc_err uc_hook_add_insn(uc_engine *handle, uc_hook *h2, uc_hook_type type, void *callback, uintptr_t user, uint64_t begin, uint64_t end, int insn); 3 | void hookCode_cgo(uc_engine *handle, uint64_t addr, uint32_t size, uintptr_t user); 4 | bool hookMemInvalid_cgo(uc_engine *handle, uc_mem_type type, uint64_t addr, int size, int64_t value, uintptr_t user); 5 | void hookMemAccess_cgo(uc_engine *handle, uc_mem_type type, uint64_t addr, int size, int64_t value, uintptr_t user); 6 | void hookInterrupt_cgo(uc_engine *handle, uint32_t intno, uintptr_t user); 7 | uint32_t hookX86In_cgo(uc_engine *handle, uint32_t port, uint32_t size, uintptr_t user); 8 | void hookX86Out_cgo(uc_engine *handle, uint32_t port, uint32_t size, uint32_t value, uintptr_t user); 9 | void hookX86Syscall_cgo(uc_engine *handle, uintptr_t user); 10 | -------------------------------------------------------------------------------- /bindings/go/unicorn/m68k_const.go: -------------------------------------------------------------------------------- 1 | package unicorn 2 | // For Unicorn Engine. AUTO-GENERATED FILE, DO NOT EDIT [m68k_const.go] 3 | const ( 4 | 5 | // M68K registers 6 | 7 | M68K_REG_INVALID = 0 8 | M68K_REG_A0 = 1 9 | M68K_REG_A1 = 2 10 | M68K_REG_A2 = 3 11 | M68K_REG_A3 = 4 12 | M68K_REG_A4 = 5 13 | M68K_REG_A5 = 6 14 | M68K_REG_A6 = 7 15 | M68K_REG_A7 = 8 16 | M68K_REG_D0 = 9 17 | M68K_REG_D1 = 10 18 | M68K_REG_D2 = 11 19 | M68K_REG_D3 = 12 20 | M68K_REG_D4 = 13 21 | M68K_REG_D5 = 14 22 | M68K_REG_D6 = 15 23 | M68K_REG_D7 = 16 24 | M68K_REG_SR = 17 25 | M68K_REG_PC = 18 26 | M68K_REG_ENDING = 19 27 | ) -------------------------------------------------------------------------------- /bindings/go/unicorn/uc.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include "_cgo_export.h" 4 | 5 | uc_err uc_reg_read_batch_helper(uc_engine *handle, int *regs, uint64_t *val_out, int count) { 6 | void **val_ref = malloc(sizeof(void *) * count); 7 | int i; 8 | for (i = 0; i < count; i++) { 9 | val_ref[i] = (void *)&val_out[i]; 10 | } 11 | uc_err ret = uc_reg_read_batch(handle, regs, val_ref, count); 12 | free(val_ref); 13 | return ret; 14 | } 15 | 16 | uc_err uc_reg_write_batch_helper(uc_engine *handle, int *regs, uint64_t *val_in, int count) { 17 | void **val_ref = malloc(sizeof(void *) * count); 18 | int i; 19 | for (i = 0; i < count; i++) { 20 | val_ref[i] = (void *)&val_in[i]; 21 | } 22 | uc_err ret = uc_reg_write_batch(handle, regs, (void *const *)val_ref, count); 23 | free(val_ref); 24 | return ret; 25 | } 26 | -------------------------------------------------------------------------------- /bindings/go/unicorn/uc.h: -------------------------------------------------------------------------------- 1 | uc_err uc_reg_read_batch_helper(uc_engine *handle, int *regs, uint64_t *val_out, int count); 2 | uc_err uc_reg_write_batch_helper(uc_engine *handle, int *regs, uint64_t *val_in, int count); 3 | -------------------------------------------------------------------------------- /bindings/haskell/.gitignore: -------------------------------------------------------------------------------- 1 | dist 2 | cabal-dev 3 | *.o 4 | *.hi 5 | *.chi 6 | *.chs.h 7 | *.dyn_o 8 | *.dyn_hi 9 | .virtualenv 10 | .hpc 11 | .hsenv 12 | .cabal-sandbox/ 13 | cabal.sandbox.config 14 | *.prof 15 | *.aux 16 | *.hp 17 | SampleArm 18 | SampleArm64 19 | SampleM68k 20 | SampleMips 21 | SampleSparc 22 | SampleX86 23 | Shellcode 24 | SampleBatchReg 25 | -------------------------------------------------------------------------------- /bindings/haskell/README.TXT: -------------------------------------------------------------------------------- 1 | This documentation explains how to install Haskell binding for Unicorn 2 | from source. 3 | 4 | 5 | 0. Install the core engine as dependency 6 | 7 | Follow README in the root directory to compile & install the core. 8 | 9 | On *nix, this can simply be done by (project root directory): 10 | 11 | $ sudo ./make.sh install 12 | 13 | 14 | 1. Change directories into the Haskell bindings, build and install 15 | 16 | $ cd bindings/haskell 17 | $ cabal install 18 | 19 | 20 | If you are installing into a sandbox, run `cabal sandbox init` before 21 | installing Unicorn's dependencies. 22 | 23 | If the build fails, install c2hs manually `cabal install c2hs` (note that this 24 | will probably also require you to run `cabal install alex` and `cabal install 25 | happy` as well). If you are NOT using a sandbox, ensure that `$HOME/.cabal/bin` 26 | is on your PATH. 27 | 28 | To build a sample (after having built and installed the Haskell bindings) 29 | 30 | $ cd bindings/haskell 31 | $ ghc --make samples/SampleArm.hs 32 | -------------------------------------------------------------------------------- /bindings/haskell/Setup.hs: -------------------------------------------------------------------------------- 1 | import Distribution.Simple 2 | main = defaultMain 3 | -------------------------------------------------------------------------------- /bindings/haskell/src/Unicorn/CPU/Arm.chs: -------------------------------------------------------------------------------- 1 | {-# LANGUAGE ForeignFunctionInterface #-} 2 | 3 | {-| 4 | Module : Unicorn.CPU.Arm 5 | Description : Definitions for the ARM architecture. 6 | Copyright : (c) Adrian Herrera, 2016 7 | License : GPL-2 8 | 9 | Definitions for the ARM architecture. 10 | -} 11 | module Unicorn.CPU.Arm 12 | ( 13 | Register(..) 14 | ) where 15 | 16 | import Unicorn.Internal.Core (Reg) 17 | 18 | {# context lib = "unicorn" #} 19 | 20 | #include 21 | 22 | -- | ARM registers. 23 | {# enum uc_arm_reg as Register 24 | { underscoreToCase } 25 | omit ( UC_ARM_REG_INVALID 26 | , UC_ARM_REG_ENDING 27 | ) 28 | with prefix = "UC_ARM_REG_" 29 | deriving (Show, Eq, Bounded) 30 | #} 31 | 32 | instance Reg Register 33 | -------------------------------------------------------------------------------- /bindings/haskell/src/Unicorn/CPU/Arm64.chs: -------------------------------------------------------------------------------- 1 | {-# LANGUAGE ForeignFunctionInterface #-} 2 | 3 | {-| 4 | Module : Unicorn.CPU.Arm64 5 | Description : Definitions for the ARM64 (ARMv8) architecture. 6 | Copyright : (c) Adrian Herrera, 2016 7 | License : GPL-2 8 | 9 | Definitions for the ARM64 (ARMv8) architecture. 10 | -} 11 | module Unicorn.CPU.Arm64 12 | ( 13 | Register(..) 14 | ) where 15 | 16 | import Unicorn.Internal.Core (Reg) 17 | 18 | {# context lib = "unicorn" #} 19 | 20 | #include 21 | 22 | -- | ARM64 registers. 23 | {# enum uc_arm64_reg as Register 24 | { underscoreToCase } 25 | omit ( UC_ARM64_REG_INVALID 26 | , UC_ARM64_REG_ENDING 27 | ) 28 | with prefix = "UC_ARM64_REG_" 29 | deriving (Show, Eq, Bounded) 30 | #} 31 | 32 | instance Reg Register 33 | -------------------------------------------------------------------------------- /bindings/haskell/src/Unicorn/CPU/M68k.chs: -------------------------------------------------------------------------------- 1 | {-# LANGUAGE ForeignFunctionInterface #-} 2 | 3 | {-| 4 | Module : Unicorn.CPU.Mk68k 5 | Description : Definitions for the MK68K architecture. 6 | Copyright : (c) Adrian Herrera, 2016 7 | License : GPL-2 8 | 9 | Definitions for the MK68K architecture. 10 | -} 11 | module Unicorn.CPU.M68k 12 | ( 13 | Register(..) 14 | ) where 15 | 16 | import Unicorn.Internal.Core (Reg) 17 | 18 | {# context lib = "unicorn" #} 19 | 20 | #include 21 | 22 | -- | M68K registers. 23 | {# enum uc_m68k_reg as Register 24 | { underscoreToCase } 25 | omit ( UC_M68K_REG_INVALID 26 | , UC_M68K_REG_ENDING 27 | ) 28 | with prefix = "UC_M68K_REG_" 29 | deriving (Show, Eq, Bounded) 30 | #} 31 | 32 | instance Reg Register 33 | -------------------------------------------------------------------------------- /bindings/haskell/src/Unicorn/CPU/Sparc.chs: -------------------------------------------------------------------------------- 1 | {-# LANGUAGE ForeignFunctionInterface #-} 2 | 3 | {-| 4 | Module : Unicorn.CPU.Sparc 5 | Description : Definitions for the SPARC architecture. 6 | Copyright : (c) Adrian Herrera, 2016 7 | License : GPL-2 8 | 9 | Definitions for the SPARC architecture. 10 | -} 11 | module Unicorn.CPU.Sparc 12 | ( 13 | Register(..) 14 | ) where 15 | 16 | import Unicorn.Internal.Core (Reg) 17 | 18 | {# context lib = "unicorn" #} 19 | 20 | #include 21 | 22 | -- | SPARC registers. 23 | {# enum uc_sparc_reg as Register 24 | { underscoreToCase } 25 | omit (UC_SPARC_REG_INVALID 26 | , UC_SPARC_REG_ENDING 27 | ) 28 | with prefix = "UC_SPARC_REG_" 29 | deriving (Show, Eq, Bounded) 30 | #} 31 | 32 | instance Reg Register 33 | -------------------------------------------------------------------------------- /bindings/haskell/src/Unicorn/Internal/Util.hs: -------------------------------------------------------------------------------- 1 | {-| 2 | Module : Unicorn.Internal.Util 3 | Description : Utility (aka helper) functions for the Unicorn emulator. 4 | Copyright : (c) Adrian Herrera, 2016 5 | License : GPL-2 6 | -} 7 | module Unicorn.Internal.Util where 8 | 9 | import Data.Bits 10 | import Foreign 11 | 12 | -- | Combine a list of Enums by performing a bitwise-OR. 13 | combineEnums :: (Enum a, Num b, Bits b) 14 | => [a] 15 | -> b 16 | combineEnums = 17 | foldr ((.|.) <$> enumToNum) 0 18 | 19 | -- | Cast a pointer and then peek inside it. 20 | castPtrAndPeek :: Storable a 21 | => Ptr b 22 | -> IO a 23 | castPtrAndPeek = 24 | peek . castPtr 25 | 26 | -- | Convert an 'Eum' to a 'Num'. 27 | enumToNum :: (Enum a, Num b) 28 | => a 29 | -> b 30 | enumToNum = 31 | fromIntegral . fromEnum 32 | -------------------------------------------------------------------------------- /bindings/haskell/src/cbits/unicorn_wrapper.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | #include "unicorn_wrapper.h" 4 | 5 | void uc_close_wrapper(uc_engine *uc) { 6 | uc_close(uc); 7 | } 8 | 9 | void uc_close_dummy(uc_engine *uc) { 10 | } 11 | 12 | uc_err uc_reg_write_wrapper(uc_engine *uc, int regid, const int64_t *value) { 13 | return uc_reg_write(uc, regid, (const void*) value); 14 | } 15 | 16 | uc_err uc_reg_read_wrapper(uc_engine *uc, int regid, int64_t *value) { 17 | return uc_reg_read(uc, regid, (void*) value); 18 | } 19 | 20 | uc_err uc_reg_write_batch_wrapper(uc_engine *uc, int *regs, int64_t *vals, int count) { 21 | void **valsPtr = malloc(sizeof(void*) * count); 22 | int i; 23 | 24 | for (i = 0; i < count; ++i) { 25 | valsPtr[i] = (void*) &vals[i]; 26 | } 27 | 28 | uc_err ret = uc_reg_write_batch(uc, regs, (void *const*) valsPtr, count); 29 | free(valsPtr); 30 | 31 | return ret; 32 | } 33 | 34 | uc_err uc_reg_read_batch_wrapper(uc_engine *uc, int *regs, int64_t *vals, int count) { 35 | void **valsPtr = malloc(sizeof(void*) * count); 36 | int i; 37 | 38 | for (i = 0; i < count; ++i) { 39 | valsPtr[i] = (void*) &vals[i]; 40 | } 41 | 42 | uc_err ret = uc_reg_read_batch(uc, regs, valsPtr, count); 43 | free(valsPtr); 44 | 45 | return ret; 46 | } 47 | 48 | void uc_free_wrapper(void *mem) { 49 | uc_free(mem); 50 | } 51 | -------------------------------------------------------------------------------- /bindings/haskell/src/include/unicorn_wrapper.h: -------------------------------------------------------------------------------- 1 | #ifndef UNICORN_WRAPPER_H 2 | #define UNICORN_WRAPPER_H 3 | 4 | #include 5 | #include 6 | 7 | /* 8 | * Wrap Unicorn's uc_close function and ignore the returned error code. 9 | */ 10 | void uc_close_wrapper(uc_engine *uc); 11 | 12 | /* 13 | * Doesn't actually do anything. 14 | */ 15 | void uc_close_dummy(uc_engine *uc); 16 | 17 | /* 18 | * Wrappers for register read/write functions that accept int64_t pointers. 19 | */ 20 | uc_err uc_reg_write_wrapper(uc_engine *uc, int regid, const int64_t *value); 21 | uc_err uc_reg_read_wrapper(uc_engine *uc, int regid, int64_t *value); 22 | uc_err uc_reg_write_batch_wrapper(uc_engine *uc, int *regs, int64_t *vals, int count); 23 | uc_err uc_reg_read_batch_wrapper(uc_engine *uc, int *regs, int64_t *vals, int count); 24 | 25 | /* 26 | * Wrap Unicorn's uc_free function and ignore the returned error code. 27 | */ 28 | void uc_free_wrapper(void *context); 29 | 30 | #endif 31 | -------------------------------------------------------------------------------- /bindings/java/Makefile: -------------------------------------------------------------------------------- 1 | .PHONY: gen_const clean jar all lib samples install 2 | 3 | all: gen_const 4 | $(MAKE) -f Makefile.build all 5 | 6 | lib: 7 | $(MAKE) -f Makefile.build lib 8 | 9 | samples: 10 | $(MAKE) -f Makefile.build samples 11 | 12 | jar: 13 | $(MAKE) -f Makefile.build jar 14 | 15 | install: lib jar 16 | $(MAKE) -f Makefile.build install 17 | 18 | uninstall: 19 | $(MAKE) -f Makefile.build uninstall 20 | 21 | gen_const: 22 | cd .. && python const_generator.py java 23 | 24 | clean: 25 | rm -f unicorn/*.class 26 | rm -f samples/*.class 27 | rm -f *.so 28 | rm -f *.dylib 29 | rm -f *.dll 30 | rm -f unicorn_Unicorn.o 31 | -------------------------------------------------------------------------------- /bindings/java/README.TXT: -------------------------------------------------------------------------------- 1 | This documentation explains how to install the Java binding for Unicorn 2 | from source. 3 | 4 | 0. Install the core engine as dependency 5 | 6 | Follow README in the root directory to compile & install the core. 7 | 8 | On *nix, this can simply done by: 9 | 10 | $ sudo ./make.sh install 11 | 12 | 13 | 1. Install a JDK for your platform. When done, make sure the JDK tools 14 | are in your PATH. 15 | 16 | 2. Change directories into the java bindings, build and install 17 | 18 | $ cd bindings/java 19 | $ make 20 | $ sudo make install 21 | $ make samples 22 | 23 | The samples directory contains some sample code to show how to use Unicorn API. 24 | 25 | - Sample_.java 26 | These show how to access architecture-specific information for each 27 | architecture. 28 | 29 | - Shellcode.java 30 | This shows how to analyze a Linux shellcode. 31 | 32 | - SampleNetworkAuditing.java 33 | Unicorn sample for auditing network connection and file handling in shellcode. 34 | 35 | To uninstall Java binding for Unicorn: 36 | 37 | $ sudo make uninstall 38 | -------------------------------------------------------------------------------- /bindings/java/src/main/java/unicorn/BlockHook.java: -------------------------------------------------------------------------------- 1 | /* 2 | 3 | Java bindings for the Unicorn Emulator Engine 4 | 5 | Copyright(c) 2015 Chris Eagle 6 | 7 | This program is free software; you can redistribute it and/or 8 | modify it under the terms of the GNU General Public License 9 | version 2 as published by the Free Software Foundation. 10 | 11 | This program is distributed in the hope that it will be useful, 12 | but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | GNU General Public License for more details. 15 | 16 | You should have received a copy of the GNU General Public License 17 | along with this program; if not, write to the Free Software 18 | Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. 19 | 20 | */ 21 | 22 | package unicorn; 23 | 24 | public interface BlockHook extends Hook { 25 | 26 | void hook(Unicorn u, long address, int size, Object user); 27 | 28 | } 29 | 30 | -------------------------------------------------------------------------------- /bindings/java/src/main/java/unicorn/CodeHook.java: -------------------------------------------------------------------------------- 1 | /* 2 | 3 | Java bindings for the Unicorn Emulator Engine 4 | 5 | Copyright(c) 2015 Chris Eagle 6 | 7 | This program is free software; you can redistribute it and/or 8 | modify it under the terms of the GNU General Public License 9 | version 2 as published by the Free Software Foundation. 10 | 11 | This program is distributed in the hope that it will be useful, 12 | but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | GNU General Public License for more details. 15 | 16 | You should have received a copy of the GNU General Public License 17 | along with this program; if not, write to the Free Software 18 | Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. 19 | 20 | */ 21 | 22 | package unicorn; 23 | 24 | public interface CodeHook extends Hook { 25 | 26 | void hook(Unicorn u, long address, int size, Object user); 27 | 28 | } 29 | 30 | -------------------------------------------------------------------------------- /bindings/java/src/main/java/unicorn/DebugHook.java: -------------------------------------------------------------------------------- 1 | /* 2 | 3 | Java bindings for the Unicorn Emulator Engine 4 | 5 | Copyright(c) 2015 Chris Eagle 6 | 7 | This program is free software; you can redistribute it and/or 8 | modify it under the terms of the GNU General Public License 9 | version 2 as published by the Free Software Foundation. 10 | 11 | This program is distributed in the hope that it will be useful, 12 | but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | GNU General Public License for more details. 15 | 16 | You should have received a copy of the GNU General Public License 17 | along with this program; if not, write to the Free Software 18 | Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. 19 | 20 | */ 21 | 22 | package unicorn; 23 | 24 | public interface DebugHook extends CodeHook { 25 | 26 | void onBreak(Unicorn u, long address, int size, Object user); 27 | 28 | } 29 | 30 | -------------------------------------------------------------------------------- /bindings/java/src/main/java/unicorn/EventMemHook.java: -------------------------------------------------------------------------------- 1 | /* 2 | 3 | Java bindings for the Unicorn Emulator Engine 4 | 5 | Copyright(c) 2015 Chris Eagle 6 | 7 | This program is free software; you can redistribute it and/or 8 | modify it under the terms of the GNU General Public License 9 | version 2 as published by the Free Software Foundation. 10 | 11 | This program is distributed in the hope that it will be useful, 12 | but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | GNU General Public License for more details. 15 | 16 | You should have received a copy of the GNU General Public License 17 | along with this program; if not, write to the Free Software 18 | Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. 19 | 20 | */ 21 | 22 | package unicorn; 23 | 24 | public interface EventMemHook extends Hook { 25 | 26 | boolean hook(Unicorn u, long address, int size, long value, Object user); 27 | 28 | } 29 | 30 | -------------------------------------------------------------------------------- /bindings/java/src/main/java/unicorn/Hook.java: -------------------------------------------------------------------------------- 1 | /* 2 | 3 | Java bindings for the Unicorn Emulator Engine 4 | 5 | Copyright(c) 2015 Chris Eagle 6 | 7 | This program is free software; you can redistribute it and/or 8 | modify it under the terms of the GNU General Public License 9 | version 2 as published by the Free Software Foundation. 10 | 11 | This program is distributed in the hope that it will be useful, 12 | but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | GNU General Public License for more details. 15 | 16 | You should have received a copy of the GNU General Public License 17 | along with this program; if not, write to the Free Software 18 | Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. 19 | 20 | */ 21 | 22 | package unicorn; 23 | 24 | /** 25 | * Base class for all unicorn hooking interfaces 26 | */ 27 | 28 | public interface Hook { 29 | } 30 | -------------------------------------------------------------------------------- /bindings/java/src/main/java/unicorn/InHook.java: -------------------------------------------------------------------------------- 1 | /* 2 | 3 | Java bindings for the Unicorn Emulator Engine 4 | 5 | Copyright(c) 2015 Chris Eagle 6 | 7 | This program is free software; you can redistribute it and/or 8 | modify it under the terms of the GNU General Public License 9 | version 2 as published by the Free Software Foundation. 10 | 11 | This program is distributed in the hope that it will be useful, 12 | but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | GNU General Public License for more details. 15 | 16 | You should have received a copy of the GNU General Public License 17 | along with this program; if not, write to the Free Software 18 | Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. 19 | 20 | */ 21 | 22 | package unicorn; 23 | 24 | public interface InHook extends Hook { 25 | 26 | int hook(Unicorn u, int port, int size, Object user); 27 | 28 | } 29 | 30 | -------------------------------------------------------------------------------- /bindings/java/src/main/java/unicorn/InterruptHook.java: -------------------------------------------------------------------------------- 1 | /* 2 | 3 | Java bindings for the Unicorn Emulator Engine 4 | 5 | Copyright(c) 2015 Chris Eagle 6 | 7 | This program is free software; you can redistribute it and/or 8 | modify it under the terms of the GNU General Public License 9 | version 2 as published by the Free Software Foundation. 10 | 11 | This program is distributed in the hope that it will be useful, 12 | but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | GNU General Public License for more details. 15 | 16 | You should have received a copy of the GNU General Public License 17 | along with this program; if not, write to the Free Software 18 | Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. 19 | 20 | */ 21 | 22 | package unicorn; 23 | 24 | public interface InterruptHook extends Hook { 25 | 26 | void hook(Unicorn u, int intno, Object user); 27 | 28 | } 29 | 30 | -------------------------------------------------------------------------------- /bindings/java/src/main/java/unicorn/M68kConst.java: -------------------------------------------------------------------------------- 1 | // For Unicorn Engine. AUTO-GENERATED FILE, DO NOT EDIT 2 | 3 | package unicorn; 4 | 5 | public interface M68kConst { 6 | 7 | // M68K registers 8 | 9 | int UC_M68K_REG_INVALID = 0; 10 | int UC_M68K_REG_A0 = 1; 11 | int UC_M68K_REG_A1 = 2; 12 | int UC_M68K_REG_A2 = 3; 13 | int UC_M68K_REG_A3 = 4; 14 | int UC_M68K_REG_A4 = 5; 15 | int UC_M68K_REG_A5 = 6; 16 | int UC_M68K_REG_A6 = 7; 17 | int UC_M68K_REG_A7 = 8; 18 | int UC_M68K_REG_D0 = 9; 19 | int UC_M68K_REG_D1 = 10; 20 | int UC_M68K_REG_D2 = 11; 21 | int UC_M68K_REG_D3 = 12; 22 | int UC_M68K_REG_D4 = 13; 23 | int UC_M68K_REG_D5 = 14; 24 | int UC_M68K_REG_D6 = 15; 25 | int UC_M68K_REG_D7 = 16; 26 | int UC_M68K_REG_SR = 17; 27 | int UC_M68K_REG_PC = 18; 28 | int UC_M68K_REG_ENDING = 19; 29 | 30 | } 31 | -------------------------------------------------------------------------------- /bindings/java/src/main/java/unicorn/MemHook.java: -------------------------------------------------------------------------------- 1 | /* 2 | 3 | Java bindings for the Unicorn Emulator Engine 4 | 5 | Copyright(c) 2015 Chris Eagle 6 | 7 | This program is free software; you can redistribute it and/or 8 | modify it under the terms of the GNU General Public License 9 | version 2 as published by the Free Software Foundation. 10 | 11 | This program is distributed in the hope that it will be useful, 12 | but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | GNU General Public License for more details. 15 | 16 | You should have received a copy of the GNU General Public License 17 | along with this program; if not, write to the Free Software 18 | Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. 19 | 20 | */ 21 | 22 | package unicorn; 23 | 24 | public interface MemHook extends ReadHook,WriteHook { 25 | 26 | } 27 | 28 | -------------------------------------------------------------------------------- /bindings/java/src/main/java/unicorn/MemRegion.java: -------------------------------------------------------------------------------- 1 | /* 2 | 3 | Java bindings for the Unicorn Emulator Engine 4 | 5 | Copyright(c) 2016 Chris Eagle 6 | 7 | This program is free software; you can redistribute it and/or 8 | modify it under the terms of the GNU General Public License 9 | version 2 as published by the Free Software Foundation. 10 | 11 | This program is distributed in the hope that it will be useful, 12 | but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | GNU General Public License for more details. 15 | 16 | You should have received a copy of the GNU General Public License 17 | along with this program; if not, write to the Free Software 18 | Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. 19 | 20 | */ 21 | 22 | package unicorn; 23 | 24 | public class MemRegion { 25 | 26 | public long begin; 27 | public long end; 28 | public int perms; 29 | 30 | public MemRegion(long begin, long end, int perms) { 31 | this.begin = begin; 32 | this.end = end; 33 | this.perms = perms; 34 | } 35 | 36 | } 37 | 38 | -------------------------------------------------------------------------------- /bindings/java/src/main/java/unicorn/OutHook.java: -------------------------------------------------------------------------------- 1 | /* 2 | 3 | Java bindings for the Unicorn Emulator Engine 4 | 5 | Copyright(c) 2015 Chris Eagle 6 | 7 | This program is free software; you can redistribute it and/or 8 | modify it under the terms of the GNU General Public License 9 | version 2 as published by the Free Software Foundation. 10 | 11 | This program is distributed in the hope that it will be useful, 12 | but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | GNU General Public License for more details. 15 | 16 | You should have received a copy of the GNU General Public License 17 | along with this program; if not, write to the Free Software 18 | Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. 19 | 20 | */ 21 | 22 | package unicorn; 23 | 24 | public interface OutHook extends Hook { 25 | 26 | void hook(Unicorn u, int port, int size, int value, Object user); 27 | 28 | } 29 | 30 | -------------------------------------------------------------------------------- /bindings/java/src/main/java/unicorn/ReadHook.java: -------------------------------------------------------------------------------- 1 | /* 2 | 3 | Java bindings for the Unicorn Emulator Engine 4 | 5 | Copyright(c) 2015 Chris Eagle 6 | 7 | This program is free software; you can redistribute it and/or 8 | modify it under the terms of the GNU General Public License 9 | version 2 as published by the Free Software Foundation. 10 | 11 | This program is distributed in the hope that it will be useful, 12 | but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | GNU General Public License for more details. 15 | 16 | You should have received a copy of the GNU General Public License 17 | along with this program; if not, write to the Free Software 18 | Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. 19 | 20 | */ 21 | 22 | package unicorn; 23 | 24 | public interface ReadHook extends Hook { 25 | 26 | void hook(Unicorn u, long address, int size, Object user); 27 | 28 | } 29 | 30 | -------------------------------------------------------------------------------- /bindings/java/src/main/java/unicorn/SyscallHook.java: -------------------------------------------------------------------------------- 1 | /* 2 | 3 | Java bindings for the Unicorn Emulator Engine 4 | 5 | Copyright(c) 2015 Chris Eagle 6 | 7 | This program is free software; you can redistribute it and/or 8 | modify it under the terms of the GNU General Public License 9 | version 2 as published by the Free Software Foundation. 10 | 11 | This program is distributed in the hope that it will be useful, 12 | but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | GNU General Public License for more details. 15 | 16 | You should have received a copy of the GNU General Public License 17 | along with this program; if not, write to the Free Software 18 | Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. 19 | 20 | */ 21 | 22 | package unicorn; 23 | 24 | public interface SyscallHook extends Hook { 25 | 26 | void hook(Unicorn u, Object user); 27 | 28 | } 29 | 30 | -------------------------------------------------------------------------------- /bindings/java/src/main/java/unicorn/UnicornException.java: -------------------------------------------------------------------------------- 1 | /* 2 | 3 | Java bindings for the Unicorn Emulator Engine 4 | 5 | Copyright(c) 2015 Chris Eagle 6 | 7 | This program is free software; you can redistribute it and/or 8 | modify it under the terms of the GNU General Public License 9 | version 2 as published by the Free Software Foundation. 10 | 11 | This program is distributed in the hope that it will be useful, 12 | but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | GNU General Public License for more details. 15 | 16 | You should have received a copy of the GNU General Public License 17 | along with this program; if not, write to the Free Software 18 | Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. 19 | 20 | */ 21 | 22 | package unicorn; 23 | 24 | public class UnicornException extends RuntimeException { 25 | 26 | public UnicornException() { 27 | super(); 28 | } 29 | 30 | public UnicornException(String msg) { 31 | super(msg); 32 | } 33 | 34 | } 35 | -------------------------------------------------------------------------------- /bindings/java/src/main/java/unicorn/WriteHook.java: -------------------------------------------------------------------------------- 1 | /* 2 | 3 | Java bindings for the Unicorn Emulator Engine 4 | 5 | Copyright(c) 2015 Chris Eagle 6 | 7 | This program is free software; you can redistribute it and/or 8 | modify it under the terms of the GNU General Public License 9 | version 2 as published by the Free Software Foundation. 10 | 11 | This program is distributed in the hope that it will be useful, 12 | but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | GNU General Public License for more details. 15 | 16 | You should have received a copy of the GNU General Public License 17 | along with this program; if not, write to the Free Software 18 | Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. 19 | 20 | */ 21 | 22 | package unicorn; 23 | 24 | public interface WriteHook extends Hook { 25 | 26 | void hook(Unicorn u, long address, int size, long value, Object user); 27 | 28 | } 29 | 30 | -------------------------------------------------------------------------------- /bindings/java/src/main/java/unicorn/X86_MMR.java: -------------------------------------------------------------------------------- 1 | /* 2 | 3 | Java bindings for the Unicorn Emulator Engine 4 | 5 | Copyright(c) 2016 Chris Eagle 6 | 7 | This program is free software; you can redistribute it and/or 8 | modify it under the terms of the GNU General Public License 9 | version 2 as published by the Free Software Foundation. 10 | 11 | This program is distributed in the hope that it will be useful, 12 | but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | GNU General Public License for more details. 15 | 16 | You should have received a copy of the GNU General Public License 17 | along with this program; if not, write to the Free Software 18 | Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. 19 | 20 | */ 21 | 22 | package unicorn; 23 | 24 | public class X86_MMR { 25 | 26 | public long base; 27 | public int limit; 28 | public int flags; 29 | public short selector; 30 | 31 | public X86_MMR(long base, int limit, int flags, short selector) { 32 | this.base = base; 33 | this.limit = limit; 34 | this.flags = flags; 35 | this.selector = selector; 36 | } 37 | 38 | public X86_MMR(long base, int limit) { 39 | this.base = base; 40 | this.limit = limit; 41 | selector = 0; 42 | flags = 0; 43 | } 44 | 45 | } 46 | 47 | -------------------------------------------------------------------------------- /bindings/java/src/main/resources/natives/linux_64/libunicorn_java.so: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/bindings/java/src/main/resources/natives/linux_64/libunicorn_java.so -------------------------------------------------------------------------------- /bindings/java/src/main/resources/natives/linux_arm64/libunicorn_java.so: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/bindings/java/src/main/resources/natives/linux_arm64/libunicorn_java.so -------------------------------------------------------------------------------- /bindings/java/src/main/resources/natives/osx_64/libunicorn_java.dylib: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/bindings/java/src/main/resources/natives/osx_64/libunicorn_java.dylib -------------------------------------------------------------------------------- /bindings/java/src/main/resources/natives/osx_arm64/libunicorn_java.dylib: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/bindings/java/src/main/resources/natives/osx_arm64/libunicorn_java.dylib -------------------------------------------------------------------------------- /bindings/java/src/main/resources/natives/windows_32/unicorn_java.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/bindings/java/src/main/resources/natives/windows_32/unicorn_java.dll -------------------------------------------------------------------------------- /bindings/java/src/main/resources/natives/windows_64/unicorn_java.dll: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/bindings/java/src/main/resources/natives/windows_64/unicorn_java.dll -------------------------------------------------------------------------------- /bindings/java/unicorn_Unicorn_NewHook.h: -------------------------------------------------------------------------------- 1 | /* DO NOT EDIT THIS FILE - it is machine generated */ 2 | #include 3 | /* Header for class unicorn_Unicorn_NewHook */ 4 | 5 | #ifndef _Included_unicorn_Unicorn_NewHook 6 | #define _Included_unicorn_Unicorn_NewHook 7 | #ifdef __cplusplus 8 | extern "C" { 9 | #endif 10 | #ifdef __cplusplus 11 | } 12 | #endif 13 | #endif 14 | -------------------------------------------------------------------------------- /bindings/java/unicorn_Unicorn_Tuple.h: -------------------------------------------------------------------------------- 1 | /* DO NOT EDIT THIS FILE - it is machine generated */ 2 | #include 3 | /* Header for class unicorn_Unicorn_Tuple */ 4 | 5 | #ifndef _Included_unicorn_Unicorn_Tuple 6 | #define _Included_unicorn_Unicorn_Tuple 7 | #ifdef __cplusplus 8 | extern "C" { 9 | #endif 10 | #ifdef __cplusplus 11 | } 12 | #endif 13 | #endif 14 | -------------------------------------------------------------------------------- /bindings/java/unicorn_Unicorn_UnHook.h: -------------------------------------------------------------------------------- 1 | /* DO NOT EDIT THIS FILE - it is machine generated */ 2 | #include 3 | /* Header for class unicorn_Unicorn_UnHook */ 4 | 5 | #ifndef _Included_unicorn_Unicorn_UnHook 6 | #define _Included_unicorn_Unicorn_UnHook 7 | #ifdef __cplusplus 8 | extern "C" { 9 | #endif 10 | #ifdef __cplusplus 11 | } 12 | #endif 13 | #endif 14 | -------------------------------------------------------------------------------- /bindings/pascal/unicorn/M68kConst.pas: -------------------------------------------------------------------------------- 1 | // For Unicorn Engine. AUTO-GENERATED FILE, DO NOT EDIT 2 | 3 | unit M68kConst; 4 | 5 | interface 6 | 7 | const 8 | // M68K registers 9 | 10 | UC_M68K_REG_INVALID = 0; 11 | UC_M68K_REG_A0 = 1; 12 | UC_M68K_REG_A1 = 2; 13 | UC_M68K_REG_A2 = 3; 14 | UC_M68K_REG_A3 = 4; 15 | UC_M68K_REG_A4 = 5; 16 | UC_M68K_REG_A5 = 6; 17 | UC_M68K_REG_A6 = 7; 18 | UC_M68K_REG_A7 = 8; 19 | UC_M68K_REG_D0 = 9; 20 | UC_M68K_REG_D1 = 10; 21 | UC_M68K_REG_D2 = 11; 22 | UC_M68K_REG_D3 = 12; 23 | UC_M68K_REG_D4 = 13; 24 | UC_M68K_REG_D5 = 14; 25 | UC_M68K_REG_D6 = 15; 26 | UC_M68K_REG_D7 = 16; 27 | UC_M68K_REG_SR = 17; 28 | UC_M68K_REG_PC = 18; 29 | UC_M68K_REG_ENDING = 19; 30 | 31 | implementation 32 | end. -------------------------------------------------------------------------------- /bindings/python/MANIFEST.in: -------------------------------------------------------------------------------- 1 | recursive-include src * 2 | recursive-include prebuilt * 3 | include LICENSE.TXT 4 | include README.TXT 5 | -------------------------------------------------------------------------------- /bindings/python/README.TXT: -------------------------------------------------------------------------------- 1 | This documentation explains how to install the python binding for Unicorn 2 | from source. 3 | 4 | 1. Installing on Linux: 5 | 6 | $ sudo python setup.py install 7 | 8 | This will build the core C library, package it with the python bindings, 9 | and install it to your system. 10 | 11 | If you want to prevent the build of the native library during the python installation, 12 | set the environment variable LIBUNICORN_PATH. You may also set this to a directory 13 | containing libunicorn.so if you wish to use a verison of the native library other than 14 | the globally installed one. 15 | 16 | 17 | 2. Installing on Windows: 18 | 19 | Run the following command in command prompt: 20 | 21 | C:\> C:\location_to_python\python.exe setup.py install 22 | 23 | Next, copy all the DLL files from the 'Core engine for Windows' package available 24 | on the Unicorn download page and paste it in the path: 25 | 26 | C:\location_to_python\Lib\site-packages\unicorn\ 27 | 28 | 29 | 3. Sample code 30 | 31 | This directory contains some sample code to show how to use Unicorn API. 32 | 33 | - sample_.py 34 | These code show how to access architecture-specific information for each 35 | architecture. 36 | 37 | - shellcode.py 38 | This shows how to analyze a Linux shellcode. 39 | 40 | - sample_network_auditing.py 41 | This shows how to analyze & interpret Linux shellcode. 42 | -------------------------------------------------------------------------------- /bindings/python/build_wheel.sh: -------------------------------------------------------------------------------- 1 | #!/bin/bash 2 | set -e -x 3 | 4 | cd bindings/python 5 | 6 | # Compile wheels 7 | if [ -f /opt/python/cp36-cp36m/bin/python ];then 8 | /opt/python/cp36-cp36m/bin/python setup.py bdist_wheel 9 | else 10 | python3 setup.py bdist_wheel 11 | fi 12 | cd dist 13 | auditwheel repair *.whl 14 | mv -f wheelhouse/*.whl . 15 | -------------------------------------------------------------------------------- /bindings/python/prebuilt/.gitkeep: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/bindings/python/prebuilt/.gitkeep -------------------------------------------------------------------------------- /bindings/python/sample_all.sh: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | 3 | ./sample_x86.py 4 | echo "==========================" 5 | ./shellcode.py 6 | echo "==========================" 7 | ./sample_arm.py 8 | echo "==========================" 9 | ./sample_arm64.py 10 | echo "==========================" 11 | ./sample_mips.py 12 | echo "==========================" 13 | ./sample_sparc.py 14 | echo "==========================" 15 | ./sample_m68k.py 16 | -------------------------------------------------------------------------------- /bindings/python/setup.cfg: -------------------------------------------------------------------------------- 1 | [bdist_wheel] 2 | universal=1 3 | -------------------------------------------------------------------------------- /bindings/python/unicorn/__init__.py: -------------------------------------------------------------------------------- 1 | # Unicorn Python bindings, by Nguyen Anh Quynnh 2 | from . import arm_const, arm64_const, mips_const, sparc_const, m68k_const, x86_const 3 | from .unicorn_const import * 4 | from .unicorn import Uc, uc_version, uc_arch_supported, version_bind, debug, UcError, __version__ 5 | -------------------------------------------------------------------------------- /bindings/python/unicorn/m68k_const.py: -------------------------------------------------------------------------------- 1 | # For Unicorn Engine. AUTO-GENERATED FILE, DO NOT EDIT [m68k_const.py] 2 | 3 | # M68K registers 4 | 5 | UC_M68K_REG_INVALID = 0 6 | UC_M68K_REG_A0 = 1 7 | UC_M68K_REG_A1 = 2 8 | UC_M68K_REG_A2 = 3 9 | UC_M68K_REG_A3 = 4 10 | UC_M68K_REG_A4 = 5 11 | UC_M68K_REG_A5 = 6 12 | UC_M68K_REG_A6 = 7 13 | UC_M68K_REG_A7 = 8 14 | UC_M68K_REG_D0 = 9 15 | UC_M68K_REG_D1 = 10 16 | UC_M68K_REG_D2 = 11 17 | UC_M68K_REG_D3 = 12 18 | UC_M68K_REG_D4 = 13 19 | UC_M68K_REG_D5 = 14 20 | UC_M68K_REG_D6 = 15 21 | UC_M68K_REG_D7 = 16 22 | UC_M68K_REG_SR = 17 23 | UC_M68K_REG_PC = 18 24 | UC_M68K_REG_ENDING = 19 25 | -------------------------------------------------------------------------------- /bindings/ruby/Makefile: -------------------------------------------------------------------------------- 1 | # Ruby binding for Unicorn engine. Sascha Schirra 2 | 3 | .PHONY: gen_const 4 | 5 | # Use bundle install && rake to install gem and test 6 | install: gen_const 7 | cd unicorn_gem && rake build 8 | cd unicorn_gem && gem install --local pkg/unicorn-engine-1.0.1.gem 9 | 10 | gen_const: 11 | cd .. && python const_generator.py ruby 12 | -------------------------------------------------------------------------------- /bindings/ruby/README.md: -------------------------------------------------------------------------------- 1 | # Installation 2 | 3 | ## Software requirements 4 | 5 | ### Linux 6 | - ruby >= 1.9.3 7 | - rubygems 8 | - make 9 | - gcc 10 | 11 | ### Mac OS 12 | - ruby >= 1.9.3 13 | - rubygems 14 | - make 15 | - XCode 16 | 17 | ## Install unicorn 18 | * cd path_to_unicorn 19 | * ./make.sh install 20 | 21 | ## Install ruby binding 22 | * cd bindings/ruby 23 | * make install 24 | -------------------------------------------------------------------------------- /bindings/ruby/unicorn_gem/Gemfile: -------------------------------------------------------------------------------- 1 | source 'https://rubygems.org' 2 | 3 | gemspec 4 | -------------------------------------------------------------------------------- /bindings/ruby/unicorn_gem/Rakefile: -------------------------------------------------------------------------------- 1 | require "bundler/gem_tasks" 2 | task :default => :spec 3 | -------------------------------------------------------------------------------- /bindings/ruby/unicorn_gem/ext/extconf.rb: -------------------------------------------------------------------------------- 1 | require 'mkmf' 2 | 3 | extension_name = 'unicorn_engine' 4 | 5 | dir_config(extension_name) 6 | have_library('unicorn') 7 | 8 | create_makefile(extension_name) 9 | -------------------------------------------------------------------------------- /bindings/ruby/unicorn_gem/ext/types.h: -------------------------------------------------------------------------------- 1 | /* 2 | 3 | Ruby bindings for the Unicorn Emulator Engine 4 | 5 | Copyright(c) 2016 Sascha Schirra 6 | 7 | This program is free software; you can redistribute it and/or 8 | modify it under the terms of the GNU General Public License 9 | version 2 as published by the Free Software Foundation. 10 | 11 | This program is distributed in the hope that it will be useful, 12 | but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14 | GNU General Public License for more details. 15 | 16 | You should have received a copy of the GNU General Public License 17 | along with this program; if not, write to the Free Software 18 | Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. 19 | 20 | */ 21 | 22 | typedef struct uc_x86_float80 { 23 | uint64_t mantissa; 24 | uint16_t exponent; 25 | } uc_x86_float80; 26 | 27 | 28 | struct hook { 29 | uc_hook trace; 30 | VALUE cb; 31 | VALUE ud; 32 | VALUE rUc; 33 | }; 34 | -------------------------------------------------------------------------------- /bindings/ruby/unicorn_gem/lib/unicorn_engine/m68k_const.rb: -------------------------------------------------------------------------------- 1 | # For Unicorn Engine. AUTO-GENERATED FILE, DO NOT EDIT [m68k_const.rb] 2 | 3 | module UnicornEngine 4 | 5 | # M68K registers 6 | 7 | UC_M68K_REG_INVALID = 0 8 | UC_M68K_REG_A0 = 1 9 | UC_M68K_REG_A1 = 2 10 | UC_M68K_REG_A2 = 3 11 | UC_M68K_REG_A3 = 4 12 | UC_M68K_REG_A4 = 5 13 | UC_M68K_REG_A5 = 6 14 | UC_M68K_REG_A6 = 7 15 | UC_M68K_REG_A7 = 8 16 | UC_M68K_REG_D0 = 9 17 | UC_M68K_REG_D1 = 10 18 | UC_M68K_REG_D2 = 11 19 | UC_M68K_REG_D3 = 12 20 | UC_M68K_REG_D4 = 13 21 | UC_M68K_REG_D5 = 14 22 | UC_M68K_REG_D6 = 15 23 | UC_M68K_REG_D7 = 16 24 | UC_M68K_REG_SR = 17 25 | UC_M68K_REG_PC = 18 26 | UC_M68K_REG_ENDING = 19 27 | end -------------------------------------------------------------------------------- /bindings/ruby/unicorn_gem/lib/unicorn_engine/version.rb: -------------------------------------------------------------------------------- 1 | module Unicorn 2 | VERSION = "1.0.1" 3 | end 4 | -------------------------------------------------------------------------------- /bindings/ruby/unicorn_gem/pkg/.gitignore: -------------------------------------------------------------------------------- 1 | /.bundle/ 2 | /.yardoc 3 | /Gemfile.lock 4 | /_yardoc/ 5 | /coverage/ 6 | /doc/ 7 | /pkg/ 8 | /spec/reports/ 9 | /tmp/ 10 | *.gem 11 | -------------------------------------------------------------------------------- /bindings/ruby/unicorn_gem/unicorn-engine.gemspec: -------------------------------------------------------------------------------- 1 | # coding: utf-8 2 | lib = File.expand_path('../lib', __FILE__) 3 | $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib) 4 | require 'unicorn_engine/version' 5 | 6 | Gem::Specification.new do |spec| 7 | spec.name = "unicorn-engine" 8 | spec.version = Unicorn::VERSION 9 | spec.authors = ["Sascha Schirra"] 10 | spec.email = ["sashs@scoding.de"] 11 | spec.license = 'GPL-2.0' 12 | spec.summary = %q{Ruby binding for Unicorn-Engine} 13 | spec.description = %q{Ruby binding for Unicorn-Engine } 14 | spec.homepage = "https://unicorn-engine.org" 15 | 16 | spec.files = Dir["lib/unicorn_engine/*.rb"] + Dir["ext/unicorn.c"] + Dir["ext/unicorn.h"] + Dir["ext/types.h"] + Dir["ext/extconf.rb"] 17 | spec.require_paths = ["lib","ext"] 18 | spec.extensions = ["ext/extconf.rb"] 19 | spec.add_development_dependency "bundler", "~> 1.11" 20 | spec.add_development_dependency "rake", "~> 10.0" 21 | end 22 | -------------------------------------------------------------------------------- /bindings/vb6/.gitattributes: -------------------------------------------------------------------------------- 1 | *.frm eol=crlf 2 | *.bas eol=crlf 3 | *.cls eol=crlf 4 | *.ctl eol=crlf 5 | *.vbp eol=crlf 6 | *.txt eol=crlf 7 | *.cpp eol=crlf 8 | *.tli eol=crlf 9 | *.tlh eol=crlf 10 | *.vcproj eol=crlf 11 | *.sln eol=crlf 12 | -------------------------------------------------------------------------------- /bindings/vb6/Project1.vbp: -------------------------------------------------------------------------------- 1 | Type=Exe 2 | Form=Form1.frm 3 | Reference=*\G{00020430-0000-0000-C000-000000000046}#2.0#0#C:\WINDOWS\system32\stdole2.tlb#OLE Automation 4 | Module=uc_def; uc_def.bas 5 | Module=misc; misc.bas 6 | Class=ucIntel32; ucIntel32.cls 7 | Class=CMemRegion; CMemRegion.cls 8 | IconForm="Form1" 9 | Startup="Form1" 10 | HelpFile="" 11 | ExeName32="vb6Test.exe" 12 | Command32="" 13 | Name="Project1" 14 | HelpContextID="0" 15 | CompatibleMode="0" 16 | MajorVer=1 17 | MinorVer=0 18 | RevisionVer=0 19 | AutoIncrementVer=0 20 | ServerSupportFiles=0 21 | VersionCompanyName="sandsprite" 22 | CompilationType=0 23 | OptimizationType=0 24 | FavorPentiumPro(tm)=0 25 | CodeViewDebugInfo=-1 26 | NoAliasing=0 27 | BoundsCheck=0 28 | OverflowCheck=0 29 | FlPointCheck=0 30 | FDIVCheck=0 31 | UnroundedFP=0 32 | StartMode=0 33 | Unattended=0 34 | Retained=0 35 | ThreadPerObject=0 36 | MaxNumberOfThreads=1 37 | 38 | [MS Transaction Server] 39 | AutoRefresh=1 40 | 41 | [fastBuild] 42 | fullPath=%ap%\vb6Test.exe 43 | -------------------------------------------------------------------------------- /bindings/vb6/Project1.vbw: -------------------------------------------------------------------------------- 1 | Form1 = 39, 35, 1148, 674, , 22, 22, 1090, 631, C 2 | uc_def = 56, 12, 1177, 758, 3 | misc = 44, 44, 1121, 685, 4 | ucIntel32 = 88, 33, 1136, 684, 5 | CMemRegion = 110, 110, 1026, 639, 6 | -------------------------------------------------------------------------------- /bindings/vb6/screenshot.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/bindings/vb6/screenshot.png -------------------------------------------------------------------------------- /bindings/vb6/ucvbshim.sln: -------------------------------------------------------------------------------- 1 |  2 | Microsoft Visual Studio Solution File, Format Version 10.00 3 | # Visual Studio 2008 4 | Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "ucvbshim", "ucvbshim.vcproj", "{6FC797B7-2985-49C8-92CD-CA985AF3511C}" 5 | EndProject 6 | Global 7 | GlobalSection(SolutionConfigurationPlatforms) = preSolution 8 | Debug|Win32 = Debug|Win32 9 | Release|Win32 = Release|Win32 10 | EndGlobalSection 11 | GlobalSection(ProjectConfigurationPlatforms) = postSolution 12 | {6FC797B7-2985-49C8-92CD-CA985AF3511C}.Debug|Win32.ActiveCfg = Debug|Win32 13 | {6FC797B7-2985-49C8-92CD-CA985AF3511C}.Debug|Win32.Build.0 = Debug|Win32 14 | {6FC797B7-2985-49C8-92CD-CA985AF3511C}.Release|Win32.ActiveCfg = Release|Win32 15 | {6FC797B7-2985-49C8-92CD-CA985AF3511C}.Release|Win32.Build.0 = Release|Win32 16 | EndGlobalSection 17 | GlobalSection(SolutionProperties) = preSolution 18 | HideSolutionNode = FALSE 19 | EndGlobalSection 20 | EndGlobal 21 | -------------------------------------------------------------------------------- /cmake.sh: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | 3 | # Unicorn Emulator Engine (www.unicorn-engine.org) 4 | # Usage: cmake.sh [x86] [arm] [aarch64] [m68k] [mips] [sparc] 5 | # By chenhuitao 2019 6 | 7 | FLAGS="-DCMAKE_BUILD_TYPE=Release" 8 | 9 | UNICORN_ARCH="${*}" 10 | 11 | if [ -z "${UNICORN_ARCH}" ]; then 12 | cmake "${FLAGS}" .. 13 | else 14 | cmake "${FLAGS}" "-DUNICORN_ARCH=${UNICORN_ARCH}" .. 15 | fi 16 | 17 | make -j8 18 | -------------------------------------------------------------------------------- /config.mk: -------------------------------------------------------------------------------- 1 | # Unicorn Emulator Engine 2 | # By Nguyen Anh Quynh, 2015 3 | 4 | # This file contains all customized compile options for Unicorn emulator. 5 | # Consult docs/COMPILE.md & docs/README.md for more details. 6 | 7 | ################################################################################ 8 | # Compile with debug info when you want to debug code. 9 | # Change this to 'no' for release edition. 10 | 11 | UNICORN_DEBUG ?= yes 12 | 13 | ################################################################################ 14 | # Specify which archs you want to compile in. By default, we build all archs. 15 | 16 | UNICORN_ARCHS ?= x86 m68k arm aarch64 mips sparc 17 | 18 | 19 | ################################################################################ 20 | # Change 'UNICORN_STATIC = yes' to 'UNICORN_STATIC = no' to avoid building 21 | # a static library. 22 | 23 | UNICORN_STATIC ?= yes 24 | 25 | 26 | ################################################################################ 27 | # Change 'UNICORN_SHARED = yes' to 'UNICORN_SHARED = no' to avoid building 28 | # a shared library. 29 | 30 | UNICORN_SHARED ?= yes 31 | -------------------------------------------------------------------------------- /docs/BHUSA2015-unicorn.pdf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/docs/BHUSA2015-unicorn.pdf -------------------------------------------------------------------------------- /docs/COMPILE.md: -------------------------------------------------------------------------------- 1 | To compile Unicorn on Mac OS X, Linux, BSD, Solaris and all kind of nix OS, 2 | see [COMPILE-NIX.md](COMPILE-NIX.md) 3 | 4 | To compile Unicorn on Windows, see [COMPILE-WINDOWS.md](COMPILE-WINDOWS.md) 5 | 6 | To compile Unicorn with CMake on Windows or *nix, see 7 | [COMPILE-CMAKE.md](COMPILE-CMAKE.md) 8 | 9 | Then learn more on how to code your own tools with our samples. 10 | 11 | - For C sample code, see code in directory samples/sample*.c 12 | - For Python sample code, see code in directory bindings/python/sample*.py 13 | - For samples of other bindings, look into directories bindings// 14 | 15 | #Building unicorn - Using vcpkg 16 | 17 | You can download and install unicorn using the [vcpkg](https://github.com/Microsoft/vcpkg) dependency manager: 18 | 19 | git clone https://github.com/Microsoft/vcpkg.git 20 | cd vcpkg 21 | ./bootstrap-vcpkg.sh 22 | ./vcpkg integrate install 23 | ./vcpkg install unicorn 24 | 25 | The unicorn port in vcpkg is kept up to date by Microsoft team members and community contributors. If the version is out of date, please [create an issue or pull request](https://github.com/Microsoft/vcpkg) on the vcpkg repository. -------------------------------------------------------------------------------- /docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/ABkexFCfphu3zIg.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/ABkexFCfphu3zIg.png -------------------------------------------------------------------------------- /docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/DkztJcigHCdmnRp.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/DkztJcigHCdmnRp.png -------------------------------------------------------------------------------- /docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/F3rSByYuNTGDtC1.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/F3rSByYuNTGDtC1.png -------------------------------------------------------------------------------- /docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/I25E9sWcJpGyax7.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/I25E9sWcJpGyax7.png -------------------------------------------------------------------------------- /docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/IZhyWrGebA5tT4i.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/IZhyWrGebA5tT4i.png -------------------------------------------------------------------------------- /docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/K4HMijIVt6lofvT.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/K4HMijIVt6lofvT.png -------------------------------------------------------------------------------- /docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/MbZk8KjQFqJOxmd.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/MbZk8KjQFqJOxmd.png -------------------------------------------------------------------------------- /docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/NExsavSgu4yMbBQ.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/NExsavSgu4yMbBQ.png -------------------------------------------------------------------------------- /docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/OVaHwelNQ4tcLmo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/OVaHwelNQ4tcLmo.png -------------------------------------------------------------------------------- /docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/YCMNcEVyX8GHoPb.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/YCMNcEVyX8GHoPb.png -------------------------------------------------------------------------------- /docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/ZtRKvUoaPTlshJ4.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/ZtRKvUoaPTlshJ4.png -------------------------------------------------------------------------------- /docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/aU1lbmxMjXA5g3K.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/aU1lbmxMjXA5g3K.png -------------------------------------------------------------------------------- /docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/bpu4r8hgzUvO7Pm.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/bpu4r8hgzUvO7Pm.png -------------------------------------------------------------------------------- /docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/dqKBwAWUL7XvypE.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/dqKBwAWUL7XvypE.png -------------------------------------------------------------------------------- /docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/fOnNpSKvjYyc7QB.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/fOnNpSKvjYyc7QB.png -------------------------------------------------------------------------------- /docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/iyodlNFY7hHEOgS.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/iyodlNFY7hHEOgS.png -------------------------------------------------------------------------------- /docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/juNPWvwGUlraKRh.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/juNPWvwGUlraKRh.png -------------------------------------------------------------------------------- /docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/kbrF7NdV6LDxnYI.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/kbrF7NdV6LDxnYI.png -------------------------------------------------------------------------------- /docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/l1AhdxgKE2U3tZB.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/l1AhdxgKE2U3tZB.png -------------------------------------------------------------------------------- /docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/l4HhgDzcJIVvFNU.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/l4HhgDzcJIVvFNU.png -------------------------------------------------------------------------------- /docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/q3JtOQRPl5xTFKp.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/docs/Micro Unicorn-Engine API Documentation/API_Doc_Pic/q3JtOQRPl5xTFKp.png -------------------------------------------------------------------------------- /docs/README.md: -------------------------------------------------------------------------------- 1 | Documention of Unicorn engine. 2 | 3 | * How to compile & install Unicorn. 4 | 5 | http://unicorn-engine.org/docs/ 6 | 7 | * Tutorial on programming with C & Python languages. 8 | 9 | http://unicorn-engine.org/docs/tutorial.html 10 | 11 | * Compare Unicorn & QEMU 12 | 13 | http://unicorn-engine.org/docs/beyond_qemu.html 14 | 15 | * Micro Uncorn-Engine API Documentation in Chinese 16 | 17 | https://github.com/kabeor/Micro-Unicorn-Engine-API-Documentation 18 | -------------------------------------------------------------------------------- /docs/unicorn-logo.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/docs/unicorn-logo.png -------------------------------------------------------------------------------- /docs/unicorn-logo.txt: -------------------------------------------------------------------------------- 1 | /\'. _,. 2 | |:\ \. .'_/ 3 | _.- |(\\ \ .'_.' 4 | _.-' ,__\\ \\_),/ _/ 5 | _:.' .:::::::.___ ,' 6 | // ' ./::::::\, 2015 */ 2 | 3 | #ifndef UC_QEMU_H 4 | #define UC_QEMU_H 5 | 6 | struct uc_struct; 7 | 8 | #define OPC_BUF_SIZE 640 9 | 10 | #include "sysemu/sysemu.h" 11 | #include "sysemu/cpus.h" 12 | #include "exec/cpu-common.h" 13 | #include "exec/memory.h" 14 | 15 | #include "qemu/thread.h" 16 | #include "include/qom/cpu.h" 17 | 18 | #include "vl.h" 19 | 20 | // This two struct is originally from qemu/include/exec/cpu-all.h 21 | // Temporarily moved here since there is circular inclusion. 22 | typedef struct RAMBlock { 23 | struct MemoryRegion *mr; 24 | uint8_t *host; 25 | ram_addr_t offset; 26 | ram_addr_t length; 27 | uint32_t flags; 28 | char idstr[256]; 29 | /* Reads can take either the iothread or the ramlist lock. 30 | * Writes must take both locks. 31 | */ 32 | QTAILQ_ENTRY(RAMBlock) next; 33 | int fd; 34 | } RAMBlock; 35 | 36 | typedef struct { 37 | MemoryRegion *mr; 38 | void *buffer; 39 | hwaddr addr; 40 | hwaddr len; 41 | } BounceBuffer; 42 | 43 | typedef struct RAMList { 44 | /* Protected by the iothread lock. */ 45 | unsigned long *dirty_memory[DIRTY_MEMORY_NUM]; 46 | RAMBlock *mru_block; 47 | QTAILQ_HEAD(, RAMBlock) blocks; 48 | uint32_t version; 49 | } RAMList; 50 | 51 | #endif 52 | -------------------------------------------------------------------------------- /include/unicorn/m68k.h: -------------------------------------------------------------------------------- 1 | /* Unicorn Emulator Engine */ 2 | /* By Nguyen Anh Quynh , 2014-2017 */ 3 | /* This file is released under LGPL2. 4 | See COPYING.LGPL2 in root directory for more details 5 | */ 6 | 7 | #ifndef UNICORN_M68K_H 8 | #define UNICORN_M68K_H 9 | 10 | #ifdef __cplusplus 11 | extern "C" { 12 | #endif 13 | 14 | #ifdef _MSC_VER 15 | #pragma warning(disable:4201) 16 | #endif 17 | 18 | //> M68K registers 19 | typedef enum uc_m68k_reg { 20 | UC_M68K_REG_INVALID = 0, 21 | 22 | UC_M68K_REG_A0, 23 | UC_M68K_REG_A1, 24 | UC_M68K_REG_A2, 25 | UC_M68K_REG_A3, 26 | UC_M68K_REG_A4, 27 | UC_M68K_REG_A5, 28 | UC_M68K_REG_A6, 29 | UC_M68K_REG_A7, 30 | 31 | UC_M68K_REG_D0, 32 | UC_M68K_REG_D1, 33 | UC_M68K_REG_D2, 34 | UC_M68K_REG_D3, 35 | UC_M68K_REG_D4, 36 | UC_M68K_REG_D5, 37 | UC_M68K_REG_D6, 38 | UC_M68K_REG_D7, 39 | 40 | UC_M68K_REG_SR, 41 | UC_M68K_REG_PC, 42 | 43 | UC_M68K_REG_ENDING, // <-- mark the end of the list of registers 44 | } uc_m68k_reg; 45 | 46 | #ifdef __cplusplus 47 | } 48 | #endif 49 | 50 | #endif 51 | -------------------------------------------------------------------------------- /install-cmocka-linux.sh: -------------------------------------------------------------------------------- 1 | #!/bin/sh -ex 2 | mkdir -p cmocka 3 | #wget https://cmocka.org/files/1.1/cmocka-1.1.0.tar.xz -O /tmp/cmocka-1.1.0.tar.xz 4 | wget --no-check-certificate https://cmocka.org/files/1.1/cmocka-1.1.1.tar.xz -P /tmp/ 5 | tar -xf /tmp/cmocka-1.1.1.tar.xz -C /tmp 6 | cd cmocka && cmake -DUNIT_TESTING=On /tmp/cmocka-1.1.1 && make && make test 7 | # cmake builds an so instead of a dll in mingw/msys 8 | if [[ ! -z $MSYSTEM ]]; then 9 | cp src/cmocka.so src/cmocka.dll 10 | fi 11 | # cmocka does not include headers in build 12 | cp -R /tmp/cmocka-1.1.1/include/ . 13 | -------------------------------------------------------------------------------- /msvc.bat: -------------------------------------------------------------------------------- 1 | :: build Unicorn MSVC solution from MSVC prompt 2 | 3 | msbuild msvc/unicorn.sln 4 | -------------------------------------------------------------------------------- /msvc/.gitignore: -------------------------------------------------------------------------------- 1 | unicorn.VC.VC.opendb 2 | unicorn.VC.db 3 | distro 4 | -------------------------------------------------------------------------------- /msvc/samples/mem_apis/mem_apis.vcxproj.filters: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | -------------------------------------------------------------------------------- /msvc/samples/sample_arm/sample_arm.vcxproj.filters: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | -------------------------------------------------------------------------------- /msvc/samples/sample_arm64/sample_arm64.vcxproj.filters: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | -------------------------------------------------------------------------------- /msvc/samples/sample_arm64eb/sample_arm64eb.vcxproj.filters: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | -------------------------------------------------------------------------------- /msvc/samples/sample_armeb/sample_armeb.vcxproj.filters: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | -------------------------------------------------------------------------------- /msvc/samples/sample_batch_reg/sample_batch_reg.vcxproj.filters: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | -------------------------------------------------------------------------------- /msvc/samples/sample_m68k/sample_m68k.vcxproj.filters: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | -------------------------------------------------------------------------------- /msvc/samples/sample_mips/sample_mips.vcxproj.filters: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | -------------------------------------------------------------------------------- /msvc/samples/sample_sparc/sample_sparc.vcxproj.filters: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | -------------------------------------------------------------------------------- /msvc/samples/sample_x86/sample_x86.vcxproj.filters: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | -------------------------------------------------------------------------------- /msvc/samples/sample_x86_32_gdt_and_seg_regs/sample_x86_32_gdt_and_seg_regs.vcxproj.filters: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | -------------------------------------------------------------------------------- /msvc/samples/shellcode/shellcode.vcxproj.filters: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | -------------------------------------------------------------------------------- /msvc/unicorn/aarch64-softmmu/config-target.h: -------------------------------------------------------------------------------- 1 | /* Automatically generated by create_config - do not modify */ 2 | #define TARGET_AARCH64 1 3 | #define TARGET_NAME "aarch64" 4 | #define TARGET_ARM 1 5 | #define CONFIG_SOFTMMU 1 6 | -------------------------------------------------------------------------------- /msvc/unicorn/aarch64eb-softmmu/config-target.h: -------------------------------------------------------------------------------- 1 | /* Automatically generated by create_config - do not modify */ 2 | #define TARGET_AARCH64 1 3 | #define TARGET_NAME "aarch64eb" 4 | #define TARGET_ARM 1 5 | #define TARGET_WORDS_BIGENDIAN 1 6 | #define CONFIG_SOFTMMU 1 7 | -------------------------------------------------------------------------------- /msvc/unicorn/arm-softmmu/config-target.h: -------------------------------------------------------------------------------- 1 | /* Automatically generated by create_config - do not modify */ 2 | #define TARGET_ARM 1 3 | #define TARGET_NAME "arm" 4 | #define TARGET_ARM 1 5 | #define CONFIG_SOFTMMU 1 6 | -------------------------------------------------------------------------------- /msvc/unicorn/armeb-softmmu/config-target.h: -------------------------------------------------------------------------------- 1 | /* Automatically generated by create_config - do not modify */ 2 | #define TARGET_ARM 1 3 | #define TARGET_NAME "armeb" 4 | #define TARGET_ARM 1 5 | #define TARGET_WORDS_BIGENDIAN 1 6 | #define CONFIG_SOFTMMU 1 7 | -------------------------------------------------------------------------------- /msvc/unicorn/config-host.h: -------------------------------------------------------------------------------- 1 | /* Automatically generated by create_config - do not modify */ 2 | #define HOST_I386 1 3 | #define CONFIG_WIN32 1 4 | #define CONFIG_FILEVERSION 2,2,1,0 5 | #define CONFIG_PRODUCTVERSION 2,2,1,0 6 | #define CONFIG_CPUID_H 1 7 | -------------------------------------------------------------------------------- /msvc/unicorn/m68k-softmmu/config-target.h: -------------------------------------------------------------------------------- 1 | /* Automatically generated by create_config - do not modify */ 2 | #define TARGET_M68K 1 3 | #define TARGET_NAME "m68k" 4 | #define TARGET_M68K 1 5 | #define TARGET_WORDS_BIGENDIAN 1 6 | #define CONFIG_SOFTMMU 1 7 | -------------------------------------------------------------------------------- /msvc/unicorn/mips-softmmu/config-target.h: -------------------------------------------------------------------------------- 1 | /* Automatically generated by create_config - do not modify */ 2 | #define TARGET_ABI_MIPSO32 1 3 | #define TARGET_MIPS 1 4 | #define TARGET_NAME "mips" 5 | #define TARGET_MIPS 1 6 | #define TARGET_WORDS_BIGENDIAN 1 7 | #define CONFIG_SOFTMMU 1 8 | -------------------------------------------------------------------------------- /msvc/unicorn/mips64-softmmu/config-target.h: -------------------------------------------------------------------------------- 1 | /* Automatically generated by create_config - do not modify */ 2 | #define TARGET_ABI_MIPSN64 1 3 | #define TARGET_MIPS64 1 4 | #define TARGET_NAME "mips64" 5 | #define TARGET_MIPS 1 6 | #define TARGET_WORDS_BIGENDIAN 1 7 | #define CONFIG_SOFTMMU 1 8 | -------------------------------------------------------------------------------- /msvc/unicorn/mips64el-softmmu/config-target.h: -------------------------------------------------------------------------------- 1 | /* Automatically generated by create_config - do not modify */ 2 | #define TARGET_ABI_MIPSN64 1 3 | #define TARGET_MIPS64 1 4 | #define TARGET_NAME "mips64el" 5 | #define TARGET_MIPS 1 6 | #define CONFIG_SOFTMMU 1 7 | -------------------------------------------------------------------------------- /msvc/unicorn/mipsel-softmmu/config-target.h: -------------------------------------------------------------------------------- 1 | /* Automatically generated by create_config - do not modify */ 2 | #define TARGET_ABI_MIPSO32 1 3 | #define TARGET_MIPS 1 4 | #define TARGET_NAME "mipsel" 5 | #define TARGET_MIPS 1 6 | #define CONFIG_SOFTMMU 1 7 | -------------------------------------------------------------------------------- /msvc/unicorn/prebuild_script.bat: -------------------------------------------------------------------------------- 1 | del ..\..\qemu\qapi-types.h 2> null 2 | del ..\..\qemu\qapi-types.c 2> null 3 | 4 | del ..\..\qemu\qapi-visit.h 2> null 5 | del ..\..\qemu\qapi-visit.c 2> null 6 | 7 | del ..\..\qemu\config-host.h 2> null 8 | 9 | del ..\..\qemu\aarch-softmmu\config-target.h 2> null 10 | del ..\..\qemu\aarcheb-softmmu\config-target.h 2> null 11 | del ..\..\qemu\arm-softmmu\config-target.h 2> null 12 | del ..\..\qemu\armeb-softmmu\config-target.h 2> null 13 | del ..\..\qemu\m68k-softmmu\config-target.h 2> null 14 | del ..\..\qemu\mips64el-softmmu\config-target.h 2> null 15 | del ..\..\qemu\mips64-softmmu\config-target.h 2> null 16 | del ..\..\qemu\mipsel-softmmu\config-target.h 2> null 17 | del ..\..\qemu\mips-softmmu\config-target.h 2> null 18 | del ..\..\qemu\sparc64-softmmu\config-target.h 2> null 19 | del ..\..\qemu\sparc-softmmu\config-target.h 2> null 20 | del ..\..\qemu\x86_64-softmmu\config-target.h 2> null 21 | del null 22 | -------------------------------------------------------------------------------- /msvc/unicorn/sparc-softmmu/config-target.h: -------------------------------------------------------------------------------- 1 | /* Automatically generated by create_config - do not modify */ 2 | #define TARGET_SPARC 1 3 | #define TARGET_NAME "sparc" 4 | #define TARGET_SPARC 1 5 | #define TARGET_WORDS_BIGENDIAN 1 6 | #define CONFIG_SOFTMMU 1 7 | -------------------------------------------------------------------------------- /msvc/unicorn/sparc64-softmmu/config-target.h: -------------------------------------------------------------------------------- 1 | /* Automatically generated by create_config - do not modify */ 2 | #define TARGET_SPARC64 1 3 | #define TARGET_NAME "sparc64" 4 | #define TARGET_SPARC 1 5 | #define TARGET_WORDS_BIGENDIAN 1 6 | #define CONFIG_SOFTMMU 1 7 | -------------------------------------------------------------------------------- /msvc/unicorn/unicorn/dllmain.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | BOOL APIENTRY DllMain( HMODULE hModule, 4 | DWORD ul_reason_for_call, 5 | LPVOID lpReserved 6 | ) 7 | { 8 | switch (ul_reason_for_call) 9 | { 10 | case DLL_PROCESS_ATTACH: 11 | case DLL_THREAD_ATTACH: 12 | case DLL_THREAD_DETACH: 13 | case DLL_PROCESS_DETACH: 14 | break; 15 | } 16 | return TRUE; 17 | } 18 | 19 | -------------------------------------------------------------------------------- /msvc/unicorn/x86_64-softmmu/config-target.h: -------------------------------------------------------------------------------- 1 | /* Automatically generated by create_config - do not modify */ 2 | #define TARGET_X86_64 1 3 | #define TARGET_NAME "x86_64" 4 | #define TARGET_I386 1 5 | #define CONFIG_SOFTMMU 1 6 | -------------------------------------------------------------------------------- /nmake.bat: -------------------------------------------------------------------------------- 1 | :: Unicorn Emulator Engine 2 | :: Build Unicorn libs on Windows with CMake & Nmake 3 | :: Usage: nmake.bat [x86 arm aarch64 m68k mips sparc], default build all. 4 | :: By Huitao Chen, 2019 5 | 6 | @echo off 7 | 8 | set flags="-DCMAKE_BUILD_TYPE=Release" 9 | 10 | set allparams= 11 | 12 | :loop 13 | set str=%1 14 | if "%str%"=="" ( 15 | goto end 16 | ) 17 | set allparams=%allparams% %str% 18 | shift /0 19 | goto loop 20 | 21 | :end 22 | if "%allparams%"=="" ( 23 | goto eof 24 | ) 25 | :: remove left, right blank 26 | :intercept_left 27 | if "%allparams:~0,1%"==" " set "allparams=%allparams:~1%" & goto intercept_left 28 | 29 | :intercept_right 30 | if "%allparams:~-1%"==" " set "allparams=%allparams:~0,-1%" & goto intercept_right 31 | 32 | :eof 33 | 34 | if "%allparams%"=="" ( 35 | cmake "%flags%" -G "NMake Makefiles" .. 36 | ) else ( 37 | cmake "%flags%" "-DUNICORN_ARCH=%allparams%" -G "NMake Makefiles" .. 38 | ) 39 | 40 | nmake 41 | -------------------------------------------------------------------------------- /pkgconfig.mk: -------------------------------------------------------------------------------- 1 | # Package version of Unicorn for Makefile. 2 | # To be used to generate unicorn.pc for pkg-config 3 | # Also used to generate python package version 4 | 5 | # version major & minor 6 | PKG_MAJOR = 1 7 | PKG_MINOR = 0 8 | 9 | # version bugfix level. Example: PKG_EXTRA = 1 10 | PKG_EXTRA = 2 11 | 12 | # version tag. Examples: rc1, b2, post1 13 | PKG_TAG = rc6 14 | -------------------------------------------------------------------------------- /qemu/LICENSE: -------------------------------------------------------------------------------- 1 | The following points clarify the QEMU license: 2 | 3 | 1) QEMU as a whole is released under the GNU General Public License, 4 | version 2. 5 | 6 | 2) Parts of QEMU have specific licenses which are compatible with the 7 | GNU General Public License, version 2. Hence each source file contains 8 | its own licensing information. Source files with no licensing information 9 | are released under the GNU General Public License, version 2 or (at your 10 | option) any later version. 11 | 12 | As of July 2013, contributions under version 2 of the GNU General Public 13 | License (and no later version) are only accepted for the following files 14 | or directories: bsd-user/, linux-user/, hw/misc/vfio.c, hw/xen/xen_pt*. 15 | 16 | 3) The Tiny Code Generator (TCG) is released under the BSD license 17 | (see license headers in files). 18 | 19 | 4) QEMU is a trademark of Fabrice Bellard. 20 | 21 | Fabrice Bellard and the QEMU team 22 | -------------------------------------------------------------------------------- /qemu/Makefile.objs: -------------------------------------------------------------------------------- 1 | ####################################################################### 2 | # Common libraries for tools and emulators 3 | util-obj-y = util/ qobject/ qapi/ qapi-types.o qapi-visit.o 4 | 5 | common-obj-y += hw/ 6 | common-obj-y += accel.o 7 | common-obj-y += vl.o qemu-timer.o 8 | common-obj-y += ../uc.o ../list.o glib_compat.o 9 | common-obj-y += qemu-log.o 10 | common-obj-y += tcg-runtime.o 11 | common-obj-y += hw/ 12 | common-obj-y += qom/ 13 | -------------------------------------------------------------------------------- /qemu/VERSION: -------------------------------------------------------------------------------- 1 | 2.2.1 2 | -------------------------------------------------------------------------------- /qemu/default-configs/aarch64-softmmu.mak: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/qemu/default-configs/aarch64-softmmu.mak -------------------------------------------------------------------------------- /qemu/default-configs/aarch64eb-softmmu.mak: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/qemu/default-configs/aarch64eb-softmmu.mak -------------------------------------------------------------------------------- /qemu/default-configs/arm-softmmu.mak: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/qemu/default-configs/arm-softmmu.mak -------------------------------------------------------------------------------- /qemu/default-configs/armeb-softmmu.mak: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/qemu/default-configs/armeb-softmmu.mak -------------------------------------------------------------------------------- /qemu/default-configs/m68k-softmmu.mak: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/qemu/default-configs/m68k-softmmu.mak -------------------------------------------------------------------------------- /qemu/default-configs/mips-softmmu.mak: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/qemu/default-configs/mips-softmmu.mak -------------------------------------------------------------------------------- /qemu/default-configs/mips64-softmmu.mak: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/qemu/default-configs/mips64-softmmu.mak -------------------------------------------------------------------------------- /qemu/default-configs/mips64el-softmmu.mak: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/qemu/default-configs/mips64el-softmmu.mak -------------------------------------------------------------------------------- /qemu/default-configs/mipsel-softmmu.mak: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/qemu/default-configs/mipsel-softmmu.mak -------------------------------------------------------------------------------- /qemu/default-configs/sparc-softmmu.mak: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/qemu/default-configs/sparc-softmmu.mak -------------------------------------------------------------------------------- /qemu/default-configs/sparc64-softmmu.mak: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/qemu/default-configs/sparc64-softmmu.mak -------------------------------------------------------------------------------- /qemu/default-configs/x86_64-softmmu.mak: -------------------------------------------------------------------------------- 1 | # Default configuration for x86_64-softmmu 2 | 3 | CONFIG_APIC=y 4 | -------------------------------------------------------------------------------- /qemu/gen_all_header.sh: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | for d in x86_64 arm armeb m68k aarch64 aarch64eb mips mipsel mips64 mips64el sparc sparc64; do 3 | python header_gen.py $d > $d.h 4 | done 5 | -------------------------------------------------------------------------------- /qemu/hw/Makefile.objs: -------------------------------------------------------------------------------- 1 | devices-dirs-$(CONFIG_SOFTMMU) += intc/ 2 | devices-dirs-y += core/ 3 | common-obj-y += $(devices-dirs-y) 4 | obj-y += $(devices-dirs-y) 5 | -------------------------------------------------------------------------------- /qemu/hw/arm/Makefile.objs: -------------------------------------------------------------------------------- 1 | obj-y += tosa.o 2 | obj-y += virt.o 3 | -------------------------------------------------------------------------------- /qemu/hw/core/Makefile.objs: -------------------------------------------------------------------------------- 1 | # core qdev-related obj files, also used by *-user: 2 | common-obj-y += qdev.o 3 | common-obj-$(CONFIG_SOFTMMU) += machine.o 4 | -------------------------------------------------------------------------------- /qemu/hw/core/machine.c: -------------------------------------------------------------------------------- 1 | /* 2 | * QEMU Machine 3 | * 4 | * Copyright (C) 2014 Red Hat Inc 5 | * 6 | * Authors: 7 | * Marcel Apfelbaum 8 | * 9 | * This work is licensed under the terms of the GNU GPL, version 2 or later. 10 | * See the COPYING file in the top-level directory. 11 | */ 12 | 13 | #include "hw/boards.h" 14 | 15 | static void machine_initfn(struct uc_struct *uc, Object *obj, void *opaque) 16 | { 17 | } 18 | 19 | static void machine_finalize(struct uc_struct *uc, Object *obj, void *opaque) 20 | { 21 | } 22 | 23 | static const TypeInfo machine_info = { 24 | TYPE_MACHINE, 25 | TYPE_OBJECT, 26 | 27 | sizeof(MachineClass), 28 | sizeof(MachineState), 29 | NULL, 30 | 31 | machine_initfn, 32 | NULL, 33 | machine_finalize, 34 | 35 | NULL, 36 | 37 | NULL, 38 | NULL, 39 | NULL, 40 | 41 | true, 42 | }; 43 | 44 | void machine_register_types(struct uc_struct *uc) 45 | { 46 | type_register_static(uc, &machine_info); 47 | } 48 | -------------------------------------------------------------------------------- /qemu/hw/i386/Makefile.objs: -------------------------------------------------------------------------------- 1 | obj-y += pc.o pc_piix.o 2 | -------------------------------------------------------------------------------- /qemu/hw/intc/Makefile.objs: -------------------------------------------------------------------------------- 1 | obj-$(CONFIG_APIC) += apic.o apic_common.o 2 | -------------------------------------------------------------------------------- /qemu/hw/m68k/Makefile.objs: -------------------------------------------------------------------------------- 1 | obj-y += dummy_m68k.o 2 | -------------------------------------------------------------------------------- /qemu/hw/m68k/dummy_m68k.c: -------------------------------------------------------------------------------- 1 | /* 2 | * Dummy board with just RAM and CPU for use as an ISS. 3 | * 4 | * Copyright (c) 2007 CodeSourcery. 5 | * 6 | * This code is licensed under the GPL 7 | */ 8 | 9 | /* Unicorn Emulator Engine */ 10 | /* By Nguyen Anh Quynh, 2015 */ 11 | 12 | #include "hw/hw.h" 13 | #include "hw/m68k/m68k.h" 14 | #include "hw/boards.h" 15 | #include "exec/address-spaces.h" 16 | 17 | 18 | /* Board init. */ 19 | static int dummy_m68k_init(struct uc_struct *uc, MachineState *machine) 20 | { 21 | const char *cpu_model = machine->cpu_model; 22 | CPUM68KState *env; 23 | 24 | if (!cpu_model) 25 | cpu_model = "cfv4e"; 26 | 27 | env = cpu_init(uc, cpu_model); 28 | if (!env) { 29 | fprintf(stderr, "Unable to find m68k CPU definition\n"); 30 | return -1; 31 | } 32 | 33 | /* Initialize CPU registers. */ 34 | env->vbr = 0; 35 | env->pc = 0; 36 | 37 | return 0; 38 | } 39 | 40 | void dummy_m68k_machine_init(struct uc_struct *uc) 41 | { 42 | static QEMUMachine dummy_m68k_machine = { 0 }; 43 | dummy_m68k_machine.name = "dummy", 44 | dummy_m68k_machine.init = dummy_m68k_init, 45 | dummy_m68k_machine.is_default = 1, 46 | dummy_m68k_machine.arch = UC_ARCH_M68K, 47 | 48 | //printf(">>> dummy_m68k_machine_init\n"); 49 | qemu_register_machine(uc, &dummy_m68k_machine, TYPE_MACHINE, NULL); 50 | } 51 | -------------------------------------------------------------------------------- /qemu/hw/mips/Makefile.objs: -------------------------------------------------------------------------------- 1 | obj-y += mips_r4k.o 2 | obj-y += addr.o cputimer.o 3 | -------------------------------------------------------------------------------- /qemu/hw/sparc/Makefile.objs: -------------------------------------------------------------------------------- 1 | obj-y += leon3.o 2 | -------------------------------------------------------------------------------- /qemu/hw/sparc64/Makefile.objs: -------------------------------------------------------------------------------- 1 | obj-y += sun4u.o 2 | -------------------------------------------------------------------------------- /qemu/include/config.h: -------------------------------------------------------------------------------- 1 | #include "config-host.h" 2 | #include "config-target.h" 3 | -------------------------------------------------------------------------------- /qemu/include/exec/address-spaces.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Internal memory management interfaces 3 | * 4 | * Copyright 2011 Red Hat, Inc. and/or its affiliates 5 | * 6 | * Authors: 7 | * Avi Kivity 8 | * 9 | * This work is licensed under the terms of the GNU GPL, version 2. See 10 | * the COPYING file in the top-level directory. 11 | * 12 | */ 13 | 14 | #ifndef EXEC_MEMORY_H 15 | #define EXEC_MEMORY_H 16 | 17 | /* 18 | * Internal interfaces between memory.c/exec.c/vl.c. Do not #include unless 19 | * you're one of them. 20 | */ 21 | 22 | #include "exec/memory.h" 23 | 24 | #ifndef CONFIG_USER_ONLY 25 | 26 | /* Get the root memory region. This interface should only be used temporarily 27 | * until a proper bus interface is available. 28 | */ 29 | MemoryRegion *get_system_memory(struct uc_struct *uc); 30 | 31 | extern AddressSpace address_space_memory; 32 | 33 | #endif 34 | 35 | #endif 36 | -------------------------------------------------------------------------------- /qemu/include/exec/helper-proto.h: -------------------------------------------------------------------------------- 1 | /* Helper file for declaring TCG helper functions. 2 | This one expands prototypes for the helper functions. */ 3 | 4 | #ifndef HELPER_PROTO_H 5 | #define HELPER_PROTO_H 1 6 | 7 | #include 8 | 9 | #define DEF_HELPER_FLAGS_0(name, flags, ret) \ 10 | dh_ctype(ret) HELPER(name) (void); 11 | 12 | #define DEF_HELPER_FLAGS_1(name, flags, ret, t1) \ 13 | dh_ctype(ret) HELPER(name) (dh_ctype(t1)); 14 | 15 | #define DEF_HELPER_FLAGS_2(name, flags, ret, t1, t2) \ 16 | dh_ctype(ret) HELPER(name) (dh_ctype(t1), dh_ctype(t2)); 17 | 18 | #define DEF_HELPER_FLAGS_3(name, flags, ret, t1, t2, t3) \ 19 | dh_ctype(ret) HELPER(name) (dh_ctype(t1), dh_ctype(t2), dh_ctype(t3)); 20 | 21 | #define DEF_HELPER_FLAGS_4(name, flags, ret, t1, t2, t3, t4) \ 22 | dh_ctype(ret) HELPER(name) (dh_ctype(t1), dh_ctype(t2), dh_ctype(t3), \ 23 | dh_ctype(t4)); 24 | 25 | #define DEF_HELPER_FLAGS_5(name, flags, ret, t1, t2, t3, t4, t5) \ 26 | dh_ctype(ret) HELPER(name) (dh_ctype(t1), dh_ctype(t2), dh_ctype(t3), \ 27 | dh_ctype(t4), dh_ctype(t5)); 28 | 29 | #include "helper.h" 30 | #include "tcg-runtime.h" 31 | 32 | #undef DEF_HELPER_FLAGS_0 33 | #undef DEF_HELPER_FLAGS_1 34 | #undef DEF_HELPER_FLAGS_2 35 | #undef DEF_HELPER_FLAGS_3 36 | #undef DEF_HELPER_FLAGS_4 37 | #undef DEF_HELPER_FLAGS_5 38 | 39 | #endif /* HELPER_PROTO_H */ 40 | -------------------------------------------------------------------------------- /qemu/include/exec/hwaddr.h: -------------------------------------------------------------------------------- 1 | /* Define hwaddr if it exists. */ 2 | 3 | #ifndef HWADDR_H 4 | #define HWADDR_H 5 | 6 | #define HWADDR_BITS 64 7 | /* hwaddr is the type of a physical address (its size can 8 | be different from 'target_ulong'). */ 9 | 10 | #include "unicorn/platform.h" 11 | 12 | typedef uint64_t hwaddr; 13 | #define HWADDR_MAX UINT64_MAX 14 | #define TARGET_FMT_plx "%016" PRIx64 15 | #define HWADDR_PRId PRId64 16 | #define HWADDR_PRIi PRIi64 17 | #define HWADDR_PRIo PRIo64 18 | #define HWADDR_PRIu PRIu64 19 | #define HWADDR_PRIx PRIx64 20 | #define HWADDR_PRIX PRIX64 21 | 22 | #endif 23 | -------------------------------------------------------------------------------- /qemu/include/exec/memory-internal.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Declarations for obsolete exec.c functions 3 | * 4 | * Copyright 2011 Red Hat, Inc. and/or its affiliates 5 | * 6 | * Authors: 7 | * Avi Kivity 8 | * 9 | * This work is licensed under the terms of the GNU GPL, version 2 or 10 | * later. See the COPYING file in the top-level directory. 11 | * 12 | */ 13 | 14 | /* 15 | * This header is for use by exec.c and memory.c ONLY. Do not include it. 16 | * The functions declared here will be removed soon. 17 | */ 18 | 19 | #ifndef MEMORY_INTERNAL_H 20 | #define MEMORY_INTERNAL_H 21 | 22 | #ifndef CONFIG_USER_ONLY 23 | typedef struct AddressSpaceDispatch AddressSpaceDispatch; 24 | 25 | void address_space_init_dispatch(AddressSpace *as); 26 | void address_space_destroy_dispatch(AddressSpace *as); 27 | 28 | extern const MemoryRegionOps unassigned_mem_ops; 29 | 30 | bool memory_region_access_valid(MemoryRegion *mr, hwaddr addr, 31 | unsigned size, bool is_write); 32 | 33 | void address_space_unregister(AddressSpace *as); 34 | 35 | #endif 36 | #endif 37 | -------------------------------------------------------------------------------- /qemu/include/hw/arm/arm.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Misc ARM declarations 3 | * 4 | * Copyright (c) 2006 CodeSourcery. 5 | * Written by Paul Brook 6 | * 7 | * This code is licensed under the LGPL. 8 | * 9 | */ 10 | 11 | #ifndef ARM_MISC_H 12 | #define ARM_MISC_H 13 | 14 | #include "exec/memory.h" 15 | 16 | void tosa_machine_init(struct uc_struct *uc); 17 | void machvirt_machine_init(struct uc_struct *uc); // ARM64 18 | 19 | void arm_cpu_register_types(void *opaque); 20 | void aarch64_cpu_register_types(void *opaque); 21 | 22 | #endif /* !ARM_MISC_H */ 23 | -------------------------------------------------------------------------------- /qemu/include/hw/hw.h: -------------------------------------------------------------------------------- 1 | /* Declarations for use by hardware emulation. */ 2 | #ifndef QEMU_HW_H 3 | #define QEMU_HW_H 4 | 5 | #include "qemu-common.h" 6 | 7 | #if !defined(CONFIG_USER_ONLY) && !defined(NEED_CPU_H) 8 | #include "exec/cpu-common.h" 9 | #endif 10 | 11 | #include "exec/ioport.h" 12 | #include "qemu/log.h" 13 | 14 | #ifdef NEED_CPU_H 15 | #if TARGET_LONG_BITS == 64 16 | #define qemu_put_betl qemu_put_be64 17 | #define qemu_get_betl qemu_get_be64 18 | #define qemu_put_betls qemu_put_be64s 19 | #define qemu_get_betls qemu_get_be64s 20 | #define qemu_put_sbetl qemu_put_sbe64 21 | #define qemu_get_sbetl qemu_get_sbe64 22 | #define qemu_put_sbetls qemu_put_sbe64s 23 | #define qemu_get_sbetls qemu_get_sbe64s 24 | #else 25 | #define qemu_put_betl qemu_put_be32 26 | #define qemu_get_betl qemu_get_be32 27 | #define qemu_put_betls qemu_put_be32s 28 | #define qemu_get_betls qemu_get_be32s 29 | #define qemu_put_sbetl qemu_put_sbe32 30 | #define qemu_get_sbetl qemu_get_sbe32 31 | #define qemu_put_sbetls qemu_put_sbe32s 32 | #define qemu_get_sbetls qemu_get_sbe32s 33 | #endif 34 | #endif 35 | 36 | typedef void QEMUResetHandler(void *opaque); 37 | 38 | void qemu_register_reset(QEMUResetHandler *func, void *opaque); 39 | void qemu_unregister_reset(QEMUResetHandler *func, void *opaque); 40 | 41 | #endif 42 | -------------------------------------------------------------------------------- /qemu/include/hw/i386/apic.h: -------------------------------------------------------------------------------- 1 | #ifndef APIC_H 2 | #define APIC_H 3 | 4 | #include "qemu-common.h" 5 | 6 | /* apic.c */ 7 | int apic_accept_pic_intr(DeviceState *s); 8 | int apic_get_interrupt(DeviceState *s); 9 | void cpu_set_apic_base(struct uc_struct *uc, DeviceState *s, uint64_t val); 10 | uint64_t cpu_get_apic_base(struct uc_struct *uc, DeviceState *s); 11 | void cpu_set_apic_tpr(struct uc_struct *uc, DeviceState *s, uint8_t val); 12 | uint8_t cpu_get_apic_tpr(struct uc_struct *uc, DeviceState *s); 13 | void apic_init_reset(struct uc_struct *uc, DeviceState *s); 14 | void apic_sipi(DeviceState *s); 15 | void apic_handle_tpr_access_report(DeviceState *d, target_ulong ip, 16 | TPRAccess access); 17 | void apic_poll_irq(DeviceState *d); 18 | void apic_designate_bsp(struct uc_struct *uc, DeviceState *d); 19 | 20 | /* pc.c */ 21 | DeviceState *cpu_get_current_apic(struct uc_struct *uc); 22 | 23 | /* cpu.c */ 24 | bool cpu_is_bsp(X86CPU *cpu); 25 | 26 | void apic_register_types(struct uc_struct *uc); 27 | void apic_common_register_types(struct uc_struct *uc); 28 | 29 | #endif 30 | -------------------------------------------------------------------------------- /qemu/include/hw/m68k/m68k.h: -------------------------------------------------------------------------------- 1 | #ifndef HW_M68K_H 2 | #define HW_M68K_H 3 | 4 | #include "uc_priv.h" 5 | 6 | void dummy_m68k_machine_init(struct uc_struct *uc); 7 | 8 | void m68k_cpu_register_types(void *opaque); 9 | 10 | #endif 11 | -------------------------------------------------------------------------------- /qemu/include/hw/mips/cpudevs.h: -------------------------------------------------------------------------------- 1 | #ifndef HW_MIPS_CPUDEVS_H 2 | #define HW_MIPS_CPUDEVS_H 3 | /* Definitions for MIPS CPU internal devices. */ 4 | 5 | /* mips_addr.c */ 6 | uint64_t cpu_mips_kseg0_to_phys(void *opaque, uint64_t addr); 7 | uint64_t cpu_mips_phys_to_kseg0(void *opaque, uint64_t addr); 8 | uint64_t cpu_mips_kvm_um_phys_to_kseg0(void *opaque, uint64_t addr); 9 | 10 | #endif 11 | -------------------------------------------------------------------------------- /qemu/include/hw/mips/mips.h: -------------------------------------------------------------------------------- 1 | #ifndef HW_MIPS_H 2 | #define HW_MIPS_H 3 | 4 | void mips_machine_init(struct uc_struct *uc); 5 | void mips_cpu_register_types(void *opaque); 6 | 7 | #endif 8 | -------------------------------------------------------------------------------- /qemu/include/hw/qdev.h: -------------------------------------------------------------------------------- 1 | #ifndef QDEV_H 2 | #define QDEV_H 3 | 4 | #include "hw/hw.h" 5 | #include "hw/qdev-core.h" 6 | 7 | #endif 8 | -------------------------------------------------------------------------------- /qemu/include/hw/sparc/sparc.h: -------------------------------------------------------------------------------- 1 | #ifndef HW_SPARC_H 2 | #define HW_SPARC_H 3 | 4 | void sparc_cpu_register_types(void *opaque); 5 | void leon3_machine_init(struct uc_struct *uc); 6 | void sun4u_machine_init(struct uc_struct *uc); 7 | 8 | #endif 9 | -------------------------------------------------------------------------------- /qemu/include/qapi/dealloc-visitor.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Dealloc Visitor 3 | * 4 | * Copyright IBM, Corp. 2011 5 | * 6 | * Authors: 7 | * Michael Roth 8 | * 9 | * This work is licensed under the terms of the GNU LGPL, version 2.1 or later. 10 | * See the COPYING.LIB file in the top-level directory. 11 | * 12 | */ 13 | 14 | #ifndef QAPI_DEALLOC_VISITOR_H 15 | #define QAPI_DEALLOC_VISITOR_H 16 | 17 | #include "qapi/visitor.h" 18 | 19 | typedef struct QapiDeallocVisitor QapiDeallocVisitor; 20 | 21 | QapiDeallocVisitor *qapi_dealloc_visitor_new(void); 22 | void qapi_dealloc_visitor_cleanup(QapiDeallocVisitor *d); 23 | 24 | Visitor *qapi_dealloc_get_visitor(QapiDeallocVisitor *v); 25 | 26 | #endif 27 | -------------------------------------------------------------------------------- /qemu/include/qapi/qmp-input-visitor.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Input Visitor 3 | * 4 | * Copyright IBM, Corp. 2011 5 | * 6 | * Authors: 7 | * Anthony Liguori 8 | * 9 | * This work is licensed under the terms of the GNU LGPL, version 2.1 or later. 10 | * See the COPYING.LIB file in the top-level directory. 11 | * 12 | */ 13 | 14 | #ifndef QMP_INPUT_VISITOR_H 15 | #define QMP_INPUT_VISITOR_H 16 | 17 | #include "qapi/visitor.h" 18 | #include "qapi/qmp/qobject.h" 19 | 20 | typedef struct QmpInputVisitor QmpInputVisitor; 21 | 22 | QmpInputVisitor *qmp_input_visitor_new(QObject *obj); 23 | QmpInputVisitor *qmp_input_visitor_new_strict(QObject *obj); 24 | 25 | void qmp_input_visitor_cleanup(QmpInputVisitor *v); 26 | 27 | Visitor *qmp_input_get_visitor(QmpInputVisitor *v); 28 | 29 | #endif 30 | -------------------------------------------------------------------------------- /qemu/include/qapi/qmp-output-visitor.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Output Visitor 3 | * 4 | * Copyright IBM, Corp. 2011 5 | * 6 | * Authors: 7 | * Anthony Liguori 8 | * 9 | * This work is licensed under the terms of the GNU LGPL, version 2.1 or later. 10 | * See the COPYING.LIB file in the top-level directory. 11 | * 12 | */ 13 | 14 | #ifndef QMP_OUTPUT_VISITOR_H 15 | #define QMP_OUTPUT_VISITOR_H 16 | 17 | #include "qapi/visitor.h" 18 | #include "qapi/qmp/qobject.h" 19 | 20 | typedef struct QmpOutputVisitor QmpOutputVisitor; 21 | 22 | QmpOutputVisitor *qmp_output_visitor_new(void); 23 | void qmp_output_visitor_cleanup(QmpOutputVisitor *v); 24 | 25 | QObject *qmp_output_get_qobject(QmpOutputVisitor *v); 26 | Visitor *qmp_output_get_visitor(QmpOutputVisitor *v); 27 | 28 | #endif 29 | -------------------------------------------------------------------------------- /qemu/include/qapi/qmp/qbool.h: -------------------------------------------------------------------------------- 1 | /* 2 | * QBool Module 3 | * 4 | * Copyright IBM, Corp. 2009 5 | * 6 | * Authors: 7 | * Anthony Liguori 8 | * 9 | * This work is licensed under the terms of the GNU LGPL, version 2.1 or later. 10 | * See the COPYING.LIB file in the top-level directory. 11 | * 12 | */ 13 | 14 | #ifndef QBOOL_H 15 | #define QBOOL_H 16 | 17 | #include "unicorn/platform.h" 18 | #include "qapi/qmp/qobject.h" 19 | 20 | typedef struct QBool { 21 | QObject_HEAD; 22 | int value; 23 | } QBool; 24 | 25 | QBool *qbool_from_int(int value); 26 | int qbool_get_int(const QBool *qb); 27 | QBool *qobject_to_qbool(const QObject *obj); 28 | 29 | #endif /* QBOOL_H */ 30 | -------------------------------------------------------------------------------- /qemu/include/qapi/qmp/qfloat.h: -------------------------------------------------------------------------------- 1 | /* 2 | * QFloat Module 3 | * 4 | * Copyright IBM, Corp. 2009 5 | * 6 | * Authors: 7 | * Anthony Liguori 8 | * 9 | * This work is licensed under the terms of the GNU LGPL, version 2.1 or later. 10 | * See the COPYING.LIB file in the top-level directory. 11 | * 12 | */ 13 | 14 | #ifndef QFLOAT_H 15 | #define QFLOAT_H 16 | 17 | #include "unicorn/platform.h" 18 | #include "qapi/qmp/qobject.h" 19 | 20 | typedef struct QFloat { 21 | QObject_HEAD; 22 | double value; 23 | } QFloat; 24 | 25 | QFloat *qfloat_from_double(double value); 26 | double qfloat_get_double(const QFloat *qi); 27 | QFloat *qobject_to_qfloat(const QObject *obj); 28 | 29 | #endif /* QFLOAT_H */ 30 | -------------------------------------------------------------------------------- /qemu/include/qapi/qmp/qint.h: -------------------------------------------------------------------------------- 1 | /* 2 | * QInt Module 3 | * 4 | * Copyright (C) 2009 Red Hat Inc. 5 | * 6 | * Authors: 7 | * Luiz Capitulino 8 | * 9 | * This work is licensed under the terms of the GNU LGPL, version 2.1 or later. 10 | * See the COPYING.LIB file in the top-level directory. 11 | */ 12 | 13 | #ifndef QINT_H 14 | #define QINT_H 15 | 16 | #include "unicorn/platform.h" 17 | #include "qapi/qmp/qobject.h" 18 | 19 | typedef struct QInt { 20 | QObject_HEAD; 21 | int64_t value; 22 | } QInt; 23 | 24 | QInt *qint_from_int(int64_t value); 25 | int64_t qint_get_int(const QInt *qi); 26 | QInt *qobject_to_qint(const QObject *obj); 27 | 28 | #endif /* QINT_H */ 29 | -------------------------------------------------------------------------------- /qemu/include/qapi/qmp/qjson.h: -------------------------------------------------------------------------------- 1 | /* 2 | * QObject JSON integration 3 | * 4 | * Copyright IBM, Corp. 2009 5 | * 6 | * Authors: 7 | * Anthony Liguori 8 | * 9 | * This work is licensed under the terms of the GNU LGPL, version 2.1 or later. 10 | * See the COPYING.LIB file in the top-level directory. 11 | * 12 | */ 13 | 14 | #ifndef QJSON_H 15 | #define QJSON_H 16 | 17 | #include 18 | #include "qemu/compiler.h" 19 | #include "qapi/qmp/qobject.h" 20 | #include "qapi/qmp/qstring.h" 21 | 22 | QObject *qobject_from_json(const char *string); 23 | QObject *qobject_from_jsonf(const char *string, ...) GCC_FMT_ATTR(1, 2); 24 | QObject *qobject_from_jsonv(const char *string, va_list *ap) GCC_FMT_ATTR(1, 0); 25 | 26 | QString *qobject_to_json(const QObject *obj); 27 | QString *qobject_to_json_pretty(const QObject *obj); 28 | 29 | #endif /* QJSON_H */ 30 | -------------------------------------------------------------------------------- /qemu/include/qapi/qmp/qstring.h: -------------------------------------------------------------------------------- 1 | /* 2 | * QString Module 3 | * 4 | * Copyright (C) 2009 Red Hat Inc. 5 | * 6 | * Authors: 7 | * Luiz Capitulino 8 | * 9 | * This work is licensed under the terms of the GNU LGPL, version 2.1 or later. 10 | * See the COPYING.LIB file in the top-level directory. 11 | */ 12 | 13 | #ifndef QSTRING_H 14 | #define QSTRING_H 15 | 16 | #include "unicorn/platform.h" 17 | #include "qapi/qmp/qobject.h" 18 | 19 | typedef struct QString { 20 | QObject_HEAD; 21 | char *string; 22 | size_t length; 23 | size_t capacity; 24 | } QString; 25 | 26 | QString *qstring_new(void); 27 | QString *qstring_from_str(const char *str); 28 | QString *qstring_from_substr(const char *str, int start, int end); 29 | size_t qstring_get_length(const QString *qstring); 30 | const char *qstring_get_str(const QString *qstring); 31 | void qstring_append_int(QString *qstring, int64_t value); 32 | void qstring_append(QString *qstring, const char *str); 33 | void qstring_append_chr(QString *qstring, int c); 34 | QString *qobject_to_qstring(const QObject *obj); 35 | 36 | #endif /* QSTRING_H */ 37 | -------------------------------------------------------------------------------- /qemu/include/qapi/qmp/types.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Include all QEMU objects. 3 | * 4 | * Copyright (C) 2009 Red Hat Inc. 5 | * 6 | * Authors: 7 | * Luiz Capitulino 8 | * 9 | * This work is licensed under the terms of the GNU LGPL, version 2.1 or later. 10 | * See the COPYING.LIB file in the top-level directory. 11 | */ 12 | 13 | #ifndef QEMU_OBJECTS_H 14 | #define QEMU_OBJECTS_H 15 | 16 | #include "qapi/qmp/qobject.h" 17 | #include "qapi/qmp/qint.h" 18 | #include "qapi/qmp/qfloat.h" 19 | #include "qapi/qmp/qbool.h" 20 | #include "qapi/qmp/qstring.h" 21 | #include "qapi/qmp/qdict.h" 22 | #include "qapi/qmp/qlist.h" 23 | #include "qapi/qmp/qjson.h" 24 | 25 | #endif /* QEMU_OBJECTS_H */ 26 | -------------------------------------------------------------------------------- /qemu/include/qapi/string-input-visitor.h: -------------------------------------------------------------------------------- 1 | /* 2 | * String parsing Visitor 3 | * 4 | * Copyright Red Hat, Inc. 2012 5 | * 6 | * Author: Paolo Bonzini 7 | * 8 | * This work is licensed under the terms of the GNU LGPL, version 2.1 or later. 9 | * See the COPYING.LIB file in the top-level directory. 10 | * 11 | */ 12 | 13 | #ifndef STRING_INPUT_VISITOR_H 14 | #define STRING_INPUT_VISITOR_H 15 | 16 | #include "qapi/visitor.h" 17 | 18 | typedef struct StringInputVisitor StringInputVisitor; 19 | 20 | StringInputVisitor *string_input_visitor_new(const char *str); 21 | void string_input_visitor_cleanup(StringInputVisitor *v); 22 | 23 | Visitor *string_input_get_visitor(StringInputVisitor *v); 24 | 25 | #endif 26 | -------------------------------------------------------------------------------- /qemu/include/qemu/crc32c.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Castagnoli CRC32C Checksum Algorithm 3 | * 4 | * Polynomial: 0x11EDC6F41 5 | * 6 | * Castagnoli93: Guy Castagnoli and Stefan Braeuer and Martin Herrman 7 | * "Optimization of Cyclic Redundancy-Check Codes with 24 8 | * and 32 Parity Bits",IEEE Transactions on Communication, 9 | * Volume 41, Number 6, June 1993 10 | * 11 | * Copyright (c) 2013 Red Hat, Inc., 12 | * 13 | * Authors: 14 | * Jeff Cody 15 | * 16 | * Based on the Linux kernel cryptographic crc32c module, 17 | * 18 | * Copyright (c) 2004 Cisco Systems, Inc. 19 | * Copyright (c) 2008 Herbert Xu 20 | * 21 | * This program is free software; you can redistribute it and/or modify it 22 | * under the terms of the GNU General Public License as published by the Free 23 | * Software Foundation; either version 2 of the License, or (at your option) 24 | * any later version. 25 | * 26 | */ 27 | 28 | #ifndef QEMU_CRC32C_H 29 | #define QEMU_CRC32C_H 30 | 31 | #include "qemu-common.h" 32 | 33 | uint32_t crc32c(uint32_t crc, const uint8_t *data, unsigned int length); 34 | 35 | #endif 36 | -------------------------------------------------------------------------------- /qemu/include/qemu/module.h: -------------------------------------------------------------------------------- 1 | /* 2 | * QEMU Module Infrastructure 3 | * 4 | * Copyright IBM, Corp. 2009 5 | * 6 | * Authors: 7 | * Anthony Liguori 8 | * 9 | * This work is licensed under the terms of the GNU GPL, version 2. See 10 | * the COPYING file in the top-level directory. 11 | * 12 | */ 13 | 14 | #ifndef QEMU_MODULE_H 15 | #define QEMU_MODULE_H 16 | 17 | #include "qemu/osdep.h" 18 | 19 | typedef enum { 20 | MODULE_INIT_MACHINE, 21 | MODULE_INIT_QOM, 22 | MODULE_INIT_MAX 23 | } module_init_type; 24 | 25 | #define machine_init(function) module_init(function, MODULE_INIT_MACHINE) 26 | #define type_init(function) module_init(function, MODULE_INIT_QOM) 27 | 28 | void module_call_init(struct uc_struct *uc, module_init_type type); 29 | 30 | #endif 31 | -------------------------------------------------------------------------------- /qemu/include/qemu/thread-posix.h: -------------------------------------------------------------------------------- 1 | #ifndef __QEMU_THREAD_POSIX_H 2 | #define __QEMU_THREAD_POSIX_H 1 3 | #include "pthread.h" 4 | #include 5 | 6 | struct QemuThread { 7 | pthread_t thread; 8 | }; 9 | 10 | #endif 11 | -------------------------------------------------------------------------------- /qemu/include/qemu/thread-win32.h: -------------------------------------------------------------------------------- 1 | #ifndef __QEMU_THREAD_WIN32_H 2 | #define __QEMU_THREAD_WIN32_H 1 3 | #include "windows.h" 4 | 5 | typedef struct QemuThreadData QemuThreadData; 6 | struct QemuThread { 7 | QemuThreadData *data; 8 | unsigned tid; 9 | }; 10 | 11 | /* Only valid for joinable threads. */ 12 | HANDLE qemu_thread_get_handle(QemuThread *thread); 13 | 14 | #endif 15 | -------------------------------------------------------------------------------- /qemu/include/qemu/thread.h: -------------------------------------------------------------------------------- 1 | #ifndef __QEMU_THREAD_H 2 | #define __QEMU_THREAD_H 1 3 | 4 | #include "unicorn/platform.h" 5 | 6 | typedef struct QemuThread QemuThread; 7 | 8 | #ifdef _WIN32 9 | #include "qemu/thread-win32.h" 10 | #else 11 | #include "qemu/thread-posix.h" 12 | #endif 13 | 14 | #define QEMU_THREAD_JOINABLE 0 15 | #define QEMU_THREAD_DETACHED 1 16 | 17 | struct uc_struct; 18 | // return -1 on error, 0 on success 19 | int qemu_thread_create(struct uc_struct *uc, QemuThread *thread, const char *name, 20 | void *(*start_routine)(void *), 21 | void *arg, int mode); 22 | void *qemu_thread_join(QemuThread *thread); 23 | void qemu_thread_exit(struct uc_struct *uc, void *retval); 24 | 25 | #endif 26 | -------------------------------------------------------------------------------- /qemu/include/qom/qom-qobject.h: -------------------------------------------------------------------------------- 1 | /* 2 | * QEMU Object Model - QObject wrappers 3 | * 4 | * Copyright (C) 2012 Red Hat, Inc. 5 | * 6 | * Author: Paolo Bonzini 7 | * 8 | * This work is licensed under the terms of the GNU GPL, version 2 or later. 9 | * See the COPYING file in the top-level directory. 10 | * 11 | */ 12 | 13 | #ifndef QEMU_QOM_QOBJECT_H 14 | #define QEMU_QOM_QOBJECT_H 15 | 16 | #include "qom/object.h" 17 | 18 | /* 19 | * object_property_get_qobject: 20 | * @obj: the object 21 | * @name: the name of the property 22 | * @errp: returns an error if this function fails 23 | * 24 | * Returns: the value of the property, converted to QObject, or NULL if 25 | * an error occurs. 26 | */ 27 | struct QObject *object_property_get_qobject(struct uc_struct *uc, Object *obj, const char *name, 28 | struct Error **errp); 29 | 30 | /** 31 | * object_property_set_qobject: 32 | * @obj: the object 33 | * @ret: The value that will be written to the property. 34 | * @name: the name of the property 35 | * @errp: returns an error if this function fails 36 | * 37 | * Writes a property to a object. 38 | */ 39 | void object_property_set_qobject(struct uc_struct *uc, Object *obj, struct QObject *qobj, 40 | const char *name, struct Error **errp); 41 | 42 | #endif 43 | -------------------------------------------------------------------------------- /qemu/include/sysemu/cpus.h: -------------------------------------------------------------------------------- 1 | #ifndef QEMU_CPUS_H 2 | #define QEMU_CPUS_H 3 | 4 | struct uc_struct; 5 | 6 | /* cpus.c */ 7 | int resume_all_vcpus(struct uc_struct*); 8 | void cpu_stop_current(struct uc_struct*); 9 | 10 | #ifndef CONFIG_USER_ONLY 11 | /* vl.c */ 12 | extern int smp_cores; 13 | extern int smp_threads; 14 | #else 15 | /* *-user doesn't have configurable SMP topology */ 16 | #define smp_cores 1 17 | #define smp_threads 1 18 | #endif 19 | 20 | #endif 21 | -------------------------------------------------------------------------------- /qemu/include/sysemu/sysemu.h: -------------------------------------------------------------------------------- 1 | #ifndef SYSEMU_H 2 | #define SYSEMU_H 3 | /* Misc. things related to the system emulator. */ 4 | 5 | #include "qemu/timer.h" 6 | #include "qapi/error.h" 7 | 8 | /* vl.c */ 9 | 10 | struct uc_struct; 11 | 12 | int runstate_is_running(void); 13 | typedef struct vm_change_state_entry VMChangeStateEntry; 14 | 15 | #define VMRESET_SILENT false 16 | #define VMRESET_REPORT true 17 | 18 | int vm_start(struct uc_struct*); 19 | 20 | void qemu_system_reset_request(struct uc_struct*); 21 | void qemu_system_shutdown_request(void); 22 | void qemu_system_powerdown_request(void); 23 | void qemu_system_reset(bool report); 24 | 25 | extern int smp_cpus; 26 | 27 | #endif 28 | -------------------------------------------------------------------------------- /qemu/qapi/Makefile.objs: -------------------------------------------------------------------------------- 1 | util-obj-y = qapi-visit-core.o qapi-dealloc-visitor.o qmp-input-visitor.o 2 | util-obj-y += qmp-output-visitor.o 3 | util-obj-y += string-input-visitor.o 4 | -------------------------------------------------------------------------------- /qemu/qemu-log.c: -------------------------------------------------------------------------------- 1 | /* 2 | * Logging support 3 | * 4 | * Copyright (c) 2003 Fabrice Bellard 5 | * 6 | * This library is free software; you can redistribute it and/or 7 | * modify it under the terms of the GNU Lesser General Public 8 | * License as published by the Free Software Foundation; either 9 | * version 2 of the License, or (at your option) any later version. 10 | * 11 | * This library is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 14 | * Lesser General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU Lesser General Public 17 | * License along with this library; if not, see . 18 | */ 19 | 20 | #include "qemu-common.h" 21 | #include "qemu/log.h" 22 | 23 | FILE *qemu_logfile; 24 | int qemu_loglevel; 25 | 26 | void qemu_log(const char *fmt, ...) 27 | { 28 | va_list ap; 29 | 30 | va_start(ap, fmt); 31 | if (qemu_logfile) { 32 | vfprintf(qemu_logfile, fmt, ap); 33 | } 34 | va_end(ap); 35 | } 36 | 37 | void qemu_log_mask(int mask, const char *fmt, ...) 38 | { 39 | va_list ap; 40 | 41 | va_start(ap, fmt); 42 | if ((qemu_loglevel & mask) && qemu_logfile) { 43 | vfprintf(qemu_logfile, fmt, ap); 44 | } 45 | va_end(ap); 46 | } 47 | 48 | -------------------------------------------------------------------------------- /qemu/qobject/Makefile.objs: -------------------------------------------------------------------------------- 1 | util-obj-y = qint.o qstring.o qdict.o qlist.o qfloat.o qbool.o 2 | util-obj-y += qerror.o 3 | -------------------------------------------------------------------------------- /qemu/qobject/qerror.c: -------------------------------------------------------------------------------- 1 | /* 2 | * QError Module 3 | * 4 | * Copyright (C) 2009 Red Hat Inc. 5 | * 6 | * Authors: 7 | * Luiz Capitulino 8 | * 9 | * This work is licensed under the terms of the GNU LGPL, version 2.1 or later. 10 | * See the COPYING.LIB file in the top-level directory. 11 | */ 12 | 13 | #include "qapi/qmp/qjson.h" 14 | #include "qapi/qmp/qerror.h" 15 | #include "qemu-common.h" 16 | 17 | 18 | /** 19 | * qerror_human(): Format QError data into human-readable string. 20 | */ 21 | QString *qerror_human(const QError *qerror) 22 | { 23 | return qstring_from_str(qerror->err_msg); 24 | } 25 | 26 | void qerror_report(ErrorClass eclass, const char *fmt, ...) 27 | { 28 | } 29 | 30 | /* Evil... */ 31 | struct Error 32 | { 33 | char *msg; 34 | ErrorClass err_class; 35 | }; 36 | 37 | void qerror_report_err(Error *err) 38 | { 39 | } 40 | -------------------------------------------------------------------------------- /qemu/qom/Makefile.objs: -------------------------------------------------------------------------------- 1 | common-obj-y = object.o container.o qom-qobject.o 2 | common-obj-y += cpu.o 3 | -------------------------------------------------------------------------------- /qemu/qom/container.c: -------------------------------------------------------------------------------- 1 | /* 2 | * Device Container 3 | * 4 | * Copyright IBM, Corp. 2012 5 | * 6 | * Authors: 7 | * Anthony Liguori 8 | * 9 | * This work is licensed under the terms of the GNU GPL, version 2 or later. 10 | * See the COPYING file in the top-level directory. 11 | */ 12 | 13 | #include "qom/object.h" 14 | #include "qemu/module.h" 15 | #include 16 | 17 | static const TypeInfo container_info = { 18 | "container", 19 | TYPE_OBJECT, 20 | 0, 21 | sizeof(Object), 22 | }; 23 | 24 | void container_register_types(struct uc_struct *uc) 25 | { 26 | type_register_static(uc, &container_info); 27 | } 28 | 29 | Object *container_get(struct uc_struct *uc, Object *root, const char *path) 30 | { 31 | Object *obj, *child; 32 | gchar **parts; 33 | int i; 34 | 35 | parts = g_strsplit(path, "/", 0); 36 | assert(parts != NULL && parts[0] != NULL && !parts[0][0]); 37 | obj = root; 38 | 39 | for (i = 1; parts[i] != NULL; i++, obj = child) { 40 | child = object_resolve_path_component(uc, obj, parts[i]); 41 | if (!child) { 42 | child = object_new(uc, "container"); 43 | object_property_add_child(obj, parts[i], child, NULL); 44 | } 45 | } 46 | 47 | g_strfreev(parts); 48 | 49 | return obj; 50 | } 51 | -------------------------------------------------------------------------------- /qemu/scripts/qapi-build.sh: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | 3 | # Run this scripts to create qapi below files in root dir 4 | # ../qapi-types.c 5 | # ../qapi-types.h 6 | # ../qapi-visit.c 7 | # ../qapi-visit.h 8 | 9 | python qapi-types.py -h -o .. -b -i qapi-schema.json 10 | python qapi-types.py -c -o .. -b -i qapi-schema.json 11 | 12 | python qapi-visit.py -h -o .. -b -i qapi-schema.json 13 | python qapi-visit.py -c -o .. -b -i qapi-schema.json 14 | 15 | -------------------------------------------------------------------------------- /qemu/scripts/qapi-schema.json: -------------------------------------------------------------------------------- 1 | # -*- Mode: Python -*- 2 | # 3 | # QAPI Schema 4 | 5 | # QAPI common definitions 6 | { 'include': 'qapi/common.json' } 7 | 8 | ## 9 | # @X86CPURegister32 10 | # 11 | # A X86 32-bit register 12 | # 13 | # Since: 1.5 14 | ## 15 | { 'enum': 'X86CPURegister32', 16 | 'data': [ 'EAX', 'EBX', 'ECX', 'EDX', 'ESP', 'EBP', 'ESI', 'EDI' ] } 17 | 18 | ## 19 | # @X86CPUFeatureWordInfo 20 | # 21 | # Information about a X86 CPU feature word 22 | # 23 | # @cpuid-input-eax: Input EAX value for CPUID instruction for that feature word 24 | # 25 | # @cpuid-input-ecx: #optional Input ECX value for CPUID instruction for that 26 | # feature word 27 | # 28 | # @cpuid-register: Output register containing the feature bits 29 | # 30 | # @features: value of output register, containing the feature bits 31 | # 32 | # Since: 1.5 33 | ## 34 | { 'type': 'X86CPUFeatureWordInfo', 35 | 'data': { 'cpuid-input-eax': 'int', 36 | '*cpuid-input-ecx': 'int', 37 | 'cpuid-register': 'X86CPURegister32', 38 | 'features': 'int' } } 39 | 40 | -------------------------------------------------------------------------------- /qemu/scripts/qapi/common.json: -------------------------------------------------------------------------------- 1 | # -*- Mode: Python -*- 2 | # 3 | # QAPI common definitions 4 | 5 | ## 6 | # @ErrorClass 7 | # 8 | # QEMU error classes 9 | # 10 | # @GenericError: this is used for errors that don't require a specific error 11 | # class. This should be the default case for most errors 12 | # 13 | # @CommandNotFound: the requested command has not been found 14 | # 15 | # @DeviceEncrypted: the requested operation can't be fulfilled because the 16 | # selected device is encrypted 17 | # 18 | # @DeviceNotActive: a device has failed to be become active 19 | # 20 | # @DeviceNotFound: the requested device has not been found 21 | # 22 | # @KVMMissingCap: the requested operation can't be fulfilled because a 23 | # required KVM capability is missing 24 | # 25 | # Since: 1.2 26 | ## 27 | { 'enum': 'ErrorClass', 28 | 'data': [ 'GenericError', 'CommandNotFound', 'DeviceEncrypted', 29 | 'DeviceNotActive', 'DeviceNotFound', 'KVMMissingCap' ] } 30 | 31 | -------------------------------------------------------------------------------- /qemu/target-arm/Makefile.objs: -------------------------------------------------------------------------------- 1 | obj-y += translate.o op_helper.o helper.o cpu.o 2 | obj-y += neon_helper.o iwmmxt_helper.o 3 | obj-$(CONFIG_SOFTMMU) += psci.o 4 | obj-$(TARGET_AARCH64) += cpu64.o translate-a64.o helper-a64.o unicorn_aarch64.o 5 | obj-$(TARGET_ARM) += unicorn_arm.o 6 | obj-y += crypto_helper.o 7 | -------------------------------------------------------------------------------- /qemu/target-arm/unicorn.h: -------------------------------------------------------------------------------- 1 | /* Unicorn Emulator Engine */ 2 | /* By Nguyen Anh Quynh , 2015 */ 3 | 4 | #ifndef UC_QEMU_TARGET_ARM_H 5 | #define UC_QEMU_TARGET_ARM_H 6 | 7 | // functions to read & write registers 8 | int arm_reg_read(struct uc_struct *uc, unsigned int *regs, void **vals, int count); 9 | int arm_reg_write(struct uc_struct *uc, unsigned int *regs, void *const *vals, int count); 10 | int arm64_reg_read(struct uc_struct *uc, unsigned int *regs, void **vals, int count); 11 | int arm64_reg_write(struct uc_struct *uc, unsigned int *regs, void *const *vals, int count); 12 | 13 | void arm_reg_reset(struct uc_struct *uc); 14 | void arm64_reg_reset(struct uc_struct *uc); 15 | 16 | DEFAULT_VISIBILITY 17 | void arm_uc_init(struct uc_struct* uc); 18 | void armeb_uc_init(struct uc_struct* uc); 19 | 20 | DEFAULT_VISIBILITY 21 | void arm64_uc_init(struct uc_struct* uc); 22 | void arm64eb_uc_init(struct uc_struct* uc); 23 | 24 | extern const int ARM_REGS_STORAGE_SIZE_arm; 25 | extern const int ARM_REGS_STORAGE_SIZE_armeb; 26 | extern const int ARM64_REGS_STORAGE_SIZE_aarch64; 27 | extern const int ARM64_REGS_STORAGE_SIZE_aarch64eb; 28 | 29 | #endif 30 | -------------------------------------------------------------------------------- /qemu/target-i386/Makefile.objs: -------------------------------------------------------------------------------- 1 | obj-y += translate.o helper.o cpu.o 2 | obj-y += excp_helper.o fpu_helper.o cc_helper.o int_helper.o svm_helper.o 3 | obj-y += smm_helper.o misc_helper.o mem_helper.o seg_helper.o 4 | obj-$(CONFIG_SOFTMMU) += arch_memory_mapping.o 5 | obj-y += unicorn.o 6 | -------------------------------------------------------------------------------- /qemu/target-i386/TODO: -------------------------------------------------------------------------------- 1 | Correctness issues: 2 | 3 | - some eflags manipulation incorrectly reset the bit 0x2. 4 | - SVM: test, cpu save/restore, SMM save/restore. 5 | - x86_64: lcall/ljmp intel/amd differences ? 6 | - better code fetch (different exception handling + CS.limit support) 7 | - user/kernel PUSHL/POPL in helper.c 8 | - add missing cpuid tests 9 | - return UD exception if LOCK prefix incorrectly used 10 | - test ldt limit < 7 ? 11 | - fix some 16 bit sp push/pop overflow (pusha/popa, lcall lret) 12 | - full support of segment limit/rights 13 | - full x87 exception support 14 | - improve x87 bit exactness (use bochs code ?) 15 | - DRx register support 16 | - CR0.AC emulation 17 | - SSE alignment checks 18 | 19 | Optimizations/Features: 20 | 21 | - add SVM nested paging support 22 | - add VMX support 23 | - add AVX support 24 | - add SSE5 support 25 | - fxsave/fxrstor AMD extensions 26 | - improve monitor/mwait support 27 | - faster EFLAGS update: consider SZAP, C, O can be updated separately 28 | with a bit field in CC_OP and more state variables. 29 | - evaluate x87 stack pointer statically 30 | - find a way to avoid translating several time the same TB if CR0.TS 31 | is set or not. 32 | -------------------------------------------------------------------------------- /qemu/target-i386/unicorn.h: -------------------------------------------------------------------------------- 1 | /* Unicorn Emulator Engine */ 2 | /* By Nguyen Anh Quynh , 2015 */ 3 | 4 | #ifndef UC_QEMU_TARGET_I386_H 5 | #define UC_QEMU_TARGET_I386_H 6 | 7 | // functions to read & write registers 8 | int x86_reg_read(struct uc_struct *uc, unsigned int *regs, void **vals, int count); 9 | int x86_reg_write(struct uc_struct *uc, unsigned int *regs, void *const *vals, int count); 10 | 11 | void x86_reg_reset(struct uc_struct *uc); 12 | 13 | void x86_uc_init(struct uc_struct* uc); 14 | int x86_uc_machine_init(struct uc_struct *uc); 15 | 16 | extern const int X86_REGS_STORAGE_SIZE; 17 | #endif 18 | -------------------------------------------------------------------------------- /qemu/target-m68k/Makefile.objs: -------------------------------------------------------------------------------- 1 | obj-y += translate.o op_helper.o helper.o cpu.o 2 | obj-y += unicorn.o 3 | -------------------------------------------------------------------------------- /qemu/target-m68k/m68k-qreg.h: -------------------------------------------------------------------------------- 1 | enum { 2 | #define DEFO32(name, offset) QREG_##name, 3 | #define DEFR(name, reg, mode) QREG_##name, 4 | #define DEFF64(name, offset) QREG_##name, 5 | QREG_NULL, 6 | #include "qregs.def" 7 | TARGET_NUM_QREGS = 0x100 8 | #undef DEFO32 9 | #undef DEFR 10 | #undef DEFF64 11 | }; 12 | -------------------------------------------------------------------------------- /qemu/target-m68k/qregs.def: -------------------------------------------------------------------------------- 1 | DEFF64(FP_RESULT, fp_result) 2 | DEFO32(PC, pc) 3 | DEFO32(SR, sr) 4 | DEFO32(CC_OP, cc_op) 5 | DEFO32(CC_DEST, cc_dest) 6 | DEFO32(CC_SRC, cc_src) 7 | DEFO32(CC_X, cc_x) 8 | DEFO32(DIV1, div1) 9 | DEFO32(DIV2, div2) 10 | DEFO32(MACSR, macsr) 11 | DEFO32(MAC_MASK, mac_mask) 12 | -------------------------------------------------------------------------------- /qemu/target-m68k/unicorn.h: -------------------------------------------------------------------------------- 1 | /* Unicorn Emulator Engine */ 2 | /* By Nguyen Anh Quynh , 2015 */ 3 | 4 | #ifndef UC_QEMU_TARGET_M68K_H 5 | #define UC_QEMU_TARGET_M68K_H 6 | 7 | // functions to read & write registers 8 | int m68k_reg_read(struct uc_struct *uc, unsigned int *regs, void **vals, int count); 9 | int m68k_reg_write(struct uc_struct *uc, unsigned int *regs, void *const *vals, int count); 10 | 11 | void m68k_reg_reset(struct uc_struct *uc); 12 | 13 | void m68k_uc_init(struct uc_struct* uc); 14 | 15 | extern const int M68K_REGS_STORAGE_SIZE; 16 | #endif 17 | -------------------------------------------------------------------------------- /qemu/target-mips/Makefile.objs: -------------------------------------------------------------------------------- 1 | obj-y += translate.o dsp_helper.o op_helper.o lmi_helper.o helper.o cpu.o 2 | obj-y += msa_helper.o 3 | obj-y += unicorn.o 4 | -------------------------------------------------------------------------------- /qemu/target-mips/unicorn.h: -------------------------------------------------------------------------------- 1 | /* Unicorn Emulator Engine */ 2 | /* By Nguyen Anh Quynh , 2015 */ 3 | 4 | #ifndef UC_QEMU_TARGET_MIPS_H 5 | #define UC_QEMU_TARGET_MIPS_H 6 | 7 | // functions to read & write registers 8 | int mips_reg_read(struct uc_struct *uc, unsigned int *regs, void **vals, int count); 9 | int mips_reg_write(struct uc_struct *uc, unsigned int *regs, void *const *vals, int count); 10 | 11 | void mips_reg_reset(struct uc_struct *uc); 12 | 13 | void mips_uc_init(struct uc_struct* uc); 14 | void mipsel_uc_init(struct uc_struct* uc); 15 | void mips64_uc_init(struct uc_struct* uc); 16 | void mips64el_uc_init(struct uc_struct* uc); 17 | 18 | extern const int MIPS_REGS_STORAGE_SIZE_mips; 19 | extern const int MIPS_REGS_STORAGE_SIZE_mipsel; 20 | extern const int MIPS64_REGS_STORAGE_SIZE_mips64; 21 | extern const int MIPS64_REGS_STORAGE_SIZE_mips64el; 22 | 23 | #endif 24 | -------------------------------------------------------------------------------- /qemu/target-sparc/Makefile.objs: -------------------------------------------------------------------------------- 1 | obj-y += translate.o helper.o cpu.o 2 | obj-y += fop_helper.o cc_helper.o win_helper.o mmu_helper.o ldst_helper.o 3 | obj-$(TARGET_SPARC) += int32_helper.o 4 | obj-$(TARGET_SPARC64) += int64_helper.o 5 | obj-$(TARGET_SPARC64) += vis_helper.o 6 | obj-$(TARGET_SPARC) += unicorn.o 7 | obj-$(TARGET_SPARC64) += unicorn64.o 8 | -------------------------------------------------------------------------------- /qemu/target-sparc/unicorn.h: -------------------------------------------------------------------------------- 1 | /* Unicorn Emulator Engine */ 2 | /* By Nguyen Anh Quynh , 2015 */ 3 | 4 | #ifndef UC_QEMU_TARGET_SPARC_H 5 | #define UC_QEMU_TARGET_SPARC_H 6 | 7 | // functions to read & write registers 8 | int sparc_reg_read(struct uc_struct *uc, unsigned int *regs, void **vals, int count); 9 | int sparc_reg_write(struct uc_struct *uc, unsigned int *regs, void *const *vals, int count); 10 | 11 | void sparc_reg_reset(struct uc_struct *uc); 12 | 13 | void sparc_uc_init(struct uc_struct* uc); 14 | void sparc64_uc_init(struct uc_struct* uc); 15 | 16 | extern const int SPARC_REGS_STORAGE_SIZE; 17 | extern const int SPARC64_REGS_STORAGE_SIZE; 18 | 19 | #endif 20 | -------------------------------------------------------------------------------- /qemu/tcg/LICENSE: -------------------------------------------------------------------------------- 1 | All the files in this directory and subdirectories are released under 2 | a BSD like license (see header in each file). No other license is 3 | accepted. 4 | -------------------------------------------------------------------------------- /qemu/tcg/TODO: -------------------------------------------------------------------------------- 1 | - Add new instructions such as: clz, ctz, popcnt. 2 | 3 | - See if it is worth exporting mul2, mulu2, div2, divu2. 4 | 5 | - Support of globals saved in fixed registers between TBs. 6 | 7 | Ideas: 8 | 9 | - Move the slow part of the qemu_ld/st ops after the end of the TB. 10 | 11 | - Change exception syntax to get closer to QOP system (exception 12 | parameters given with a specific instruction). 13 | 14 | - Add float and vector support. 15 | -------------------------------------------------------------------------------- /qemu/tcg/tcg-runtime.h: -------------------------------------------------------------------------------- 1 | DEF_HELPER_FLAGS_2(div_i32, TCG_CALL_NO_RWG_SE, s32, s32, s32) 2 | DEF_HELPER_FLAGS_2(rem_i32, TCG_CALL_NO_RWG_SE, s32, s32, s32) 3 | DEF_HELPER_FLAGS_2(divu_i32, TCG_CALL_NO_RWG_SE, i32, i32, i32) 4 | DEF_HELPER_FLAGS_2(remu_i32, TCG_CALL_NO_RWG_SE, i32, i32, i32) 5 | 6 | DEF_HELPER_FLAGS_2(div_i64, TCG_CALL_NO_RWG_SE, s64, s64, s64) 7 | DEF_HELPER_FLAGS_2(rem_i64, TCG_CALL_NO_RWG_SE, s64, s64, s64) 8 | DEF_HELPER_FLAGS_2(divu_i64, TCG_CALL_NO_RWG_SE, i64, i64, i64) 9 | DEF_HELPER_FLAGS_2(remu_i64, TCG_CALL_NO_RWG_SE, i64, i64, i64) 10 | 11 | DEF_HELPER_FLAGS_2(shl_i64, TCG_CALL_NO_RWG_SE, i64, i64, i64) 12 | DEF_HELPER_FLAGS_2(shr_i64, TCG_CALL_NO_RWG_SE, i64, i64, i64) 13 | DEF_HELPER_FLAGS_2(sar_i64, TCG_CALL_NO_RWG_SE, s64, s64, s64) 14 | 15 | DEF_HELPER_FLAGS_2(mulsh_i64, TCG_CALL_NO_RWG_SE, s64, s64, s64) 16 | DEF_HELPER_FLAGS_2(muluh_i64, TCG_CALL_NO_RWG_SE, i64, i64, i64) 17 | -------------------------------------------------------------------------------- /qemu/translate-all.h: -------------------------------------------------------------------------------- 1 | /* 2 | * Translated block handling 3 | * 4 | * Copyright (c) 2003 Fabrice Bellard 5 | * 6 | * This library is free software; you can redistribute it and/or 7 | * modify it under the terms of the GNU Lesser General Public 8 | * License as published by the Free Software Foundation; either 9 | * version 2 of the License, or (at your option) any later version. 10 | * 11 | * This library is distributed in the hope that it will be useful, 12 | * but WITHOUT ANY WARRANTY; without even the implied warranty of 13 | * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 14 | * Lesser General Public License for more details. 15 | * 16 | * You should have received a copy of the GNU Lesser General Public 17 | * License along with this library; if not, see . 18 | */ 19 | #ifndef TRANSLATE_ALL_H 20 | #define TRANSLATE_ALL_H 21 | 22 | /* translate-all.c */ 23 | void cpu_unlink_tb(CPUState *cpu); 24 | void tb_check_watchpoint(CPUState *cpu); 25 | void tb_invalidate_phys_page_fast(struct uc_struct* uc, tb_page_addr_t start, int len); 26 | void tb_cleanup(struct uc_struct *uc); 27 | 28 | #endif /* TRANSLATE_ALL_H */ 29 | -------------------------------------------------------------------------------- /qemu/util/Makefile.objs: -------------------------------------------------------------------------------- 1 | util-obj-y = cutils.o qemu-timer-common.o 2 | util-obj-$(CONFIG_WIN32) += oslib-win32.o qemu-thread-win32.o 3 | util-obj-$(CONFIG_POSIX) += oslib-posix.o qemu-thread-posix.o 4 | util-obj-y += module.o 5 | util-obj-y += bitmap.o bitops.o 6 | util-obj-y += error.o 7 | util-obj-y += aes.o 8 | util-obj-y += crc32c.o 9 | util-obj-y += host-utils.o 10 | util-obj-y += getauxval.o 11 | -------------------------------------------------------------------------------- /qemu/util/module.c: -------------------------------------------------------------------------------- 1 | /* 2 | * QEMU Module Infrastructure 3 | * 4 | * Copyright IBM, Corp. 2009 5 | * 6 | * Authors: 7 | * Anthony Liguori 8 | * 9 | * This work is licensed under the terms of the GNU GPL, version 2. See 10 | * the COPYING file in the top-level directory. 11 | * 12 | * Contributions after 2012-01-13 are licensed under the terms of the 13 | * GNU GPL, version 2 or (at your option) any later version. 14 | */ 15 | 16 | #include "qemu-common.h" 17 | #include "qemu/queue.h" 18 | 19 | #include "uc_priv.h" 20 | 21 | static void init_lists(struct uc_struct *uc) 22 | { 23 | int i; 24 | 25 | for (i = 0; i < MODULE_INIT_MAX; i++) { 26 | QTAILQ_INIT(&uc->init_type_list[i]); 27 | } 28 | } 29 | 30 | 31 | static ModuleTypeList *find_type(struct uc_struct *uc, module_init_type type) 32 | { 33 | ModuleTypeList *l; 34 | 35 | init_lists(uc); 36 | 37 | l = &uc->init_type_list[type]; 38 | 39 | return l; 40 | } 41 | 42 | static void module_load(module_init_type type) 43 | { 44 | } 45 | 46 | void module_call_init(struct uc_struct *uc, module_init_type type) 47 | { 48 | ModuleTypeList *l; 49 | ModuleEntry *e; 50 | 51 | module_load(type); 52 | l = find_type(uc, type); 53 | 54 | QTAILQ_FOREACH(e, l, node) { 55 | e->init(); 56 | } 57 | } 58 | -------------------------------------------------------------------------------- /qemu/util/setjmp-wrapper-win32.asm: -------------------------------------------------------------------------------- 1 | EXTERN _setjmp: proc 2 | PUBLIC _setjmp_wrapper 3 | 4 | _TEXT SEGMENT 5 | 6 | _setjmp_wrapper PROC 7 | 8 | ; Why do we need this wrapper? 9 | ; Short answer: Windows default implementation of setjmp/longjmp is incompatible with generated code. 10 | ; A longer answer: https://blog.lazym.io/2020/09/21/Unicorn-Devblog-setjmp-longjmp-on-Windows/. 11 | 12 | ; From qemu os-win32 comments: 13 | ; > On w64, setjmp is implemented by _setjmp which needs a second parameter. 14 | ; > If this parameter is NULL, longjump does no stack unwinding. 15 | ; > That is what we need for QEMU. Passing the value of register rsp (default) 16 | ; > lets longjmp try a stack unwinding which will crash with generated code. 17 | ; It's true indeed, but MSVC doesn't has a setjmp signature which receives two arguements. 18 | ; Therefore, we add a wrapper to keep the second argument zero. 19 | xor rdx, rdx 20 | jmp _setjmp 21 | 22 | _setjmp_wrapper ENDP 23 | 24 | _TEXT ENDS 25 | 26 | END -------------------------------------------------------------------------------- /qemu/vl.h: -------------------------------------------------------------------------------- 1 | #ifndef VL_H_ 2 | #define VL_H_ 3 | 4 | int machine_initialize(struct uc_struct *uc); 5 | 6 | #endif 7 | 8 | -------------------------------------------------------------------------------- /samples/.gitignore: -------------------------------------------------------------------------------- 1 | !*.c 2 | sample_* 3 | shellcode* 4 | mem_apis* 5 | 6 | -------------------------------------------------------------------------------- /tests/fuzz/Makefile: -------------------------------------------------------------------------------- 1 | CFLAGS += -L ../../ -I ../../include 2 | 3 | UNAME_S := $(shell uname -s) 4 | LDFLAGS += -pthread 5 | ifeq ($(UNAME_S), Linux) 6 | LDFLAGS += -lrt 7 | endif 8 | 9 | LDFLAGS += ../../libunicorn.a 10 | 11 | 12 | ALL_TESTS_SOURCES = $(wildcard fuzz*.c) 13 | ALL_TESTS = $(ALL_TESTS_SOURCES:%.c=%) 14 | 15 | .PHONY: all 16 | all: ${ALL_TESTS} 17 | 18 | .PHONY: clean 19 | clean: 20 | rm -rf ${ALL_TESTS} 21 | 22 | fuzz%: fuzz%.c 23 | $(CC) $(CFLAGS) $^ onedir.c $(LDFLAGS) -o $@ 24 | -------------------------------------------------------------------------------- /tests/fuzz/dlcorpus.sh: -------------------------------------------------------------------------------- 1 | #/bin/sh 2 | #change to script directory 3 | cd `dirname $0` 4 | ls fuzz_emu*.c | sed 's/.c//' | while read target 5 | do 6 | #download public corpus 7 | wget "https://storage.googleapis.com/unicorn-backup.clusterfuzz-external.appspot.com/corpus/libFuzzer/unicorn_$target/public.zip" 8 | unzip -q public.zip -d corpus_$target 9 | #run target on corpus 10 | ./$target corpus_$target 11 | done 12 | -------------------------------------------------------------------------------- /tests/fuzz/fuzz_emu.options: -------------------------------------------------------------------------------- 1 | [libfuzzer] 2 | max_len = 4096 3 | -------------------------------------------------------------------------------- /tests/fuzz/onefile.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | int LLVMFuzzerTestOneInput(const uint8_t *Data, size_t Size); 6 | 7 | int main(int argc, char** argv) 8 | { 9 | FILE * fp; 10 | uint8_t *Data; 11 | size_t Size; 12 | 13 | if (argc != 2) { 14 | return 1; 15 | } 16 | //opens the file, get its size, and reads it into a buffer 17 | fp = fopen(argv[1], "rb"); 18 | if (fp == NULL) { 19 | return 2; 20 | } 21 | if (fseek(fp, 0L, SEEK_END) != 0) { 22 | fclose(fp); 23 | return 2; 24 | } 25 | Size = ftell(fp); 26 | if (Size == (size_t) -1) { 27 | fclose(fp); 28 | return 2; 29 | } 30 | if (fseek(fp, 0L, SEEK_SET) != 0) { 31 | fclose(fp); 32 | return 2; 33 | } 34 | Data = malloc(Size); 35 | if (Data == NULL) { 36 | fclose(fp); 37 | return 2; 38 | } 39 | if (fread(Data, Size, 1, fp) != 1) { 40 | fclose(fp); 41 | return 2; 42 | } 43 | 44 | //lauch fuzzer 45 | LLVMFuzzerTestOneInput(Data, Size); 46 | fclose(fp); 47 | return 0; 48 | } 49 | 50 | -------------------------------------------------------------------------------- /tests/regress/.gitignore: -------------------------------------------------------------------------------- 1 | !*.c 2 | 3 | arm_enable_vfp 4 | map_crash 5 | sigill 6 | sigill2 7 | block_test 8 | map_write 9 | ro_mem_test 10 | nr_mem_test 11 | timeout_segfault 12 | rep_movsb 13 | mips_kseg0_1 14 | eflags_nosync 15 | 00opcode_uc_crash 16 | eflags_noset 17 | invalid_read_in_cpu_tb_exec 18 | invalid_write_in_cpu_tb_exec_x86_64 19 | x86_16_segfault 20 | mips_invalid_read_of_size_4_when_tracing 21 | invalid_read_in_tb_flush_x86_64 22 | sparc_jump_to_zero 23 | mips_delay_slot_code_hook 24 | threaded_emu_start 25 | emu_stop_in_hook_overrun 26 | mips_branch_likely_issue 27 | emu_clear_errors 28 | 001-bad_condition_code_0xe 29 | 002-qemu__fatal__unimplemented_control_register_write_0xffb___0x0 30 | 003-qemu__fatal__wdebug_not_implemented 31 | 004-segmentation_fault_1 32 | 005-qemu__fatal__illegal_instruction__0000___00000404 33 | 006-qemu__fatal__illegal_instruction__0421___00040026 34 | 35 | rw_hookstack 36 | hook_extrainvoke 37 | sysenter_hook_x86 38 | 39 | memleak_* 40 | mem_* 41 | -------------------------------------------------------------------------------- /tests/regress/001-bad_condition_code_0xe.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | #define HARDWARE_ARCHITECTURE UC_ARCH_ARM 4 | #define HARDWARE_MODE 16 5 | #define MEMORY_STARTING_ADDRESS 8192 6 | #define MEMORY_SIZE 4096 7 | #define MEMORY_PERMISSIONS 6 8 | #define BINARY_CODE "\x56\xe8\x46\x46\x80\xf6\x8c\x56\xff\xbf\xcd\x90\xda\xa0\xed\xe8\x46\x43\x45\xe5\x80\x90\x44\x46\x04" 9 | 10 | static void hook_code(uc_engine *uc, uint64_t address, uint32_t size, void *user_data) { 11 | printf("hook_code(…) called\n"); 12 | } 13 | 14 | int main(int argc, char **argv, char **envp) { 15 | uc_engine *uc; 16 | if (uc_open(HARDWARE_ARCHITECTURE, HARDWARE_MODE, &uc)) { 17 | printf("uc_open(…) failed\n"); 18 | return 1; 19 | } 20 | uc_mem_map(uc, MEMORY_STARTING_ADDRESS, MEMORY_SIZE, MEMORY_PERMISSIONS); 21 | if (uc_mem_write(uc, MEMORY_STARTING_ADDRESS, BINARY_CODE, sizeof(BINARY_CODE) - 1)) { 22 | printf("uc_mem_write(…) failed\n"); 23 | return 1; 24 | } 25 | uc_hook trace; 26 | uc_hook_add(uc, &trace, UC_HOOK_CODE, hook_code, NULL, (uint64_t)MEMORY_STARTING_ADDRESS, (uint64_t)(MEMORY_STARTING_ADDRESS + 1)); 27 | printf("uc_emu_start(…)\n"); 28 | uc_emu_start(uc, MEMORY_STARTING_ADDRESS, MEMORY_STARTING_ADDRESS + sizeof(BINARY_CODE) - 1, 0, 0); 29 | printf("done\n"); 30 | return 0; 31 | } 32 | -------------------------------------------------------------------------------- /tests/regress/002-qemu__fatal__unimplemented_control_register_write_0xffb___0x0.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | #define HARDWARE_ARCHITECTURE UC_ARCH_M68K 4 | #define HARDWARE_MODE 1073741824 5 | #define MEMORY_STARTING_ADDRESS 8388608 6 | #define MEMORY_SIZE 2097152 7 | #define MEMORY_PERMISSIONS 7 8 | #define BINARY_CODE "\xaf\x80\x4e\x7b\xff\xfb\x80\x4e\x3e\x80" 9 | 10 | static void hook_code(uc_engine *uc, uint64_t address, uint32_t size, void *user_data) { 11 | printf("hook_code(…) called\n"); 12 | } 13 | 14 | int main(int argc, char **argv, char **envp) { 15 | uc_engine *uc; 16 | if (uc_open(HARDWARE_ARCHITECTURE, HARDWARE_MODE, &uc)) { 17 | printf("uc_open(…) failed\n"); 18 | return 1; 19 | } 20 | uc_mem_map(uc, MEMORY_STARTING_ADDRESS, MEMORY_SIZE, MEMORY_PERMISSIONS); 21 | if (uc_mem_write(uc, MEMORY_STARTING_ADDRESS, BINARY_CODE, sizeof(BINARY_CODE) - 1)) { 22 | printf("uc_mem_write(…) failed\n"); 23 | return 1; 24 | } 25 | uc_hook trace; 26 | uc_hook_add(uc, &trace, UC_HOOK_CODE, hook_code, NULL, (uint64_t)MEMORY_STARTING_ADDRESS, (uint64_t)(MEMORY_STARTING_ADDRESS + 1)); 27 | printf("uc_emu_start(…)\n"); 28 | uc_emu_start(uc, MEMORY_STARTING_ADDRESS, MEMORY_STARTING_ADDRESS + sizeof(BINARY_CODE) - 1, 0, 0); 29 | printf("done\n"); 30 | return 0; 31 | } 32 | -------------------------------------------------------------------------------- /tests/regress/003-qemu__fatal__wdebug_not_implemented.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | #define HARDWARE_ARCHITECTURE UC_ARCH_M68K 4 | #define HARDWARE_MODE 1073741824 5 | #define MEMORY_STARTING_ADDRESS 1048576 6 | #define MEMORY_SIZE 403456 7 | #define MEMORY_PERMISSIONS 7 8 | #define BINARY_CODE "\x42\xc7\xfb\xfb\x54\x36" 9 | 10 | static void hook_code(uc_engine *uc, uint64_t address, uint32_t size, void *user_data) { 11 | printf("hook_code(…) called\n"); 12 | } 13 | 14 | int main(int argc, char **argv, char **envp) { 15 | uc_engine *uc; 16 | if (uc_open(HARDWARE_ARCHITECTURE, HARDWARE_MODE, &uc)) { 17 | printf("uc_open(…) failed\n"); 18 | return 1; 19 | } 20 | uc_mem_map(uc, MEMORY_STARTING_ADDRESS, MEMORY_SIZE, MEMORY_PERMISSIONS); 21 | if (uc_mem_write(uc, MEMORY_STARTING_ADDRESS, BINARY_CODE, sizeof(BINARY_CODE) - 1)) { 22 | printf("uc_mem_write(…) failed\n"); 23 | return 1; 24 | } 25 | uc_hook trace; 26 | uc_hook_add(uc, &trace, UC_HOOK_CODE, hook_code, NULL, (uint64_t)MEMORY_STARTING_ADDRESS, (uint64_t)(MEMORY_STARTING_ADDRESS + 1)); 27 | printf("uc_emu_start(…)\n"); 28 | uc_emu_start(uc, MEMORY_STARTING_ADDRESS, MEMORY_STARTING_ADDRESS + sizeof(BINARY_CODE) - 1, 0, 0); 29 | printf("done\n"); 30 | return 0; 31 | } 32 | -------------------------------------------------------------------------------- /tests/regress/004-segmentation_fault_1.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | #define HARDWARE_ARCHITECTURE UC_ARCH_ARM 4 | #define HARDWARE_MODE 16 5 | #define MEMORY_STARTING_ADDRESS 1024 6 | #define MEMORY_SIZE 1796096 7 | #define MEMORY_PERMISSIONS 7 8 | #define BINARY_CODE "\x20\xbf\xbf\xbf\xbf\xdd\x5d\x74\x5e\x66\x72\x10" 9 | 10 | static void hook_code(uc_engine *uc, uint64_t address, uint32_t size, void *user_data) { 11 | printf("hook_code(…) called\n"); 12 | } 13 | 14 | int main(int argc, char **argv, char **envp) { 15 | uc_engine *uc; 16 | if (uc_open(HARDWARE_ARCHITECTURE, HARDWARE_MODE, &uc)) { 17 | printf("uc_open(…) failed\n"); 18 | return 1; 19 | } 20 | uc_mem_map(uc, MEMORY_STARTING_ADDRESS, MEMORY_SIZE, MEMORY_PERMISSIONS); 21 | if (uc_mem_write(uc, MEMORY_STARTING_ADDRESS, BINARY_CODE, sizeof(BINARY_CODE) - 1)) { 22 | printf("uc_mem_write(…) failed\n"); 23 | return 1; 24 | } 25 | uc_hook trace; 26 | uc_hook_add(uc, &trace, UC_HOOK_CODE, hook_code, NULL, (uint64_t)MEMORY_STARTING_ADDRESS, (uint64_t)(MEMORY_STARTING_ADDRESS + 1)); 27 | printf("uc_emu_start(…)\n"); 28 | uc_emu_start(uc, MEMORY_STARTING_ADDRESS, MEMORY_STARTING_ADDRESS + sizeof(BINARY_CODE) - 1, 0, 0); 29 | printf("done\n"); 30 | return 0; 31 | } 32 | -------------------------------------------------------------------------------- /tests/regress/005-qemu__fatal__illegal_instruction__0000___00000404.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | #define HARDWARE_ARCHITECTURE UC_ARCH_M68K 4 | #define HARDWARE_MODE 1073741824 5 | #define MEMORY_STARTING_ADDRESS 1024 6 | #define MEMORY_SIZE 1044480 7 | #define MEMORY_PERMISSIONS 5 8 | #define BINARY_CODE "\x4c\x4c" 9 | 10 | static void hook_code(uc_engine *uc, uint64_t address, uint32_t size, void *user_data) { 11 | printf("hook_code(…) called\n"); 12 | } 13 | 14 | int main(int argc, char **argv, char **envp) { 15 | uc_engine *uc; 16 | if (uc_open(HARDWARE_ARCHITECTURE, HARDWARE_MODE, &uc)) { 17 | printf("uc_open(…) failed\n"); 18 | return 1; 19 | } 20 | uc_mem_map(uc, MEMORY_STARTING_ADDRESS, MEMORY_SIZE, MEMORY_PERMISSIONS); 21 | if (uc_mem_write(uc, MEMORY_STARTING_ADDRESS, BINARY_CODE, sizeof(BINARY_CODE) - 1)) { 22 | printf("uc_mem_write(…) failed\n"); 23 | return 1; 24 | } 25 | uc_hook trace; 26 | uc_hook_add(uc, &trace, UC_HOOK_CODE, hook_code, NULL, (uint64_t)MEMORY_STARTING_ADDRESS, (uint64_t)(MEMORY_STARTING_ADDRESS + 1)); 27 | printf("uc_emu_start(…)\n"); 28 | uc_emu_start(uc, MEMORY_STARTING_ADDRESS, MEMORY_STARTING_ADDRESS + sizeof(BINARY_CODE) - 1, 0, 0); 29 | printf("done\n"); 30 | return 0; 31 | } 32 | -------------------------------------------------------------------------------- /tests/regress/Makefile: -------------------------------------------------------------------------------- 1 | CFLAGS += -Wall -Werror -I../../include 2 | CFLAGS += -D__USE_MINGW_ANSI_STDIO=1 3 | LDLIBS += -L../../ -lm -lunicorn 4 | 5 | UNAME_S := $(shell uname -s) 6 | LDLIBS += -pthread 7 | ifeq ($(UNAME_S), Linux) 8 | LDLIBS += -lrt 9 | endif 10 | 11 | EXECUTE_VARS = LD_LIBRARY_PATH=../../cmocka/src:../../ DYLD_LIBRARY_PATH=../../ 12 | 13 | TESTS_SOURCE = $(wildcard *.c) 14 | TESTS = $(TESTS_SOURCE:%.c=%) 15 | 16 | .PHONY: all clean test 17 | 18 | test: $(TESTS) 19 | 20 | all: $(TESTS) 21 | 22 | clean: 23 | rm -f $(TESTS) 24 | -------------------------------------------------------------------------------- /tests/regress/arm64_reg_rw_w0_w30.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | 3 | from unicorn import * 4 | from unicorn.arm64_const import * 5 | from unicorn.x86_const import * 6 | 7 | import regress 8 | 9 | class Arm64RegReadWriteW0ThroughW30(regress.RegressTest): 10 | """ 11 | Testing the functionality to read/write 32-bit registers in AArch64 12 | See issue #716 13 | """ 14 | 15 | def runTest(self): 16 | uc = Uc(UC_ARCH_ARM64, UC_MODE_ARM) 17 | 18 | uc.reg_write(UC_ARM64_REG_X0, 0x1234567890abcdef) 19 | self.assertEquals(uc.reg_read(UC_ARM64_REG_X0), 0x1234567890abcdef) 20 | self.assertEquals(uc.reg_read(UC_ARM64_REG_W0), 0x90abcdef) 21 | 22 | uc.reg_write(UC_ARM64_REG_X30, 0xa1b2c3d4e5f6a7b8) 23 | self.assertEquals(uc.reg_read(UC_ARM64_REG_W30), 0xe5f6a7b8) 24 | 25 | uc.reg_write(UC_ARM64_REG_W30, 0xaabbccdd) 26 | self.assertEquals(uc.reg_read(UC_ARM64_REG_X30), 0xa1b2c3d4aabbccdd) 27 | self.assertEquals(uc.reg_read(UC_ARM64_REG_W30), 0xaabbccdd) 28 | 29 | if __name__ == '__main__': 30 | regress.main() 31 | -------------------------------------------------------------------------------- /tests/regress/arm_apsr_access.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | 3 | from unicorn import * 4 | from unicorn.arm_const import * 5 | 6 | import regress 7 | 8 | class APSRAccess(regress.RegressTest): 9 | 10 | def runTest(self): 11 | code = ( 12 | b'\x00\x00\xa0\xe1' + # 0: mov r0, r0 13 | b'\x08\x10\x9f\xe5' + # 4: ldr r1, [pc, #8] 14 | b'\x01\xf0\x28\xe1' + # 8: 01 f0 28 e1 msr apsr_nzcvq, r1 15 | b'\x00\x00\xa0\xe1' + # c: mov r0, r0 16 | b'\x00\x00\xa0\xe1' + # 10: mov r0, r0 17 | b'\x00\x00\x00\xff') # 14: data for inst @4 18 | 19 | uc = Uc(UC_ARCH_ARM, UC_MODE_ARM) 20 | uc.mem_map(0x1000, 0x1000) 21 | uc.mem_write(0x1000, code) # bxeq lr; mov r0, r0 22 | 23 | uc.reg_write(UC_ARM_REG_APSR, 0) 24 | uc.emu_start(0x1000, 0x100c) 25 | 26 | self.assertEqual(uc.reg_read(UC_ARM_REG_APSR), 0xf8000000) 27 | self.assertEqual(uc.reg_read(UC_ARM_REG_APSR_NZCV), 0xf0000000) 28 | 29 | if __name__ == '__main__': 30 | regress.main() 31 | -------------------------------------------------------------------------------- /tests/regress/arm_bxeq_hang.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | 3 | from unicorn import * 4 | from unicorn.arm_const import * 5 | 6 | import regress 7 | 8 | class BxHang(regress.RegressTest): 9 | 10 | def runTest(self): 11 | uc = Uc(UC_ARCH_ARM, UC_MODE_ARM) 12 | uc.mem_map(0x1000, 0x1000) 13 | uc.mem_write(0x1000, '1eff2f010000a0e1'.decode('hex')) # bxeq lr; mov r0, r0 14 | uc.count = 0 15 | 16 | def hook_block(uc, addr, *args): 17 | print 'enter block 0x%04x' % addr 18 | uc.count += 1 19 | 20 | uc.reg_write(UC_ARM_REG_LR, 0x1004) 21 | uc.hook_add(UC_HOOK_BLOCK, hook_block) 22 | print 'block should only run once' 23 | uc.emu_start(0x1000, 0x1004) 24 | 25 | self.assertEqual(uc.count, 1) 26 | 27 | if __name__ == '__main__': 28 | regress.main() 29 | -------------------------------------------------------------------------------- /tests/regress/arm_fp_vfp_disabled.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | # coding=utf8 3 | 4 | # Added by Peter Mackay, relating to issue 571 5 | # "ARM NEON/VFP support seems to exist but is disabled by default" 6 | # https://github.com/unicorn-engine/unicorn/issues/571 7 | 8 | from unicorn import * 9 | from unicorn.arm_const import * 10 | 11 | import regress 12 | 13 | class FpVfpDisabled(regress.RegressTest): 14 | 15 | def runTest(self): 16 | # MRC p15, #0, r1, c1, c0, #2 17 | # ORR r1, r1, #(0xf << 20) 18 | # MCR p15, #0, r1, c1, c0, #2 19 | # MOV r1, #0 20 | # MCR p15, #0, r1, c7, c5, #4 21 | # MOV r0,#0x40000000 22 | # FMXR FPEXC, r0 23 | code = '11EE501F' 24 | code += '41F47001' 25 | code += '01EE501F' 26 | code += '4FF00001' 27 | code += '07EE951F' 28 | code += '4FF08040' 29 | code += 'E8EE100A' 30 | # vpush {d8} 31 | code += '2ded028b' 32 | 33 | address = 0x1000 34 | mem_size = 0x1000 35 | code_bytes = code.decode('hex') 36 | 37 | uc = Uc(UC_ARCH_ARM, UC_MODE_THUMB) 38 | uc.mem_map(address, mem_size) 39 | uc.mem_write(address, code_bytes) 40 | uc.reg_write(UC_ARM_REG_SP, address + mem_size) 41 | uc.emu_start(address + 1, address + len(code_bytes)) 42 | 43 | if __name__ == '__main__': 44 | regress.main() 45 | -------------------------------------------------------------------------------- /tests/regress/arm_movr12_hang.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | 3 | from unicorn import * 4 | from unicorn.arm_const import * 5 | 6 | import regress 7 | 8 | class MovHang(regress.RegressTest): 9 | 10 | def runTest(self): 11 | uc = Uc(UC_ARCH_ARM, UC_MODE_ARM) 12 | uc.mem_map(0x1000, 0x1000) 13 | uc.mem_write(0x1000, '00c000e3'.decode('hex')) # movw r12, #0 14 | 15 | def hook_block(uc, addr, *args): 16 | print 'enter block 0x%04x' % addr 17 | uc.count += 1 18 | 19 | uc.reg_write(UC_ARM_REG_R12, 0x123) 20 | self.assertEquals(uc.reg_read(UC_ARM_REG_R12), 0x123) 21 | 22 | uc.hook_add(UC_HOOK_BLOCK, hook_block) 23 | uc.count = 0 24 | 25 | #print 'block should only run once' 26 | uc.emu_start(0x1000, 0x1004, timeout=500) 27 | 28 | self.assertEquals(uc.reg_read(UC_ARM_REG_R12), 0x0) 29 | self.assertEquals(uc.count, 1) 30 | 31 | if __name__ == '__main__': 32 | regress.main() 33 | -------------------------------------------------------------------------------- /tests/regress/arm_vldr_invalid.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | 3 | from unicorn import * 4 | from unicorn.arm_const import * 5 | 6 | import regress 7 | 8 | class VldrPcInsn(regress.RegressTest): 9 | 10 | def runTest(self): 11 | uc = Uc(UC_ARCH_ARM, UC_MODE_ARM) 12 | uc.mem_map(0x1000, 0x1000) 13 | uc.mem_write(0x1000, 'ed9f8a3d'.decode('hex')) # vldr s16, [pc, #244] 14 | # this will raise invalid insn 15 | uc.emu_start(0x1000, 0x1004) 16 | 17 | if __name__ == '__main__': 18 | regress.main() 19 | -------------------------------------------------------------------------------- /tests/regress/bad_ram.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | 3 | from unicorn import * 4 | from unicorn.x86_const import * 5 | 6 | import regress 7 | 8 | 9 | class Hang(regress.RegressTest): 10 | 11 | def runTest(self): 12 | PAGE_SIZE = 0x5000 13 | CODE_ADDR = 0x400000 14 | RSP_ADDR = 0x200000 15 | binary1 = "\xCA\x24\x5D" # retf 0x5d24 16 | mu = Uc(UC_ARCH_X86, UC_MODE_64) 17 | 18 | mu.mem_map(CODE_ADDR, PAGE_SIZE) 19 | mu.mem_map(RSP_ADDR, PAGE_SIZE) 20 | 21 | mu.mem_write(CODE_ADDR, binary1) 22 | mu.reg_write(UC_X86_REG_RSP, RSP_ADDR) 23 | try: 24 | self.assertEqual(mu.emu_start(CODE_ADDR, CODE_ADDR + PAGE_SIZE, 0), UC_ERR_FETCH_INVALID) 25 | except UcError as e: 26 | print("ERROR: %s" % e) 27 | 28 | 29 | if __name__ == '__main__': 30 | regress.main() 31 | -------------------------------------------------------------------------------- /tests/regress/crash_tb.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | 3 | from unicorn import * 4 | from unicorn.x86_const import * 5 | 6 | import regress 7 | 8 | CODE_ADDR = 0x0 9 | binary1 = b'\xb8\x02\x00\x00\x00' 10 | binary2 = b'\xb8\x01\x00\x00\x00' 11 | 12 | class CrashTB(regress.RegressTest): 13 | 14 | def runTest(self): 15 | mu = Uc(UC_ARCH_X86, UC_MODE_64) 16 | 17 | mu.mem_map(CODE_ADDR, 2 * 1024 * 1024) 18 | 19 | # write machine code to be emulated to memory 20 | mu.mem_write(CODE_ADDR, binary1) 21 | 22 | # emu for maximum 1 sec. 23 | mu.emu_start(CODE_ADDR, len(binary1), UC_SECOND_SCALE) 24 | 25 | self.assertEqual(0x2, mu.reg_read(UC_X86_REG_RAX)) 26 | 27 | # write machine code to be emulated to memory 28 | mu.mem_write(CODE_ADDR, binary2) 29 | 30 | # emu for maximum 1 sec. 31 | mu.emu_start(CODE_ADDR, len(binary2), UC_SECOND_SCALE) 32 | 33 | self.assertEqual(0x1, mu.reg_read(UC_X86_REG_RAX)) 34 | 35 | if __name__ == '__main__': 36 | regress.main() 37 | 38 | -------------------------------------------------------------------------------- /tests/regress/deadlock_1.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | # From issue #1 of Ryan Hileman 3 | 4 | from unicorn import * 5 | import regress 6 | 7 | CODE = b"\x90\x91\x92" 8 | 9 | class DeadLock(regress.RegressTest): 10 | 11 | def runTest(self): 12 | mu = Uc(UC_ARCH_X86, UC_MODE_64) 13 | mu.mem_map(0x100000, 4 * 1024) 14 | mu.mem_write(0x100000, CODE) 15 | 16 | with self.assertRaises(UcError): 17 | mu.emu_start(0x100000, 0x1000 + len(CODE)) 18 | 19 | if __name__ == '__main__': 20 | regress.main() 21 | -------------------------------------------------------------------------------- /tests/regress/emu_stop_segfault.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | 3 | """See https://github.com/unicorn-engine/unicorn/issues/65""" 4 | 5 | import unicorn 6 | import regress 7 | 8 | class EmuStopSegFault(regress.RegressTest): 9 | 10 | def runTest(self): 11 | ADDR = 0x10101000 12 | mu = unicorn.Uc(unicorn.UC_ARCH_X86, unicorn.UC_MODE_32) 13 | mu.mem_map(ADDR, 1024 * 4) 14 | mu.mem_write(ADDR, b'\x41') 15 | mu.emu_start(ADDR, ADDR + 1, count=1) 16 | # The following should not trigger a null pointer dereference 17 | self.assertEqual(None, mu.emu_stop()) 18 | 19 | if __name__ == '__main__': 20 | regress.main() 21 | -------------------------------------------------------------------------------- /tests/regress/ensure_typedef_consts_generated.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | 3 | """See https://github.com/unicorn-engine/unicorn/issues/161 4 | 5 | Ensure that constants which are specified via a typedef, rather than an enum, 6 | are included in the bindings by the script for autogenerating mappings for 7 | constants. 8 | """ 9 | 10 | import unicorn 11 | 12 | try: 13 | unicorn.UC_HOOK_MEM_UNMAPPED 14 | except AttributeError: 15 | assert(False and "Definition for UC_HOOK_MEM_UNMAPPED not generated") 16 | -------------------------------------------------------------------------------- /tests/regress/fpu_mem_write.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | from unicorn import * 3 | from unicorn.x86_const import * 4 | 5 | import regress 6 | 7 | ESP = 0x2000 8 | PAGE_SIZE = 1 * 1024 * 1024 9 | 10 | # wait 11 | # fnstcw word ptr [esp] 12 | # pop ecx 13 | CODE = b'\x9B\xD9\x3C\x24\x59' 14 | 15 | def hook_mem_write(uc, access, address, size, value, user_data): 16 | print("mem WRITE: 0x%x, data size = %u, data value = 0x%x" % (address, size, value)) 17 | return True 18 | 19 | class FpuWrite(regress.RegressTest): 20 | 21 | def mem_reader(self, mu, addr, size, expected): 22 | tmp = mu.mem_read(addr, size) 23 | for i, e in zip(tmp, expected): 24 | self.assertEquals(e, i) 25 | 26 | def runTest(self): 27 | mu = Uc(UC_ARCH_X86, UC_MODE_32) 28 | mu.mem_map(0, PAGE_SIZE) 29 | mu.mem_write(0, CODE) 30 | mu.reg_write(UC_X86_REG_ESP, ESP) 31 | 32 | mu.hook_add(UC_HOOK_MEM_WRITE, hook_mem_write) 33 | mu.emu_start(0x0, 5, 0, 2) 34 | esp = mu.reg_read(UC_X86_REG_ESP) 35 | self.mem_reader(mu, esp, 10, [0] * 10) 36 | 37 | if __name__ == '__main__': 38 | regress.main() 39 | -------------------------------------------------------------------------------- /tests/regress/hook_add_crash.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | 3 | """https://github.com/unicorn-engine/unicorn/issues/165""" 4 | 5 | import unicorn 6 | 7 | def hook_mem_read_unmapped(mu, access, address, size, value, user_data): 8 | pass 9 | 10 | mu = unicorn.Uc(unicorn.UC_ARCH_X86, unicorn.UC_MODE_32) 11 | 12 | try: 13 | for x in range(0, 1000): 14 | mu.hook_add(unicorn.UC_HOOK_MEM_READ_UNMAPPED, hook_mem_read_unmapped, None) 15 | except unicorn.UcError as e: 16 | print("ERROR: %s" % e) 17 | -------------------------------------------------------------------------------- /tests/regress/hook_readonly_write_local.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | from unicorn import * 3 | from unicorn.x86_const import * 4 | import regress 5 | 6 | PAGE_SIZE = 4 * 1024 7 | ACCESS_ADDR = 0x1000 8 | 9 | # mov eax, [0x1000] 10 | # mov eax, [0x1000] 11 | CODE = b'\xA1\x00\x10\x00\x00\xA1\x00\x10\x00\x00' 12 | 13 | def hook_mem_read(uc, access, address, size, value, data): 14 | print("Reading at " + str(address)) 15 | uc.mem_write(address, CODE); 16 | 17 | class REP(regress.RegressTest): 18 | 19 | def test_rep(self): 20 | mu = Uc(UC_ARCH_X86, UC_MODE_32) 21 | 22 | mu.mem_map(0, PAGE_SIZE) 23 | mu.mem_write(0, CODE) 24 | mu.mem_map(ACCESS_ADDR, PAGE_SIZE, UC_PROT_READ); 25 | mu.hook_add(UC_HOOK_MEM_READ, hook_mem_read, begin = ACCESS_ADDR, end = ACCESS_ADDR + PAGE_SIZE) 26 | 27 | mu.emu_start(0, len(CODE)) 28 | 29 | if __name__ == '__main__': 30 | regress.main() 31 | -------------------------------------------------------------------------------- /tests/regress/invalid_read_in_cpu_tb_exec.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | static void hook_block(uc_engine *uc, uint64_t address, uint32_t size, void *user_data) { 4 | printf("hook_block(%p, %"PRIx64", %d, %p)\n", uc, address, size, user_data); 5 | } 6 | 7 | /* 8 | * Disassembly according to capstone: 9 | * add byte ptr [rip - 1], 0x30 10 | * jmp 0x1000000 11 | */ 12 | #define BINARY "\x80\x05\xff\xff\xff\xff\x30\xeb\xf7\x30" 13 | #define MEMORY_SIZE 2 * 1024 * 1024 14 | #define STARTING_ADDRESS 0x1000000 15 | 16 | int main(int argc, char **argv, char **envp) { 17 | uc_engine *uc; 18 | if (uc_open(UC_ARCH_X86, UC_MODE_64, &uc)) { 19 | printf("uc_open(…) failed\n"); 20 | return 1; 21 | } 22 | uc_mem_map(uc, STARTING_ADDRESS, MEMORY_SIZE, UC_PROT_ALL); 23 | if (uc_mem_write(uc, STARTING_ADDRESS, BINARY, sizeof(BINARY) - 1)) { 24 | printf("uc_mem_write(…) failed\n"); 25 | return 1; 26 | } 27 | uc_hook hook; 28 | uc_hook_add(uc, &hook, UC_HOOK_BLOCK, hook_block, NULL, 1, 0); 29 | printf("uc_emu_start(…)\n"); 30 | uc_emu_start(uc, STARTING_ADDRESS, STARTING_ADDRESS + sizeof(BINARY) - 1, 0, 20); 31 | printf("done\n"); 32 | return 0; 33 | } 34 | -------------------------------------------------------------------------------- /tests/regress/invalid_read_in_tb_flush_x86_64.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | #define HARDWARE_ARCHITECTURE UC_ARCH_X86 4 | #define HARDWARE_MODE UC_MODE_64 5 | 6 | #define MEMORY_STARTING_ADDRESS 0x1000000 7 | #define MEMORY_SIZE 2 * 1024 * 1024 8 | #define MEMORY_PERMISSIONS UC_PROT_READ 9 | 10 | #define BINARY_CODE "\x90" 11 | 12 | int main(int argc, char **argv, char **envp) { 13 | uc_engine *uc; 14 | if (uc_open(HARDWARE_ARCHITECTURE, HARDWARE_MODE, &uc)) { 15 | printf("uc_open(…) failed\n"); 16 | return 1; 17 | } 18 | uc_mem_map(uc, MEMORY_STARTING_ADDRESS, MEMORY_SIZE, MEMORY_PERMISSIONS); 19 | if (uc_mem_write(uc, MEMORY_STARTING_ADDRESS, BINARY_CODE, sizeof(BINARY_CODE) - 1)) { 20 | printf("uc_mem_write(…) failed\n"); 21 | return 1; 22 | } 23 | printf("uc_emu_start(…)\n"); 24 | uc_emu_start(uc, MEMORY_STARTING_ADDRESS, MEMORY_STARTING_ADDRESS + sizeof(BINARY_CODE) - 1, 0, 20); 25 | printf("done\n"); 26 | return 0; 27 | } 28 | -------------------------------------------------------------------------------- /tests/regress/invalid_write_in_cpu_tb_exec_x86_64.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | /* 4 | * Disassembly according to capstone: 5 | * mulx rsp, rsp, rdx 6 | */ 7 | #define BINARY "\xc4\xe2\xdb\xf6\xe2" 8 | #define MEMORY_SIZE 2 * 1024 * 1024 9 | #define STARTING_ADDRESS 0x1000000 10 | 11 | int main(int argc, char **argv, char **envp) { 12 | uc_engine *uc; 13 | if (uc_open(UC_ARCH_X86, UC_MODE_64, &uc)) { 14 | printf("uc_open(…) failed\n"); 15 | return 1; 16 | } 17 | uc_mem_map(uc, STARTING_ADDRESS, MEMORY_SIZE, UC_PROT_ALL); 18 | if (uc_mem_write(uc, STARTING_ADDRESS, BINARY, sizeof(BINARY) - 1)) { 19 | printf("uc_mem_write(…) failed\n"); 20 | return 1; 21 | } 22 | printf("uc_emu_start(…)\n"); 23 | uc_emu_start(uc, STARTING_ADDRESS, STARTING_ADDRESS + sizeof(BINARY) - 1, 0, 20); 24 | printf("done\n"); 25 | return 0; 26 | } 27 | -------------------------------------------------------------------------------- /tests/regress/jmp_ebx_hang.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | 3 | """See https://github.com/unicorn-engine/unicorn/issues/82""" 4 | 5 | import unicorn 6 | from unicorn import * 7 | import regress 8 | 9 | CODE_ADDR = 0x10101000 10 | CODE = b'\xff\xe3' # jmp ebx 11 | 12 | class JumEbxHang(regress.RegressTest): 13 | 14 | def runTest(self): 15 | mu = unicorn.Uc(UC_ARCH_X86, UC_MODE_32) 16 | mu.mem_map(CODE_ADDR, 1024 * 4) 17 | mu.mem_write(CODE_ADDR, CODE) 18 | # If EBX is zero then an exception is raised, as expected 19 | mu.reg_write(unicorn.x86_const.UC_X86_REG_EBX, 0x0) 20 | 21 | print(">>> jmp ebx (ebx = 0)"); 22 | with self.assertRaises(UcError) as m: 23 | mu.emu_start(CODE_ADDR, CODE_ADDR + 2, count=1) 24 | 25 | self.assertEqual(m.exception.errno, UC_ERR_FETCH_UNMAPPED) 26 | 27 | print(">>> jmp ebx (ebx = 0xaa96a47f)"); 28 | mu = unicorn.Uc(UC_ARCH_X86, UC_MODE_32) 29 | mu.mem_map(CODE_ADDR, 1024 * 4) 30 | # If we write this address to EBX then the emulator hangs on emu_start 31 | mu.reg_write(unicorn.x86_const.UC_X86_REG_EBX, 0xaa96a47f) 32 | mu.mem_write(CODE_ADDR, CODE) 33 | with self.assertRaises(UcError) as m: 34 | mu.emu_start(CODE_ADDR, CODE_ADDR + 2, count=1) 35 | 36 | self.assertEqual(m.exception.errno, UC_ERR_FETCH_UNMAPPED) 37 | 38 | if __name__ == '__main__': 39 | regress.main() 40 | -------------------------------------------------------------------------------- /tests/regress/map_crash.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | 6 | #define UC_BUG_WRITE_SIZE 13000 7 | #define UC_BUG_WRITE_ADDR 0x1000 8 | 9 | int main() 10 | { 11 | int size; 12 | uint8_t *buf; 13 | uc_engine *uc; 14 | uc_err err = uc_open (UC_ARCH_X86, UC_MODE_64, &uc); 15 | if (err) { 16 | fprintf (stderr, "Cannot initialize unicorn\n"); 17 | return 1; 18 | } 19 | size = UC_BUG_WRITE_SIZE; 20 | buf = malloc (size); 21 | if (!buf) { 22 | fprintf (stderr, "Cannot allocate\n"); 23 | return 1; 24 | } 25 | memset (buf, 0, size); 26 | if (!uc_mem_map (uc, UC_BUG_WRITE_ADDR, size, UC_PROT_ALL)) { 27 | uc_mem_write (uc, UC_BUG_WRITE_ADDR, buf, size); 28 | } 29 | uc_close(uc); 30 | free(buf); 31 | return 0; 32 | } 33 | -------------------------------------------------------------------------------- /tests/regress/map_write.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | 5 | #define ADDR 0x00400000 6 | #define SIZE 1024*64 7 | #define OVERFLOW 1 8 | 9 | int main() 10 | { 11 | uc_engine *uc = NULL; 12 | uint8_t *buf = NULL, *buf2 = NULL; 13 | int i; 14 | uc_err err; 15 | 16 | err = uc_open (UC_ARCH_X86, UC_MODE_64, &uc); 17 | if (err) { 18 | printf ("uc_open %d\n", err); 19 | goto exit; 20 | } 21 | err = uc_mem_map (uc, ADDR, SIZE, UC_PROT_ALL); 22 | if (err) { 23 | printf ("uc_mem_map %d\n", err); 24 | goto exit; 25 | } 26 | buf = calloc (SIZE*2, 1); 27 | buf2 = calloc (SIZE, 1); 28 | for (i=0;i 2 | #include 3 | 4 | uint64_t starts[] = {0x10000000, 0x110004000ll}; 5 | 6 | int main(int argc, char **argv, char **envp) { 7 | uc_engine *uc; 8 | uc_err err; 9 | int i; 10 | // Initialize emulator in X86-64bit mode 11 | err = uc_open(UC_ARCH_X86, UC_MODE_64, &uc); 12 | if (err) { 13 | printf("Failed on uc_open() with error returned: %u\n", err); 14 | return 1; 15 | } 16 | 17 | for (i = 0; i < (sizeof(starts) / sizeof(uint64_t)); i++) { 18 | uc_mem_map(uc, starts[i], 4096, UC_PROT_ALL); 19 | } 20 | 21 | uint32_t count; 22 | uc_mem_region *regions; 23 | int err_count = 0; 24 | err = uc_mem_regions(uc, ®ions, &count); 25 | if (err == UC_ERR_OK) { 26 | for (i = 0; i < count; i++) { 27 | fprintf(stderr, "region %d: 0x%"PRIx64"-0x%"PRIx64" (%d)\n", i, regions[i].begin, regions[i].end - 1, regions[i].perms); 28 | if (regions[i].begin != starts[i]) { 29 | err_count++; 30 | fprintf(stderr, " ERROR: region start does not match requested start address, expected 0x%"PRIx64", found 0x%"PRIx64"\n", 31 | starts[i], regions[i].begin); 32 | } 33 | } 34 | uc_free(regions); 35 | } 36 | 37 | uc_close(uc); 38 | return err_count; 39 | } 40 | -------------------------------------------------------------------------------- /tests/regress/mem_double_unmap.c: -------------------------------------------------------------------------------- 1 | #define __STDC_FORMAT_MACROS 2 | #include 3 | #include 4 | #include 5 | #include 6 | 7 | #include 8 | 9 | int main(int argc, char **argv, char **envp) 10 | { 11 | uc_engine *uc; 12 | uc_err err; 13 | 14 | // Initialize emulator in X86-32bit mode 15 | err = uc_open(UC_ARCH_X86, UC_MODE_32, &uc); 16 | if (err) { 17 | printf("not ok - Failed on uc_open() with error returned: %u\n", err); 18 | return -1; 19 | } 20 | 21 | uc_mem_map(uc, 0x1000, 0x1000, UC_PROT_ALL); 22 | if (err) { 23 | printf("not ok - Failed on uc_mem_map() with error returned: %u\n", err); 24 | return -1; 25 | } 26 | 27 | uc_mem_map(uc, 0x4000, 0x1000, UC_PROT_ALL); 28 | if (err) { 29 | printf("not ok - Failed on uc_mem_map() with error returned: %u\n", err); 30 | return -1; 31 | } 32 | 33 | err = uc_mem_unmap(uc, 0x4000, 0x1000); 34 | if (err) { 35 | printf("not ok - Failed on uc_mem_unmap() with error returned: %u\n", err); 36 | return -1; 37 | } 38 | 39 | err = uc_mem_unmap(uc, 0x4000, 0x1000); 40 | if (!err) { 41 | printf("not ok - second unmap succeeded\n"); 42 | return -1; 43 | } 44 | 45 | printf("Tests OK\n"); 46 | uc_close(uc); 47 | return 0; 48 | } 49 | -------------------------------------------------------------------------------- /tests/regress/mem_map_0x100000000.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | int main() { 5 | uc_engine *u; 6 | uc_err err; 7 | 8 | printf("mem_map_0x100000000.c \n"); 9 | 10 | if ((err = uc_open(UC_ARCH_X86, UC_MODE_32, &u)) != UC_ERR_OK) { 11 | printf("uc_open() failed: %s\n", uc_strerror(err)); 12 | return -1; 13 | } 14 | 15 | if ((err = uc_mem_map(u, 0x100000000, 0x002c0000, UC_PROT_ALL)) != UC_ERR_OK) { 16 | printf("uc_mem_map() failed: %s\n", uc_strerror(err)); 17 | return -1; 18 | } 19 | if ((err = uc_mem_map(u, 0x0018D000, 0x00006000, UC_PROT_ALL)) != UC_ERR_OK) { 20 | printf("uc_mem_map() failed: %s\n", uc_strerror(err)); 21 | return -1; 22 | } 23 | 24 | if ((err = uc_close(u)) != UC_ERR_OK) { 25 | printf("uc_close() failed: %s\n", uc_strerror(err)); 26 | return -1; 27 | } 28 | 29 | printf("Success.\n"); 30 | return 0; 31 | } 32 | -------------------------------------------------------------------------------- /tests/regress/mem_map_large.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | 4 | int main() { 5 | uc_engine *u; 6 | uc_err err; 7 | if ((err = uc_open(UC_ARCH_X86, UC_MODE_32, &u)) != UC_ERR_OK) { 8 | printf("uc_open() failed: %s\n", uc_strerror(err)); 9 | } 10 | printf("Trying large map.\n"); 11 | if ((err = uc_mem_map(u, 0x60802000, (unsigned) 0x28bd211200004000, UC_PROT_ALL)) != UC_ERR_OK) { 12 | printf("uc_mem_map() failed: %s\n", uc_strerror(err)); 13 | return -1; 14 | } 15 | printf("Success.\n"); 16 | return 0; 17 | } 18 | -------------------------------------------------------------------------------- /tests/regress/memmap.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | # By Ryan Hileman, issue #9 3 | 4 | # this prints out 2 lines and the contents must be the same 5 | 6 | from unicorn import * 7 | import regress 8 | 9 | class MemMap(regress.RegressTest): 10 | 11 | def test_mmap_write(self): 12 | uc = Uc(UC_ARCH_X86, UC_MODE_64) 13 | 14 | uc.mem_map(0x8048000, 0x2000) 15 | uc.mem_write(0x8048000, 'test') 16 | s1 = str(uc.mem_read(0x8048000, 4)).encode('hex') 17 | 18 | self.assertEqual('test'.encode('hex'), s1) 19 | 20 | uc.mem_map(0x804a000, 0x8000) 21 | s2 = str(uc.mem_read(0x8048000, 4)).encode('hex') 22 | self.assertEqual(s1, s2) 23 | 24 | def test_mmap_invalid(self): 25 | u = unicorn.Uc(unicorn.UC_ARCH_X86, unicorn.UC_MODE_32) 26 | with self.assertRaises(UcError): 27 | u.mem_map(0x2000, 0) 28 | with self.assertRaises(UcError): 29 | u.mem_map(0x4000, 1) 30 | 31 | def test_mmap_weird(self): 32 | u = unicorn.Uc(unicorn.UC_ARCH_X86, unicorn.UC_MODE_32) 33 | 34 | for i in xrange(20): 35 | with self.assertRaises(UcError): 36 | u.mem_map(i*0x1000, 5) 37 | u.mem_read(i*0x1000+6, 1) 38 | 39 | if __name__ == '__main__': 40 | regress.main() 41 | -------------------------------------------------------------------------------- /tests/regress/memmap_segfault.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | 3 | import unicorn 4 | from unicorn import * 5 | 6 | import regress 7 | 8 | class MmapSeg(regress.RegressTest): 9 | 10 | def test_seg1(self): 11 | u = unicorn.Uc(unicorn.UC_ARCH_X86, unicorn.UC_MODE_32) 12 | u.mem_map(0x2000, 0x1000) 13 | u.mem_read(0x2000, 1) 14 | 15 | for i in range(50): 16 | u = unicorn.Uc(unicorn.UC_ARCH_X86, unicorn.UC_MODE_32) 17 | u.mem_map(i*0x1000, 0x1000) 18 | u.mem_read(i*0x1000, 1) 19 | 20 | for i in range(20): 21 | with self.assertRaises(UcError): 22 | u = unicorn.Uc(unicorn.UC_ARCH_X86, unicorn.UC_MODE_32) 23 | u.mem_map(i*0x1000, 5) 24 | u.mem_read(i*0x1000, 1) 25 | 26 | def test_seg2(self): 27 | uc = Uc(UC_ARCH_X86, UC_MODE_32) 28 | uc.mem_map(0x0000, 0x2000) 29 | uc.mem_map(0x2000, 0x4000) 30 | uc.mem_write(0x1000, 0x1004 * ' ') 31 | self.assertTrue(1, 32 | 'If not reached, then we have BUG (crash on x86_64 Linux).') 33 | 34 | if __name__ == '__main__': 35 | regress.main() 36 | -------------------------------------------------------------------------------- /tests/regress/mips_branch_delay.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | from capstone import * 3 | from unicorn import * 4 | 5 | import regress 6 | 7 | class MipsBranchDelay(regress.RegressTest): 8 | 9 | def runTest(self): 10 | md = Cs(CS_ARCH_MIPS, CS_MODE_MIPS32 + CS_MODE_LITTLE_ENDIAN) 11 | 12 | def disas(code, addr): 13 | for i in md.disasm(code, addr): 14 | print '0x%x: %s %-6s %s' % (i.address, str(i.bytes).encode('hex'), i.mnemonic, i.op_str) 15 | 16 | def hook_code(uc, addr, size, _): 17 | mem = str(uc.mem_read(addr, size)) 18 | disas(mem, addr) 19 | 20 | CODE = 0x400000 21 | asm = '0000a4126a00822800000000'.decode('hex') # beq $a0, $s5, 0x4008a0; slti $v0, $a0, 0x6a; nop 22 | 23 | print 'Input instructions:' 24 | disas(asm, CODE) 25 | print 26 | 27 | print 'Hooked instructions:' 28 | 29 | uc = Uc(UC_ARCH_MIPS, UC_MODE_MIPS32 + UC_MODE_LITTLE_ENDIAN) 30 | uc.hook_add(UC_HOOK_CODE, hook_code) 31 | uc.mem_map(CODE, 0x1000) 32 | uc.mem_write(CODE, asm) 33 | self.assertEqual(None, uc.emu_start(CODE, CODE + len(asm))) 34 | 35 | if __name__ == '__main__': 36 | regress.main() 37 | -------------------------------------------------------------------------------- /tests/regress/mips_except.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | from unicorn import * 3 | from unicorn.mips_const import * 4 | 5 | import regress 6 | 7 | def hook_intr(uc, intno, _): 8 | print 'interrupt', intno 9 | 10 | CODE = 0x400000 11 | asm = '0000a48f'.decode('hex') # lw $a0, ($sp) 12 | 13 | class MipsExcept(regress.RegressTest): 14 | 15 | def runTest(self): 16 | uc = Uc(UC_ARCH_MIPS, UC_MODE_MIPS32 + UC_MODE_LITTLE_ENDIAN) 17 | uc.hook_add(UC_HOOK_INTR, hook_intr) 18 | uc.mem_map(CODE, 0x1000) 19 | uc.mem_write(CODE, asm) 20 | 21 | with self.assertRaises(UcError) as m: 22 | uc.reg_write(UC_MIPS_REG_SP, 0x400001) 23 | uc.emu_start(CODE, CODE + len(asm), 300) 24 | 25 | self.assertEqual(UC_ERR_READ_UNALIGNED, m.exception.errno) 26 | 27 | with self.assertRaises(UcError) as m: 28 | uc.reg_write(UC_MIPS_REG_SP, 0xFFFFFFF0) 29 | uc.emu_start(CODE, CODE + len(asm), 200) 30 | 31 | self.assertEqual(UC_ERR_READ_UNMAPPED, m.exception.errno) 32 | 33 | with self.assertRaises(UcError) as m: 34 | uc.reg_write(UC_MIPS_REG_SP, 0x80000000) 35 | uc.emu_start(CODE, CODE + len(asm), 100) 36 | 37 | self.assertEqual(UC_ERR_READ_UNMAPPED, m.exception.errno) 38 | 39 | if __name__ == '__main__': 40 | regress.main() 41 | 42 | -------------------------------------------------------------------------------- /tests/regress/mips_invalid_read_of_size_4_when_tracing.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | static void hook_code(uc_engine *uc, uint64_t address, uint32_t size, void *user_data) { 4 | printf("tracing\n"); 5 | } 6 | 7 | #define HARDWARE_ARCHITECTURE UC_ARCH_MIPS 8 | #define HARDWARE_MODE UC_MODE_MIPS32 9 | 10 | #define MEMORY_STARTING_ADDRESS 0x1000000 11 | #define MEMORY_SIZE 2 * 1024 * 1024 12 | #define MEMORY_PERMISSIONS UC_PROT_ALL 13 | 14 | #define BINARY_CODE "00000000000000000000000000AA" 15 | 16 | int main(int argc, char **argv, char **envp) { 17 | uc_engine *uc; 18 | if (uc_open(HARDWARE_ARCHITECTURE, HARDWARE_MODE, &uc)) { 19 | printf("uc_open(…) failed\n"); 20 | return 1; 21 | } 22 | uc_mem_map(uc, MEMORY_STARTING_ADDRESS, MEMORY_SIZE, MEMORY_PERMISSIONS); 23 | if (uc_mem_write(uc, MEMORY_STARTING_ADDRESS, BINARY_CODE, sizeof(BINARY_CODE) - 1)) { 24 | printf("uc_mem_write(…) failed\n"); 25 | return 1; 26 | } 27 | uc_hook trace; 28 | uc_hook_add(uc, &trace, UC_HOOK_CODE, hook_code, NULL, MEMORY_STARTING_ADDRESS, MEMORY_STARTING_ADDRESS + 1); 29 | printf("uc_emu_start(…)\n"); 30 | uc_emu_start(uc, MEMORY_STARTING_ADDRESS, MEMORY_STARTING_ADDRESS + sizeof(BINARY_CODE) - 1, 0, 0); 31 | printf("done\n"); 32 | return 0; 33 | } 34 | -------------------------------------------------------------------------------- /tests/regress/mips_kernel_mmu.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | 3 | from unicorn import * 4 | from unicorn.mips_const import * 5 | 6 | import regress 7 | 8 | class MipsSyscall(regress.RegressTest): 9 | def test(self): 10 | addr = 0x80000000 11 | code = '34213456'.decode('hex') # ori $at, $at, 0x3456 12 | 13 | uc = Uc(UC_ARCH_MIPS, UC_MODE_MIPS32 + UC_MODE_BIG_ENDIAN) 14 | uc.mem_map(addr, 0x1000) 15 | uc.mem_write(addr, code) 16 | uc.reg_write(UC_MIPS_REG_AT, 0) 17 | 18 | uc.emu_start(addr, addr + len(code)) 19 | 20 | self.assertEqual(uc.reg_read(UC_MIPS_REG_AT), 0x3456) 21 | 22 | 23 | if __name__ == '__main__': 24 | regress.main() 25 | -------------------------------------------------------------------------------- /tests/regress/mips_syscall_pc.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | 3 | from unicorn import * 4 | from unicorn.mips_const import * 5 | 6 | import regress 7 | 8 | def intr_hook(uc, intno, data): 9 | print 'interrupt=%d, v0=%d, pc=0x%08x' % (intno, uc.reg_read(UC_MIPS_REG_V0), uc.reg_read(UC_MIPS_REG_PC)) 10 | 11 | class MipsSyscall(regress.RegressTest): 12 | def test(self): 13 | addr = 0x40000 14 | code = '0c000000'.decode('hex') # syscall 15 | 16 | uc = Uc(UC_ARCH_MIPS, UC_MODE_MIPS32 + UC_MODE_LITTLE_ENDIAN) 17 | uc.mem_map(addr, 0x1000) 18 | uc.mem_write(addr, code) 19 | uc.reg_write(UC_MIPS_REG_V0, 100) 20 | uc.hook_add(UC_HOOK_INTR, intr_hook) 21 | 22 | uc.emu_start(addr, addr+len(code)) 23 | self.assertEqual(0x40004, uc.reg_read(UC_MIPS_REG_PC)) 24 | 25 | 26 | if __name__ == '__main__': 27 | regress.main() 28 | -------------------------------------------------------------------------------- /tests/regress/mov_gs_eax.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | 3 | from unicorn import * 4 | from unicorn.x86_const import * 5 | 6 | import regress 7 | 8 | class VldrPcInsn(regress.RegressTest): 9 | 10 | def runTest(self): 11 | uc = Uc(UC_ARCH_X86, UC_MODE_32) 12 | uc.mem_map(0x1000, 0x1000) 13 | # mov gs, eax; mov eax, 1 14 | code = '8ee8b801000000'.decode('hex') 15 | uc.mem_write(0x1000, code) 16 | uc.reg_write(UC_X86_REG_EAX, 0xFFFFFFFF) 17 | 18 | with self.assertRaises(UcError) as ex_ctx: 19 | uc.emu_start(0x1000, 0x1000 + len(code)) 20 | 21 | self.assertEquals(ex_ctx.exception.errno, UC_ERR_EXCEPTION) 22 | 23 | if __name__ == '__main__': 24 | regress.main() 25 | -------------------------------------------------------------------------------- /tests/regress/movsd.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | # By Ryan Hileman, issue #3 3 | 4 | from capstone import * 5 | from unicorn import * 6 | from unicorn.x86_const import * 7 | 8 | import regress 9 | code = 'f20f1005aa120000'.decode('hex') 10 | 11 | def dis(mem, addr): 12 | md = Cs(CS_ARCH_X86, CS_MODE_64) 13 | return '\n'.join([ 14 | '%s %s' % (i.mnemonic, i.op_str) 15 | for i in md.disasm(str(mem), addr) 16 | ]) 17 | 18 | def hook_code(uc, addr, size, user_data): 19 | mem = uc.mem_read(addr, size) 20 | print 'instruction size:', size 21 | print 'instruction:', str(mem).encode('hex'), dis(mem, addr) 22 | print 'reference: ', code.encode('hex'), dis(code, addr) 23 | 24 | class Movsd(regress.RegressTest): 25 | 26 | def runTest(self): 27 | addr = 0x400000 28 | mu = Uc(UC_ARCH_X86, UC_MODE_64) 29 | mu.hook_add(UC_HOOK_CODE, hook_code) 30 | mu.mem_map(addr, 8 * 1024 * 1024) 31 | mu.mem_write(addr, code) 32 | mu.emu_start(addr, addr + len(code)) 33 | 34 | if __name__ == '__main__': 35 | regress.main() 36 | -------------------------------------------------------------------------------- /tests/regress/osx_qemu_thread_create_crash.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | 3 | import platform 4 | import resource 5 | 6 | from unicorn import * 7 | 8 | import regress 9 | 10 | # OS X: OK with 2047 iterations. 11 | # OS X: Crashes at 2048:th iteration ("qemu: qemu_thread_create: Resource temporarily unavailable"). 12 | # Linux: No crashes observed. 13 | class ThreadCreateCrash(regress.RegressTest): 14 | def test(self): 15 | for i in xrange(2048): 16 | Uc(UC_ARCH_X86, UC_MODE_64) 17 | self.assertTrue(True, "If not reached, then we have a crashing bug.") 18 | 19 | if __name__ == '__main__': 20 | regress.main() 21 | -------------------------------------------------------------------------------- /tests/regress/potential_memory_leak.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | 3 | import platform 4 | import resource 5 | 6 | from unicorn import * 7 | 8 | import regress 9 | 10 | class MemoryLeak(regress.RegressTest): 11 | def test(self): 12 | if platform.system() == "Darwin": 13 | rusage_multiplier = 1 14 | elif platform.system() == "Linux": 15 | rusage_multiplier = 1024 16 | else: 17 | # resource.getrusage(...) is platform dependent. Only tested under OS X and Linux. 18 | return 19 | max_rss_before = resource.getrusage(resource.RUSAGE_SELF).ru_maxrss * rusage_multiplier 20 | for i in xrange(10000): 21 | mu = Uc(UC_ARCH_X86, UC_MODE_64) 22 | mu.mem_map(0, 4096) 23 | mu.emu_start(0, 0) 24 | max_rss_after = resource.getrusage(resource.RUSAGE_SELF).ru_maxrss * rusage_multiplier 25 | rss_increase_per_iteration = (max_rss_after - max_rss_before) / i 26 | self.assertLess(rss_increase_per_iteration, 8000) 27 | 28 | if __name__ == '__main__': 29 | regress.main() 30 | -------------------------------------------------------------------------------- /tests/regress/pshufb.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | # By Ryan Hileman, issue #91 3 | 4 | # Invalid instruction = test failed 5 | 6 | from unicorn import * 7 | from unicorn.x86_const import * 8 | 9 | import regress 10 | 11 | class Pshufb(regress.RegressTest): 12 | 13 | def runTest(self): 14 | uc = Uc(UC_ARCH_X86, UC_MODE_64) 15 | uc.mem_map(0x2000, 0x1000) 16 | # pshufb xmm0, xmm1 17 | uc.mem_write(0x2000, '660f3800c1'.decode('hex')) 18 | uc.emu_start(0x2000, 0x2005) 19 | 20 | if __name__ == '__main__': 21 | regress.main() 22 | -------------------------------------------------------------------------------- /tests/regress/reg_write_sign_extension.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | 3 | """See https://github.com/unicorn-engine/unicorn/issues/98""" 4 | 5 | import unicorn 6 | import regress 7 | 8 | ADDR = 0xffaabbcc 9 | 10 | def hook_mem_invalid(mu, access, address, size, value, user_data): 11 | print ">>> Access type: %u, expected value: 0x%x, actual value: 0x%x" % (access, ADDR, address) 12 | assert(address == ADDR) 13 | mu.mem_map(address & 0xfffff000, 4 * 1024) 14 | mu.mem_write(address, b'\xcc') 15 | return True 16 | 17 | class RegWriteSignExt(regress.RegressTest): 18 | 19 | def runTest(self): 20 | mu = unicorn.Uc(unicorn.UC_ARCH_X86, unicorn.UC_MODE_32) 21 | mu.reg_write(unicorn.x86_const.UC_X86_REG_EBX, ADDR) 22 | 23 | mu.mem_map(0x10000000, 1024 * 4) 24 | # jmp ebx 25 | mu.mem_write(0x10000000, b'\xff\xe3') 26 | 27 | mu.hook_add(unicorn.UC_HOOK_MEM_FETCH_UNMAPPED | unicorn.UC_HOOK_MEM_FETCH_PROT, hook_mem_invalid) 28 | mu.emu_start(0x10000000, 0x10000000 + 2, count=1) 29 | 30 | if __name__ == '__main__': 31 | regress.main() 32 | -------------------------------------------------------------------------------- /tests/regress/regress.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | 3 | import unittest 4 | 5 | from os.path import dirname, basename, isfile 6 | import glob 7 | 8 | # Find all unittest type in this directory and run it. 9 | 10 | class RegressTest(unittest.TestCase): 11 | pass 12 | 13 | def main(): 14 | unittest.main() 15 | 16 | if __name__ == '__main__': 17 | directory = dirname(__file__) 18 | if directory == '': 19 | directory = '.' 20 | modules = glob.glob(directory+"/*.py") 21 | __all__ = [ basename(f)[:-3] for f in modules if isfile(f)] 22 | suite = unittest.TestSuite() 23 | 24 | for module in __all__: 25 | m = __import__(module) 26 | for cl in dir(m): 27 | try: 28 | realcl = getattr(m,cl) 29 | if issubclass(realcl, unittest.TestCase): 30 | suite.addTest(realcl()) 31 | except Exception as e: 32 | pass 33 | 34 | unittest.TextTestRunner().run(suite) 35 | -------------------------------------------------------------------------------- /tests/regress/regress.sh: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | 3 | 4 | ./map_crash 5 | ./map_write 6 | ./sigill 7 | ./sigill2 8 | ./block_test 9 | ./ro_mem_test 10 | ./nr_mem_test 11 | ./timeout_segfault 12 | ./rep_movsb 13 | ./mem_unmap 14 | ./mem_protect 15 | ./mem_exec 16 | ./mem_map_large 17 | ./00opcode_uc_crash 18 | ./eflags_noset 19 | ./eflags_nosync 20 | ./mips_kseg0_1 21 | ./mem_double_unmap 22 | 23 | -------------------------------------------------------------------------------- /tests/regress/rep_hook.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | from unicorn import * 3 | from unicorn.x86_const import * 4 | import regress 5 | 6 | PAGE_SIZE = 4 * 1024 7 | 8 | CODE = b'\xf3\xaa' # rep stosb 9 | 10 | 11 | def hook_code(uc, addr, size, user_data): 12 | print("hook called at %x" %addr) 13 | 14 | class REP(regress.RegressTest): 15 | 16 | def test_rep(self): 17 | mu = Uc(UC_ARCH_X86, UC_MODE_32) 18 | 19 | mu.mem_map(0, PAGE_SIZE) 20 | mu.mem_write(0, CODE) 21 | mu.reg_write(UC_X86_REG_ECX, 3) 22 | mu.reg_write(UC_X86_REG_EDI, 0x100) 23 | mu.hook_add(UC_HOOK_CODE, hook_code) 24 | 25 | mu.emu_start(0, len(CODE)) 26 | self.assertEqual(0, mu.reg_read(UC_X86_REG_ECX)) 27 | 28 | 29 | if __name__ == '__main__': 30 | regress.main() 31 | -------------------------------------------------------------------------------- /tests/regress/segfault_on_stop.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | 3 | import regress 4 | import unicorn 5 | 6 | 7 | class SegfaultOnStop(regress.RegressTest): 8 | def test(self): 9 | unicorn.Uc(unicorn.UC_ARCH_X86, unicorn.UC_MODE_64).emu_stop() 10 | self.assertTrue(True, "If not reached, then we have a crashing bug.") 11 | 12 | if __name__ == '__main__': 13 | regress.main() 14 | -------------------------------------------------------------------------------- /tests/regress/sigill.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | 6 | #define UC_BUG_WRITE_SIZE 128 7 | #define UC_BUG_WRITE_ADDR 0x1000 // fix this by change this to 0x2000 8 | 9 | int got_sigill = 0; 10 | 11 | void _interrupt(uc_engine *uc, uint32_t intno, void *user_data) 12 | { 13 | if (intno == 6) { 14 | uc_emu_stop(uc); 15 | got_sigill = 1; 16 | } 17 | } 18 | 19 | int main() 20 | { 21 | int size; 22 | uint8_t *buf; 23 | uc_engine *uc; 24 | uc_hook uh_trap; 25 | uc_err err = uc_open (UC_ARCH_X86, UC_MODE_64, &uc); 26 | if (err) { 27 | fprintf (stderr, "Cannot initialize unicorn\n"); 28 | return 1; 29 | } 30 | size = UC_BUG_WRITE_SIZE; 31 | buf = malloc (size); 32 | if (!buf) { 33 | fprintf (stderr, "Cannot allocate\n"); 34 | return 1; 35 | } 36 | memset (buf, 0, size); 37 | if (!uc_mem_map(uc, UC_BUG_WRITE_ADDR, size, UC_PROT_ALL)) { 38 | uc_mem_write(uc, UC_BUG_WRITE_ADDR, 39 | (const uint8_t*)"\xff\xff\xff\xff\xff\xff\xff\xff", 8); 40 | } 41 | uc_hook_add(uc, &uh_trap, UC_HOOK_INTR, _interrupt, NULL, 1, 0); 42 | uc_emu_start(uc, UC_BUG_WRITE_ADDR, UC_BUG_WRITE_ADDR+8, 0, 1); 43 | uc_close(uc); 44 | free(buf); 45 | printf ("Correct: %s\n", got_sigill? "YES": "NO"); 46 | return got_sigill? 0: 1; 47 | } 48 | -------------------------------------------------------------------------------- /tests/regress/sigill2.c: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | 6 | #define UC_BUG_WRITE_SIZE 128 7 | #define UC_BUG_WRITE_ADDR 0x2000 8 | 9 | int main() 10 | { 11 | int size; 12 | uc_engine *uc; 13 | 14 | uc_err err = uc_open (UC_ARCH_X86, UC_MODE_64, &uc); 15 | if (err) { 16 | fprintf (stderr, "Cannot initialize unicorn\n"); 17 | return 1; 18 | } 19 | size = UC_BUG_WRITE_SIZE; 20 | if (!uc_mem_map (uc, UC_BUG_WRITE_ADDR, size, UC_PROT_ALL)) { 21 | uc_mem_write (uc, UC_BUG_WRITE_ADDR, 22 | (const uint8_t*)"\xff\xff\xff\xff\xff\xff\xff\xff", 8); 23 | } 24 | err = uc_emu_start(uc, UC_BUG_WRITE_ADDR, UC_BUG_WRITE_ADDR+8, 0, 1); 25 | uc_close(uc); 26 | printf ("Error = %u (%s)\n", err, uc_strerror(err)); 27 | return err? -1: 0; 28 | } 29 | -------------------------------------------------------------------------------- /tests/regress/sparc64.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | 3 | from unicorn import * 4 | from unicorn.sparc_const import * 5 | 6 | PAGE_SIZE = 1 * 1024 * 1024 7 | 8 | uc = Uc(UC_ARCH_SPARC, UC_MODE_SPARC64|UC_MODE_BIG_ENDIAN) 9 | uc.reg_write(UC_SPARC_REG_SP, 100) 10 | print 'writing sp = 100' 11 | 12 | # 0: b0 06 20 01 inc %i0 13 | # 4: b2 06 60 01 inc %i1 14 | 15 | CODE = "\xb0\x06\x20\x01" \ 16 | "\xb2\x06\x60\x01" 17 | 18 | uc.mem_map(0, PAGE_SIZE) 19 | uc.mem_write(0, CODE) 20 | uc.emu_start(0, len(CODE), 0, 2) 21 | 22 | print 'sp =', uc.reg_read(UC_SPARC_REG_SP) 23 | print 'i0 =', uc.reg_read(UC_SPARC_REG_I0) 24 | print 'i1 =', uc.reg_read(UC_SPARC_REG_I1) 25 | -------------------------------------------------------------------------------- /tests/regress/sparc_jump_to_zero.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | #define HARDWARE_ARCHITECTURE UC_ARCH_SPARC 4 | #define HARDWARE_MODE UC_MODE_SPARC32|UC_MODE_BIG_ENDIAN 5 | 6 | #define MEMORY_STARTING_ADDRESS 0x1000000 7 | #define MEMORY_SIZE 2 * 1024 * 1024 8 | #define MEMORY_PERMISSIONS UC_PROT_ALL 9 | 10 | #define BINARY_CODE "\x02\xbc\x00\x00" 11 | 12 | int main(int argc, char **argv, char **envp) { 13 | uc_engine *uc; 14 | if (uc_open(HARDWARE_ARCHITECTURE, HARDWARE_MODE, &uc)) { 15 | printf("uc_open(…) failed\n"); 16 | return 1; 17 | } 18 | uc_mem_map(uc, MEMORY_STARTING_ADDRESS, MEMORY_SIZE, MEMORY_PERMISSIONS); 19 | if (uc_mem_write(uc, MEMORY_STARTING_ADDRESS, BINARY_CODE, sizeof(BINARY_CODE) - 1)) { 20 | printf("uc_mem_write(…) failed\n"); 21 | return 1; 22 | } 23 | printf("uc_emu_start(…)\n"); 24 | uc_emu_start(uc, MEMORY_STARTING_ADDRESS, MEMORY_STARTING_ADDRESS + sizeof(BINARY_CODE) - 1, 0, 20); 25 | printf("done\n"); 26 | return 0; 27 | } 28 | -------------------------------------------------------------------------------- /tests/regress/write_before_map.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | 3 | from __future__ import print_function 4 | from unicorn import * 5 | from unicorn.x86_const import * 6 | 7 | import regress 8 | 9 | X86_CODE64 = "\x90" # NOP 10 | 11 | 12 | class WriteBeforeMap(regress.RegressTest): 13 | def runTest(self): 14 | # Initialize emulator in X86-32bit mode 15 | mu = Uc(UC_ARCH_X86, UC_MODE_64) 16 | 17 | # memory address where emulation starts 18 | ADDRESS = 0x1000000 19 | 20 | # write machine code to be emulated to memory 21 | mu.mem_write(ADDRESS, X86_CODE64) 22 | 23 | 24 | if __name__ == '__main__': 25 | regress.main() 26 | -------------------------------------------------------------------------------- /tests/regress/wrong_rip_arm.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | 3 | from unicorn import * 4 | from unicorn.x86_const import * 5 | from unicorn.arm_const import * 6 | 7 | import regress 8 | 9 | # adds r1, #0x48 10 | # ldrsb r7, [r7, r7] 11 | # ldrsh r7, [r2, r1] 12 | # ldr r0, [pc, #0x168] 13 | # cmp r7, #0xbf 14 | # str r7, [r5, #0x20] 15 | # ldr r1, [r5, #0x64] 16 | # strb r7, [r5, #0xc] 17 | # ldr r0, [pc, #0x1a0] 18 | binary1 = b'\x48\x31\xff\x57\x57\x5e\x5a\x48\xbf\x2f\x2f\x62\x69\x6e\x2f\x73\x68\x48\xc1\xef\x08\x57\x54\x5f\x6a\x3b\x58\x0f\x05' 19 | # binary1 = b'\x48\x31\xff\x57' 20 | #adds r1, #0x48 21 | #ldrsb r7, [r7, r7] 22 | 23 | class WrongRIPArm(regress.RegressTest): 24 | 25 | def runTest(self): 26 | mu = Uc(UC_ARCH_ARM, UC_MODE_THUMB) 27 | mu.mem_map(0, 2 * 1024 * 1024) 28 | # write machine code to be emulated to memory 29 | mu.mem_write(0, binary1) 30 | mu.reg_write(UC_ARM_REG_R13, 1 * 1024 * 1024) 31 | # emu for maximum 1 instruction. 32 | mu.emu_start(0, len(binary1), 0, 1) 33 | self.assertEqual(0x48, mu.reg_read(UC_ARM_REG_R1)) 34 | pos = mu.reg_read(UC_ARM_REG_R15) 35 | self.assertEqual(0x2, pos) 36 | 37 | if __name__ == '__main__': 38 | regress.main() 39 | -------------------------------------------------------------------------------- /tests/regress/wrong_sp_arm.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | # By Ryan Hileman, issue #16 3 | 4 | from unicorn import * 5 | from unicorn.arm_const import * 6 | from unicorn.arm64_const import * 7 | 8 | import regress 9 | 10 | class WrongSPArm(regress.RegressTest): 11 | 12 | def test_32(self): 13 | with self.assertRaises(UcError): 14 | uc = Uc(UC_ARCH_ARM, UC_MODE_32) 15 | uc.reg_write(UC_ARM_REG_SP, 4) 16 | 17 | def test_64(self): 18 | uc = Uc(UC_ARCH_ARM64, UC_MODE_ARM) 19 | uc.reg_write(UC_ARM64_REG_SP, 4) 20 | self.assertEqual(0x4, uc.reg_read(UC_ARM64_REG_SP)) 21 | 22 | def test_arm(self): 23 | uc = Uc(UC_ARCH_ARM, UC_MODE_ARM) 24 | uc.reg_write(UC_ARM_REG_SP, 4) 25 | self.assertEqual(0x4, uc.reg_read(UC_ARM_REG_SP)) 26 | 27 | if __name__ == '__main__': 28 | regress.main() 29 | -------------------------------------------------------------------------------- /tests/regress/x86_16_segfault.c: -------------------------------------------------------------------------------- 1 | #include 2 | 3 | #define BINARY "\x90" 4 | #define MEMORY_SIZE 4 * 1024 5 | #define STARTING_ADDRESS 100 * 1024 6 | 7 | int main(int argc, char **argv, char **envp) { 8 | uc_engine *uc; 9 | if (uc_open(UC_ARCH_X86, UC_MODE_16, &uc)) { 10 | printf("uc_open(…) failed\n"); 11 | return 1; 12 | } 13 | uc_mem_map(uc, STARTING_ADDRESS, MEMORY_SIZE, UC_PROT_ALL); 14 | if (uc_mem_write(uc, STARTING_ADDRESS, BINARY, sizeof(BINARY) - 1)) { 15 | printf("uc_mem_write(…) failed\n"); 16 | return 1; 17 | } 18 | printf("uc_emu_start(…)\n"); 19 | uc_emu_start(uc, STARTING_ADDRESS, STARTING_ADDRESS + sizeof(BINARY) - 1, 0, 20); 20 | printf("done\n"); 21 | return 0; 22 | } 23 | -------------------------------------------------------------------------------- /tests/regress/x86_64_eflags.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | import regress 3 | import unicorn as U 4 | 5 | class WrongEFLAGS(regress.RegressTest): 6 | def test_eflags(self): 7 | # xor r14,r14 8 | CODE = 'M1\xf6' 9 | 10 | uc = U.Uc(U.UC_ARCH_X86, U.UC_MODE_64) 11 | uc.reg_write(U.x86_const.UC_X86_REG_RIP, 0x6000b0) 12 | uc.reg_write(U.x86_const.UC_X86_REG_EFLAGS, 0x200) 13 | 14 | uc.mem_map(0x600000, 0x1000) 15 | uc.mem_write(0x6000b0, CODE) 16 | uc.emu_start(0x6000b0, 0, count=1) 17 | 18 | 19 | # Here's the original execution trace for this on actual hardware. 20 | # 21 | # (gdb) x/i $pc 22 | # => 0x6000b0: xor %r14,%r14 23 | # (gdb) p/x $eflags 24 | # $1 = 0x200 25 | # (gdb) p $eflags 26 | # $2 = [ IF ] 27 | # (gdb) si 28 | # 0x00000000006000b3 in ?? () 29 | # (gdb) p/x $eflags 30 | # $3 = 0x246 31 | # (gdb) p $eflags 32 | # $4 = [ PF ZF IF ] 33 | 34 | self.assertEqual(0x6000b3, uc.reg_read(U.x86_const.UC_X86_REG_RIP)) 35 | self.assertEqual(0x246, uc.reg_read(U.x86_const.UC_X86_REG_EFLAGS)) 36 | 37 | if __name__ == '__main__': 38 | regress.main() 39 | -------------------------------------------------------------------------------- /tests/regress/x86_eflags.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/python 2 | import regress 3 | import unicorn as U 4 | 5 | class WrongEFLAGS2(regress.RegressTest): 6 | def test_eflags(self): 7 | # imul eax, ebx 8 | CODE = '\x0f\xaf\xc3' 9 | 10 | uc = U.Uc(U.UC_ARCH_X86, U.UC_MODE_32) 11 | uc.reg_write(U.x86_const.UC_X86_REG_EAX, 16) 12 | uc.reg_write(U.x86_const.UC_X86_REG_EBX, 1) 13 | uc.reg_write(U.x86_const.UC_X86_REG_EFLAGS, 0x292) 14 | 15 | uc.mem_map(0x600000, 0x1000) 16 | uc.mem_write(0x6000b0, CODE) 17 | uc.emu_start(0x6000b0, 0, count=1) 18 | 19 | 20 | # Here's the original execution trace for this on actual hardware. 21 | # 22 | # (gdb) x/i $eip 23 | # => 0x804aae5: imul eax,DWORD PTR [ebp-0x8] 24 | # (gdb) p/x $eax 25 | # $2 = 0x10 26 | # (gdb) x/wx $ebp-8 27 | # 0xbaaaad4c: 0x00000001 28 | # (gdb) p/x $eflags 29 | # $3 = 0x292 30 | # (gdb) si 31 | # 0x0804aae9 in ?? () 32 | # (gdb) p/x $eflags 33 | # $4 = 0x202 34 | 35 | self.assertEqual(0x202, uc.reg_read(U.x86_const.UC_X86_REG_EFLAGS)) 36 | 37 | if __name__ == '__main__': 38 | regress.main() 39 | -------------------------------------------------------------------------------- /tests/regress/x86_fldt_fsqrt.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | from unicorn import * 3 | from unicorn.x86_const import * 4 | from struct import pack 5 | 6 | import regress 7 | 8 | CODE_ADDR = 0x1000000 9 | CODE = ( 10 | '\xb8\x00\x00\x00\x02' # mov eax, 0x2000000 11 | '\xdb\x28' # fldt [eax] 12 | '\xd9\xfa' # fsqrt 13 | ) 14 | 15 | DATA_ADDR = 0x2000000 16 | DATA = '\0\0\0\0\0\0\0\0\0\1' 17 | 18 | class FldtFsqrt(regress.RegressTest): 19 | def test_fldt_fsqrt(self): 20 | uc = Uc(UC_ARCH_X86, UC_MODE_32) 21 | 22 | uc.mem_map(CODE_ADDR, 0x1000) 23 | uc.mem_write(CODE_ADDR, CODE) 24 | 25 | uc.mem_map(DATA_ADDR, 0x1000) 26 | uc.mem_write(DATA_ADDR, DATA) 27 | 28 | uc.emu_start(CODE_ADDR, CODE_ADDR + len(CODE), 10000, 10) 29 | 30 | if __name__ == '__main__': 31 | regress.main() 32 | -------------------------------------------------------------------------------- /tests/regress/x86_self_modifying.elf: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/zhkl0228/unicorn/15cad005ed027685e5e3da429eb84325fba55f8a/tests/regress/x86_self_modifying.elf -------------------------------------------------------------------------------- /tests/regress/x86_self_modifying.py: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env python 2 | from unicorn import * 3 | from unicorn.x86_const import * 4 | from struct import pack 5 | 6 | import os 7 | import regress 8 | 9 | # The file we're loading is a full assembled ELF. 10 | # Source for it, along with assembly instructions, are in x86_self_modifying.s 11 | 12 | CODE_ADDR = 0x08048000 13 | STACK_ADDR = 0x2000000 14 | CODE = open(os.path.join(os.path.dirname(os.path.realpath(__file__)), 'x86_self_modifying.elf')).read() 15 | CODE_SIZE = len(CODE) + (0x1000 - len(CODE)%0x1000) 16 | STACK_SIZE = 0x8000 17 | 18 | ENTRY_POINT = 0x8048074 19 | 20 | def hook_intr(uc, intno, data): 21 | uc.emu_stop() 22 | 23 | class SelfModifying(regress.RegressTest): 24 | def test_self_modifying(self): 25 | uc = Uc(UC_ARCH_X86, UC_MODE_32) 26 | 27 | uc.mem_map(CODE_ADDR, CODE_SIZE, 5) 28 | uc.mem_map(STACK_ADDR, STACK_SIZE, 7) 29 | uc.mem_write(CODE_ADDR, CODE) 30 | uc.reg_write(UC_X86_REG_ESP, STACK_ADDR + STACK_SIZE) 31 | 32 | uc.hook_add(UC_HOOK_INTR, hook_intr) 33 | 34 | uc.emu_start(ENTRY_POINT, -1) 35 | 36 | retcode = uc.reg_read(UC_X86_REG_EBX) 37 | self.assertEqual(retcode, 65) 38 | 39 | if __name__ == '__main__': 40 | regress.main() 41 | -------------------------------------------------------------------------------- /tests/regress/x86_self_modifying.s: -------------------------------------------------------------------------------- 1 | # Assembly instructions (tested on ubuntu 16.04 x86_64): 2 | # $ as --32 x86_self_modifying.s -o x86_self_modifying.o 3 | # $ ld -melf_i386 -z execstack x86_self_modifying.o -o x86_self_modifying.elf 4 | 5 | # Test that it works. return code should be 65 6 | # $ ./x86_self_modifying.elf 7 | # $ echo $? 8 | # 65 9 | 10 | # Fix the entry point address in x86_self_modifying.py 11 | # $ readelf -h x86_self_modifying.elf | grep Entry 12 | # Entry point address: 0x8048074 13 | 14 | 15 | .intel_syntax noprefix 16 | 17 | .global _start 18 | _start: 19 | mov ebp, esp 20 | sub ebp, 0x4000 21 | mov edx, ebp 22 | 23 | lea esi, [self_modifying] 24 | mov edi, ebp 25 | mov ecx, 0x2d 26 | call memcpy 27 | add ebp, 0x2d 28 | xor ebx, ebx 29 | call edx 30 | 31 | mov eax, 1 32 | int 0x80 33 | 34 | memcpy: 35 | cmp ecx, 0 36 | je _end 37 | dec ecx 38 | mov al, byte ptr [esi+ecx] 39 | mov byte ptr [edi+ecx], al 40 | jmp memcpy 41 | 42 | _end: 43 | ret 44 | 45 | self_modifying: 46 | inc ebx 47 | call $+5 48 | pop esi 49 | dec byte ptr [esi+11] 50 | xor edx, edx 51 | sub esi, 6 52 | _loop_start: 53 | cmp edx, 5 54 | jz _loop_end 55 | 56 | mov edi, ebp 57 | mov ecx, 0x2d 58 | lea eax, [memcpy] 59 | call eax 60 | inc edx 61 | add ebp, 0x2d 62 | mov byte ptr [ebp], 0xc3 63 | jmp _loop_start 64 | 65 | _loop_end: 66 | -------------------------------------------------------------------------------- /tests/unit/.gitignore: -------------------------------------------------------------------------------- 1 | !*.c 2 | test_* 3 | *.bin 4 | -------------------------------------------------------------------------------- /tests/unit/gdt_idx.s: -------------------------------------------------------------------------------- 1 | .text 2 | sidt (esp) 3 | sgdt (esp+6) 4 | -------------------------------------------------------------------------------- /tests/unit/high_address.s: -------------------------------------------------------------------------------- 1 | dec %eax 2 | mov (%eax), %eax 3 | nop 4 | nop 5 | nop 6 | nop 7 | -------------------------------------------------------------------------------- /tests/unit/pc_change.s: -------------------------------------------------------------------------------- 1 | .text 2 | inc %ecx 3 | inc %ecx 4 | inc %ecx 5 | inc %ecx 6 | inc %ecx 7 | inc %ecx 8 | inc %edx 9 | inc %edx 10 | -------------------------------------------------------------------------------- /tests/unit/tb_x86.s: -------------------------------------------------------------------------------- 1 | mov %esp,%ecx 2 | fxch %st(5) 3 | fnstenv -0xc(%ecx) 4 | pop %ebp 5 | push %ebp 6 | pop %ecx 7 | dec %ecx 8 | dec %ecx 9 | dec %ecx 10 | dec %ecx 11 | dec %ecx 12 | dec %ecx 13 | dec %ecx 14 | dec %ecx 15 | dec %ecx 16 | dec %ecx 17 | inc %ebx 18 | inc %ebx 19 | inc %ebx 20 | inc %ebx 21 | inc %ebx 22 | inc %ebx 23 | aaa 24 | push %ecx 25 | pop %edx 26 | push $0x41 27 | pop %eax 28 | push %eax 29 | xor %al,0x30(%ecx) 30 | inc %ecx 31 | imul $0x51,0x41(%ecx),%eax 32 | xor 0x42(%ecx),%al 33 | xor 0x42(%edx),%al 34 | xor %al,0x42(%edx) 35 | inc %ecx 36 | inc %edx 37 | pop %eax 38 | push %eax 39 | cmp %al,0x42(%ecx) 40 | jne .+0x4c 41 | dec %ecx 42 | push %ecx 43 | push %ecx 44 | push %ecx 45 | push %edx 46 | inc %edi 47 | xor 0x34(%edi),%eax 48 | push %ecx 49 | push %ebp 50 | push %ecx 51 | push %esi 52 | push %eax 53 | inc %edi 54 | inc %edi 55 | cmp %al,0x39(%edi) 56 | push %eax 57 | dec %edx 58 | push %eax 59 | dec %ebx 60 | push %eax 61 | dec %esp 62 | push %eax 63 | dec %ebp 64 | push %eax 65 | dec %esi 66 | push %eax 67 | dec %edi 68 | push %eax 69 | push %eax 70 | push %eax 71 | xor %eax, 0x42(%edi) 72 | inc %edi 73 | inc %edx 74 | push %eax 75 | xor $0x50,%al 76 | pop %edx 77 | push %eax 78 | inc %ebp 79 | push %ecx 80 | push %edx 81 | inc %esi 82 | xor 0x31(%edi),%al 83 | push %eax 84 | dec %ebp 85 | push %ecx 86 | push %ecx 87 | push %eax 88 | dec %esi 89 | inc %ecx 90 | inc %ecx 91 | -------------------------------------------------------------------------------- /tests/unit/x86_soft_paging_low.s: -------------------------------------------------------------------------------- 1 | // Zero memory for page directories and page tables 2 | mov $0x1000,%edi 3 | mov $0x1000,%ecx 4 | xor %eax,%eax 5 | rep stos %eax,(%edi) 6 | 7 | // Load DWORD [0x4000] with 0xDEADBEEF to retrieve later 8 | mov $0x4000,%edi 9 | mov $0xBEEF,%eax 10 | mov %eax, (%edi) 11 | 12 | // Identify map the first 4MiB of memory 13 | mov $0x400,%ecx 14 | mov $0x2000,%edi 15 | mov $3, %eax 16 | loop: 17 | stos %eax,(%edi) 18 | add $0x1000,%eax 19 | loop loop 20 | 21 | // Map phyiscal address 0x4000 to cirtual address 0x7FF000 22 | mov $0x3ffc,%edi 23 | mov $0x4003,%eax 24 | mov %eax, (%edi) 25 | 26 | // Add page tables into page directory 27 | mov $0x1000, %edi 28 | mov $0x2003, %eax 29 | mov %eax, (%edi) 30 | mov $0x1004, %edi 31 | mov $0x3003, %eax 32 | mov %eax, (%edi) 33 | 34 | // Load the page directory register 35 | mov $0x1000, %eax 36 | mov %eax, %cr3 37 | 38 | // Enable paging 39 | mov %cr0, %eax 40 | or $0x80000000, %eax 41 | 42 | // Clear EAX 43 | mov %eax, %cr0 44 | 45 | //Load using virtual memory address; EAX = 0xBEEF 46 | xor %eax,%eax 47 | mov $0x7FF000, %esi 48 | mov (%esi), %eax 49 | hlt 50 | --------------------------------------------------------------------------------