Skip to content

Commit cc1cb5f

Browse files
Merge branch 'qilingframework:dev' into dev
2 parents c5100cb + 5da9098 commit cc1cb5f

File tree

7 files changed

+114
-95
lines changed

7 files changed

+114
-95
lines changed

qiling/const.py

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -57,11 +57,11 @@ class QL_INTERCEPT(IntEnum):
5757
QL_ARCH_32BIT = (QL_ARCH.ARM, QL_ARCH.ARM_THUMB, QL_ARCH.MIPS, QL_ARCH.X86, QL_ARCH.CORTEX_M)
5858
QL_ARCH_64BIT = (QL_ARCH.ARM64, QL_ARCH.X8664)
5959

60-
QL_OS_NONPID = (QL_OS.DOS, QL_OS.UEFI)
61-
QL_ARCH_HARDWARE = (QL_ARCH.CORTEX_M,)
62-
QL_ARCH_NONEOS = (QL_ARCH.EVM,)
63-
QL_OS_POSIX = (QL_OS.LINUX, QL_OS.FREEBSD, QL_OS.MACOS, QL_OS.QNX)
64-
QL_OS_ALL = QL_OS_POSIX + QL_OS_NONPID + (QL_OS.WINDOWS,)
60+
QL_OS_NONPID = (QL_OS.DOS, QL_OS.UEFI)
61+
QL_ARCH_BAREMETAL = (QL_ARCH.CORTEX_M,)
62+
QL_ARCH_INTERPRETER = (QL_ARCH.EVM,)
63+
QL_OS_POSIX = (QL_OS.LINUX, QL_OS.FREEBSD, QL_OS.MACOS, QL_OS.QNX)
64+
QL_OS_ALL = QL_OS_POSIX + QL_OS_NONPID + (QL_OS.WINDOWS,)
6565

6666
QL_HOOK_BLOCK = 0b0001
6767
QL_CALL_BLOCK = 0b0010

qiling/core.py

Lines changed: 90 additions & 70 deletions
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,7 @@
1919
from .hw.hw import QlHwManager
2020
from .loader.loader import QlLoader
2121

22-
from .const import QL_ARCH_ENDIAN, QL_ENDIAN, QL_OS, QL_VERBOSE, QL_ARCH_NONEOS, QL_ARCH_HARDWARE
22+
from .const import QL_ARCH_ENDIAN, QL_ENDIAN, QL_OS, QL_VERBOSE, QL_ARCH_INTERPRETER, QL_ARCH_BAREMETAL, QL_OS_ALL
2323
from .exception import QlErrorFileNotFound, QlErrorArch, QlErrorOsType, QlErrorOutput
2424
from .utils import *
2525
from .core_struct import QlCoreStructs
@@ -68,8 +68,10 @@ def __init__(
6868
self._code = code
6969
self._ostype = ostype
7070
self._archtype = archtype
71-
self._noneos = None,
72-
self._archendian = None
71+
self._interpreter = False
72+
self._baremetal = False
73+
self._gpos = False
74+
self._archendian = QL_ENDIAN.EL
7375
self._archbit = None
7476
self._pointersize = None
7577
self._profile = profile
@@ -106,53 +108,48 @@ def __init__(
106108
self.count = None
107109
self._initial_sp = None
108110

109-
110111
"""
111112
Qiling Framework Core Engine
112113
"""
113-
##############
114-
# Shellcode? #
115-
##############
116-
114+
###############
115+
# code_exec() #
116+
###############
117117
if self._code or (self._archtype and type(self._archtype) == str):
118118
if (self._archtype and type(self._archtype) == str):
119119
self._archtype= arch_convert(self._archtype.lower())
120120

121-
if (self._ostype and type(self._ostype) == str):
121+
if self._ostype == None:
122+
self._ostype = arch_os_convert(self._archtype)
123+
else:
122124
self._ostype = ostype_convert(self._ostype.lower())
123125

124-
if self._archtype in QL_ARCH_NONEOS or self._ostype == None:
125-
if self._ostype == None:
126-
self._ostype = arch_os_convert(self._archtype)
127-
if self._code == None:
128-
self._code = self._archtype
129-
130-
126+
if self._code == None:
127+
self._code = "qilingcode"
131128
if self._argv is None:
132129
self._argv = ["qilingcode"]
133130
if self._rootfs is None:
134131
self._rootfs = "."
135-
136-
# file check
137-
if self._code is None:
132+
133+
self._interpreter = True if self._archtype in (QL_ARCH_INTERPRETER) else False
134+
self._baremetal = True if self._archtype in (QL_ARCH_BAREMETAL) else False
135+
self._path = (str(self._argv[0]))
136+
self._targetname = ntpath.basename(self._argv[0])
137+
138+
##############
139+
# File check #
140+
##############
141+
if (not self._interpreter and not self._baremetal) and self._code == None:
138142
if not os.path.exists(str(self._argv[0])):
139143
raise QlErrorFileNotFound("Target binary not found: %s" %(self._argv[0]))
140144
if not os.path.exists(self._rootfs):
141145
raise QlErrorFileNotFound("Target rootfs not found")
142-
143-
self._path = (str(self._argv[0]))
144-
self._targetname = ntpath.basename(self._argv[0])
145-
146-
##########
147-
# Loader #
148-
##########
149-
if self._code is None:
146+
150147
guessed_archtype, guessed_ostype, guessed_archendian = ql_guess_emu_env(self._path)
148+
151149
if self._ostype is None:
152150
self._ostype = guessed_ostype
153151
if self._archtype is None:
154152
self._archtype = guessed_archtype
155-
if self.archendian is None:
156153
self._archendian = guessed_archendian
157154

158155
if not ql_is_valid_ostype(self._ostype):
@@ -161,6 +158,13 @@ def __init__(
161158
if not ql_is_valid_arch(self._archtype):
162159
raise QlErrorArch("Invalid Arch %s" % self._archtype)
163160

161+
162+
163+
164+
#######################################
165+
# Loader and General Purpose OS check #
166+
#######################################
167+
self._gpos = True if self._ostype in (QL_OS_ALL) else False
164168
self._loader = loader_setup(self._ostype, self)
165169

166170
#####################
@@ -169,7 +173,6 @@ def __init__(
169173
self._profile, debugmsg = profile_setup(self)
170174

171175
# Log's configuration
172-
173176
self._log_file_fd, self._log_filter = ql_setup_logger(self,
174177
self._log_file,
175178
self._console,
@@ -188,25 +191,23 @@ def __init__(
188191
self._archbit = ql_get_arch_bits(self._archtype)
189192
self._pointersize = (self.archbit // 8)
190193

191-
# Endian for shellcode needs to set manually
192-
if self._code:
193-
self._archendian = QL_ENDIAN.EL
194-
if bigendian == True and self._archtype in (QL_ARCH_ENDIAN):
195-
self._archendian = QL_ENDIAN.EB
194+
195+
if bigendian == True and self._archtype in (QL_ARCH_ENDIAN):
196+
self._archendian = QL_ENDIAN.EB
197+
196198

197199
# Once we finish setting up archendian and arcbit, we can init QlCoreStructs.
198200
QlCoreStructs.__init__(self, self._archendian, self._archbit)
199201

200202
##############
201203
# Components #
202204
##############
203-
204-
if self.archtype not in QL_ARCH_NONEOS:
205+
if self._gpos or self._baremetal:
205206
self._mem = component_setup("os", "memory", self)
206207
self._reg = component_setup("arch", "register", self)
207-
208-
if self.archtype in QL_ARCH_HARDWARE:
209-
self._hw = component_setup("hw", "hw", self)
208+
209+
if self._baremetal:
210+
self._hw = component_setup("hw", "hw", self)
210211

211212
self._arch = arch_setup(self.archtype, self)
212213

@@ -215,29 +216,27 @@ def __init__(
215216
QlCoreHooks.__init__(self, self.uc)
216217

217218
# Setup Outpt
218-
if self.archtype not in QL_ARCH_NONEOS:
219+
if self._gpos or self._baremetal:
219220
self.arch.utils.setup_output()
220221

221-
if (self.archtype not in QL_ARCH_NONEOS):
222-
if (self.archtype not in QL_ARCH_HARDWARE):
223-
self._os = os_setup(self.archtype, self.ostype, self)
222+
if self._gpos:
223+
self._os = os_setup(self.archtype, self.ostype, self)
224224

225-
if stdin is not None:
226-
self._os.stdin = stdin
225+
if stdin is not None:
226+
self._os.stdin = stdin
227227

228-
if stdout is not None:
229-
self._os.stdout = stdout
228+
if stdout is not None:
229+
self._os.stdout = stdout
230230

231-
if stderr is not None:
232-
self._os.stderr = stderr
231+
if stderr is not None:
232+
self._os.stderr = stderr
233233

234234
# Run the loader
235235
self.loader.run()
236236

237-
if (self.archtype not in QL_ARCH_NONEOS):
238-
if (self.archtype not in QL_ARCH_HARDWARE):
239-
# Add extra guard options when configured to do so
240-
self._init_stop_guard()
237+
if self._gpos:
238+
# Add extra guard options when configured to do so
239+
self._init_stop_guard()
241240

242241
#####################
243242
# Qiling Components #
@@ -471,6 +470,34 @@ def targetname(self) -> str:
471470
"""
472471
return self._targetname
473472

473+
@property
474+
def interpreter(self) -> bool:
475+
""" Interpreter Engine
476+
- Blockchain related
477+
- Java engine?
478+
479+
Type: bool
480+
"""
481+
return self._interpreter
482+
483+
@property
484+
def baremetal(self) -> bool:
485+
""" MCU / Bare Metal type
486+
- STM32, RTOS
487+
488+
Type: bool
489+
"""
490+
return self._baremetal
491+
492+
@property
493+
def gpos(self) -> bool:
494+
""" General purpose OS
495+
- Windows, Linux, MacOS and etc
496+
497+
Type: bool
498+
"""
499+
return self._gpos
500+
474501
@property
475502
def platform_os(self):
476503
""" Specify current platform os where Qiling runs on.
@@ -545,7 +572,7 @@ def verbose(self):
545572
def verbose(self, v):
546573
self._verbose = v
547574
self.log.setLevel(ql_resolve_logger_level(self._verbose))
548-
if self.archtype not in QL_ARCH_NONEOS:
575+
if self.interpreter:
549576
self.arch.utils.setup_output()
550577

551578
@property
@@ -710,32 +737,25 @@ def run(self, begin=None, end=None, timeout=0, count=0, code = None):
710737
if self._debugger != False and self._debugger != None:
711738
self._debugger = debugger_setup(self._debugger, self)
712739

713-
if self.archtype not in QL_ARCH_NONEOS and self.archtype not in QL_ARCH_HARDWARE:
740+
if self.interpreter:
741+
return self.arch.run(code)
742+
elif self.baremetal:
743+
self.__enable_bin_patch()
744+
if self.count <= 0:
745+
self.count = -1
746+
self.arch.run(count=self.count, end=self.exit_point)
747+
else:
714748
self.write_exit_trap()
715749
# patch binary
716750
self.__enable_bin_patch()
717-
718751
# emulate the binary
719752
self.os.run()
720753

721-
if self.archtype in QL_ARCH_NONEOS:
722-
if code == None:
723-
return self.arch.run(self._code)
724-
else:
725-
return self.arch.run(code)
726-
727-
if self.archtype in QL_ARCH_HARDWARE:
728-
self.__enable_bin_patch()
729-
if self.count <= 0:
730-
self.count = -1
731-
self.arch.run(count=self.count, end=self.exit_point)
732-
733754
# run debugger
734755
if self._debugger != False and self._debugger != None:
735756
self._debugger.run()
736757

737758

738-
739759
# patch code to memory address
740760
def patch(self, addr, code, file_name=b''):
741761
if file_name == b'':
@@ -872,7 +892,7 @@ def stop(self):
872892
if self.multithread:
873893
self.os.thread_management.stop()
874894

875-
elif self.archtype in QL_ARCH_HARDWARE:
895+
elif self.baremetal:
876896
self.arch.stop()
877897

878898
else:

qiling/core_hooks.py

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,7 @@
1515

1616
from .core_hooks_types import Hook, HookAddr, HookIntr, HookRet
1717
from .utils import catch_KeyboardInterrupt
18-
from .const import QL_HOOK_BLOCK, QL_ARCH_NONEOS
18+
from .const import QL_HOOK_BLOCK
1919
from .exception import QlErrorCoreHook
2020

2121
# Don't assume self is Qiling.
@@ -238,7 +238,7 @@ def ql_hook(self, hook_type: int, callback: Callable, user_data=None, begin=1, e
238238

239239

240240
def hook_code(self, callback, user_data=None, begin=1, end=0):
241-
if self.archtype in QL_ARCH_NONEOS:
241+
if self.interpreter:
242242
from .arch.evm.hooks import ql_evm_hooks
243243
return ql_evm_hooks(self, 'HOOK_CODE', callback, user_data, begin, end)
244244

@@ -281,7 +281,7 @@ def hook_mem_invalid(self, callback, user_data=None, begin=1, end=0):
281281
def hook_address(self, callback, address, user_data=None):
282282
hook = HookAddr(callback, address, user_data)
283283

284-
if self.archtype in QL_ARCH_NONEOS:
284+
if self.interpreter:
285285
from .arch.evm.hooks import evm_hook_address
286286
return evm_hook_address(self, 'HOOK_ADDR', hook, address)
287287

@@ -320,7 +320,7 @@ def hook_mem_fetch(self, callback, user_data=None, begin=1, end=0):
320320

321321

322322
def hook_insn(self, callback, arg1, user_data=None, begin=1, end=0):
323-
if self.archtype in QL_ARCH_NONEOS:
323+
if self.interpreter:
324324
from .arch.evm.hooks import evm_hook_insn
325325
return evm_hook_insn(self, 'HOOK_INSN', callback, arg1, user_data, begin, end)
326326

@@ -337,7 +337,7 @@ def hook_del(self, *args):
337337

338338
hook_type, h = args
339339

340-
if self.archtype in QL_ARCH_NONEOS:
340+
if self.interpreter:
341341
from .arch.evm.hooks import evm_hook_del
342342
return evm_hook_del(hook_type, h)
343343

qiling/debugger/gdb/gdb.py

Lines changed: 8 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -51,19 +51,18 @@ def __init__(self, ql: Qiling, ip: str = '127.0.01', port: int = 9999):
5151
self.ip = ip
5252
self.port = port
5353

54-
55-
if ql.archtype in QL_ARCH_HARDWARE:
56-
load_address = ql.loader.load_address
54+
if self.ql.baremetal:
55+
load_address = self.ql.loader.load_address
5756
exit_point = load_address + os.path.getsize(ql.path)
58-
elif ql.code:
59-
load_address = ql.os.entry_point
57+
elif self.ql.code and ql.gpos:
58+
load_address = self.ql.os.entry_point
6059
exit_point = load_address + len(ql.code)
6160
else:
6261
load_address = ql.loader.load_address
6362
exit_point = load_address + os.path.getsize(ql.path)
6463

65-
if ql.archtype in QL_ARCH_HARDWARE:
66-
self.entry_point = ql.loader.entry_point
64+
if self.ql.baremetal:
65+
self.entry_point = self.ql.loader.entry_point
6766
elif self.ql.ostype in (QL_OS.LINUX, QL_OS.FREEBSD) and not self.ql.code:
6867
self.entry_point = self.ql.os.elf_entry
6968
else:
@@ -506,7 +505,7 @@ def handle_q(subcmd):
506505

507506

508507
elif subcmd.startswith('Xfer:threads:read::0,'):
509-
if self.ql.ostype in QL_OS_NONPID or self.ql.archtype in QL_ARCH_HARDWARE:
508+
if self.ql.ostype in QL_OS_NONPID or self.ql.baremetal:
510509
self.send("l")
511510
else:
512511
file_contents = ("<threads>\r\n<thread id=\""+ str(self.ql.os.pid) + "\" core=\"1\" name=\"" + self.ql.targetname + "\"/>\r\n</threads>")
@@ -621,7 +620,7 @@ def handle_v(subcmd):
621620
self.send("")
622621

623622
elif subcmd.startswith('File:open'):
624-
if self.ql.ostype == QL_OS.UEFI or self.ql.archtype in QL_ARCH_HARDWARE:
623+
if self.ql.ostype == QL_OS.UEFI or self.ql.baremetal:
625624
self.send("F-1")
626625
return
627626

0 commit comments

Comments
 (0)