146 lines
5.9 KiB
Python
146 lines
5.9 KiB
Python
#!/usr/bin/python
|
|
# -*- coding: latin-1 -*-
|
|
# --------------------------------------------------------------------------------
|
|
# @Title: An exmple to show how to initiate the types T32_RegisterHandle,
|
|
# T32_SymbolHandle and T32_AddressHandle and how to call the obj functions
|
|
# @Description:
|
|
# TRACE32 Remote API sample program written in Python, illustrating
|
|
# the use of the types T32_RegisterHandle, T32_SymbolHandle and T32_AddressHandle
|
|
# and the obj functions
|
|
#
|
|
# TRACE32's configuration file "config.t32" has to contain these lines:
|
|
# RCL=NETASSIST
|
|
# PORT=20000
|
|
# The port value may be changed but has to match with the port number
|
|
# used in this python script.
|
|
#
|
|
# @Keywords: python
|
|
# @Author: WBA
|
|
# @Copyright: (C) 1989-2021 Lauterbach GmbH, licensed for use with TRACE32(R) only
|
|
# --------------------------------------------------------------------------------
|
|
# $Id: objfunctions.py $
|
|
#
|
|
|
|
import platform
|
|
import ctypes
|
|
|
|
# auto-detect the correct library
|
|
if (platform.system() == "Windows") or (platform.system()[0:6] == "CYGWIN"):
|
|
if ctypes.sizeof(ctypes.c_voidp) == 4:
|
|
# WINDOWS 32bit
|
|
t32api = ctypes.CDLL("./t32api.dll")
|
|
# alternative using windows DLL search order:
|
|
# t32api = ctypes.cdll.t32api
|
|
else:
|
|
# WINDOWS 64bit
|
|
t32api = ctypes.CDLL("./t32api64.dll")
|
|
# alternative using windows DLL search order:
|
|
# t32api = ctypes.cdll.t32api64
|
|
elif platform.system() == "Darwin":
|
|
# Mac OS X
|
|
t32api = ctypes.CDLL("./t32api.dylib")
|
|
else:
|
|
if ctypes.sizeof(ctypes.c_voidp) == 4:
|
|
# Linux 32bit
|
|
t32api = ctypes.CDLL("./t32api.so")
|
|
else:
|
|
# Linux 64bit
|
|
t32api = ctypes.CDLL("./t32api64.so")
|
|
|
|
|
|
def check_error(error):
|
|
"""Raises a ValueError if error is not zero."""
|
|
if error != 0:
|
|
raise ValueError(f"{error}")
|
|
|
|
|
|
# declare the argument- and return-types of the functions used in this file
|
|
t32api.T32_Config.argtypes = [ctypes.POINTER(ctypes.c_char)]
|
|
t32api.T32_Config.restype = ctypes.c_int
|
|
t32api.T32_Init.argtypes = []
|
|
t32api.T32_Init.restype = ctypes.c_int
|
|
t32api.T32_Attach.argtypes = [ctypes.c_int]
|
|
t32api.T32_Attach.restype = ctypes.c_int
|
|
t32api.T32_Ping.argtypes = []
|
|
t32api.T32_Ping.restype = ctypes.c_int
|
|
t32api.T32_RequestSymbolObjName.argtypes = [ctypes.POINTER(ctypes.c_void_p), ctypes.POINTER(ctypes.c_char)]
|
|
t32api.T32_RequestSymbolObjName.restype = ctypes.c_int
|
|
t32api.T32_QuerySymbolObj.argtypes = [ctypes.c_void_p]
|
|
t32api.T32_QuerySymbolObj.restype = ctypes.c_int
|
|
t32api.T32_GetSymbolObjAddress.argtypes = [ctypes.c_void_p, ctypes.POINTER(ctypes.c_void_p)]
|
|
t32api.T32_GetSymbolObjAddress.restype = ctypes.c_int
|
|
t32api.T32_GetAddressObjAddr64.argtypes = [ctypes.POINTER(ctypes.c_void_p)]
|
|
t32api.T32_GetAddressObjAddr64.restype = ctypes.c_int
|
|
t32api.T32_ReleaseAllObjects.argtypes = []
|
|
t32api.T32_ReleaseAllObjects.restype = ctypes.c_int
|
|
t32api.T32_RequestRegisterObjR32Name.argtypes = [ctypes.POINTER(ctypes.c_void_p), ctypes.POINTER(ctypes.c_char)]
|
|
t32api.T32_RequestRegisterObjR32Name.restype = ctypes.c_int
|
|
t32api.T32_ReadRegisterObj.argtypes = [ctypes.c_void_p]
|
|
t32api.T32_ReadRegisterObj.restype = ctypes.c_int
|
|
t32api.T32_GetRegisterObjValue32.argtypes = [ctypes.c_void_p, ctypes.POINTER(ctypes.c_long)]
|
|
t32api.T32_GetRegisterObjValue32.restype = ctypes.c_int
|
|
t32api.T32_ReleaseRegisterObj.argtypes = [ctypes.POINTER(ctypes.c_void_p)]
|
|
t32api.T32_ReleaseRegisterObj.restype = ctypes.c_int
|
|
t32api.T32_Exit.argtypes = []
|
|
t32api.T32_Exit.restype = ctypes.c_int
|
|
|
|
check_error(t32api.T32_Config(b"NODE=", b"localhost"))
|
|
check_error(t32api.T32_Config(b"PORT=", b"20000"))
|
|
check_error(t32api.T32_Config(b"PACKLEN=", b"1024"))
|
|
check_error(t32api.T32_Init())
|
|
check_error(t32api.T32_Attach(1))
|
|
|
|
# configuration
|
|
cpufamily = "RISCV"
|
|
cpu = "RV32"
|
|
|
|
try:
|
|
c_buffer = (ctypes.c_char * 4096)()
|
|
c_result_type = ctypes.c_uint32()
|
|
|
|
check_error(t32api.T32_Ping())
|
|
|
|
# Check CPUFAMILY()
|
|
check_error(t32api.T32_ExecuteFunction(b"CPUFAMILY()", c_buffer, len(c_buffer), c_result_type))
|
|
if c_buffer.value != cpufamily.encode():
|
|
raise ValueError(f"CPUFAMILY(): Expected '{cpufamily}' got '{c_buffer.value.decode()}'")
|
|
|
|
check_error(t32api.T32_ExecuteCommand(f"SYStem.CPU {cpu}".encode(), c_buffer, len(c_buffer)))
|
|
check_error(t32api.T32_ExecuteCommand(b"SYStem.Mode Up", c_buffer, len(c_buffer)))
|
|
check_error(
|
|
t32api.T32_ExecuteCommand(b"Data.LOAD ~~/demo/riscv/compiler/gcc/rv32/sieve/sieve.elf", c_buffer, len(c_buffer))
|
|
)
|
|
|
|
# query symbol "main"
|
|
myAddress = ctypes.c_uint32(0)
|
|
mySymbolHandle = ctypes.c_void_p(0)
|
|
myAddressHandle = ctypes.c_void_p(0)
|
|
check_error(t32api.T32_RequestSymbolObjName(ctypes.byref(mySymbolHandle), b"main"))
|
|
check_error(t32api.T32_QuerySymbolObj(mySymbolHandle))
|
|
check_error(t32api.T32_GetSymbolObjAddress(mySymbolHandle, ctypes.byref(myAddressHandle)))
|
|
check_error(t32api.T32_GetAddressObjAddr32(myAddressHandle, ctypes.byref(myAddress)))
|
|
print(f"Symbol 'main': {hex(myAddress.value)}")
|
|
check_error(t32api.T32_ReleaseSymbolObj(ctypes.byref(mySymbolHandle)))
|
|
|
|
# set breakpoint to "main"
|
|
myBreakpointHandle = ctypes.c_void_p(0)
|
|
check_error(t32api.T32_RequestBreakpointObj(ctypes.byref(myBreakpointHandle)))
|
|
check_error(t32api.T32_SetBreakpointObjAddress(myBreakpointHandle, myAddressHandle))
|
|
check_error(t32api.T32_WriteBreakpointObj(myBreakpointHandle, 1))
|
|
check_error(t32api.T32_ReleaseBreakpointObj(ctypes.byref(myBreakpointHandle)))
|
|
|
|
# query register "PC"
|
|
regValue = ctypes.c_long(0)
|
|
myRegisterHandle32 = ctypes.c_void_p(0)
|
|
check_error(t32api.T32_RequestRegisterObjR32Name(ctypes.byref(myRegisterHandle32), b"PC"))
|
|
check_error(t32api.T32_ReadRegisterObj(myRegisterHandle32))
|
|
check_error(t32api.T32_GetRegisterObjValue32(myRegisterHandle32, ctypes.byref(regValue)))
|
|
print(f"Register 'PC': {hex(regValue.value)}")
|
|
check_error(t32api.T32_ReleaseRegisterObj(ctypes.byref(myRegisterHandle32)))
|
|
|
|
check_error(t32api.T32_ReleaseAllObjects())
|
|
|
|
finally:
|
|
|
|
check_error(t32api.T32_Exit())
|