This is the mail archive of the gdb-patches@sourceware.org mailing list for the GDB project.
| Index Nav: | [Date Index] [Subject Index] [Author Index] [Thread Index] | |
|---|---|---|
| Message Nav: | [Date Prev] [Date Next] | [Thread Prev] [Thread Next] |
| Other format: | [Raw text] | |
Hello,
This is support for MDI or Microprocessor Debug Interface as defined by
the spec published by MIPS Technologies. The implementation corresponds
to the version 2.20 of the spec.
The following modes of operation are supported:
1. Single-processor operation. For explicitly threaded hardware, such as
one specified by the MIPS MT spec (34K, etc.) all the contexts of
execution are seen as software threads. The usual "thread" commands
can be used.
2. Team operation. The primary processor is handled as with 1. above.
Additional processors are controlled transparently via the team set of
MDI calls.
3. Group (or SMP) operation. Sort of a combination of the two above. All
the controlled processors are treated the same and all contexts of
execution within are seen as software threads. Useful for debugging
SMP operating systems. Note it is currently impossible to add
transparently controlled devices when a group of processors is being
debugged.
I have tested it using the mipsisa32-sde-elf target with the
mips-fs2-sdelib/-EB/-march=mips32r2 and
mips-fs2-sdelib/-EL/-march=mips32r2 boards -- this is actual hardware with
a MIPS 24KEf core controlled through an FS2 probe. The results are as
follows:
# of expected passes 9845
# of unexpected failures 69
# of unexpected successes 2
# of expected failures 41
# of known failures 32
# of unresolved testcases 2
# of untested testcases 18
# of unsupported tests 69
and:
# of expected passes 9854
# of unexpected failures 60
# of unexpected successes 2
# of expected failures 41
# of known failures 32
# of unresolved testcases 2
# of untested testcases 18
# of unsupported tests 69
respectively. Due to the lack of support in my current Dejagnu setup
gdb.threads/ tests have not been run even though the target is capable of
running them (and actually succeed).
2004-08-23 Nigel Stephens <nigel@mips.com>
David Ung <davidu@mips.com>
Chris Dearman <chris@mips.com>
Maciej W. Rozycki <macro@mips.com>
Thiemo Seufer <ths@mips.com>
* remote-mdi.c: MDI target support.
* mdi.h: MDI generic API definition.
* mdilink.h: MDI dynamic loading support.
* mdimips.h: MDI MIPS-specific API definition.
* msim_cfg.txt: MIPSsim configuration file template.
* top.c (gdb_program_name): New global variable.
(gdb_init): Set gdb_program_name to argv0.
* defs.h (gdb_program_name): New global variable.
* cli/cli-decode.c (add_setshow_cmd_full): If var_type is
var_filename then force command completer function to be
filename_completer.
* configure.tgt (mips*-sde-elf*): Add ruleset for MIPS SDE.
* Makefile.in (gmon_h, gmon_out_h): New headers.
(install-mipssim): Add MIPSsim configuration file rule.
(uninstall-mipssim): Similarly.
(clean-mipssim): Similarly.
(mipssim.cfg): Similarly.
(ALLDEPFILES): Add remote-mdi.c.
(remote-mdi.o): Add dependencies. Add rule to compile
remote-mdi.c with GUI flags.
I have a pair of follow-on patches for the test suite to actually support
this target and to set timeouts reasonably (required for it is real
hardware which is not exactly lightning-fast) that I will post shortly.
OK to apply?
Maciej
mdi.diff
Index: binutils-quilt/src/gdb/mdi.h
===================================================================
--- /dev/null 1970-01-01 00:00:00.000000000 +0000
+++ binutils-quilt/src/gdb/mdi.h 2008-02-14 14:49:36.000000000 +0000
@@ -0,0 +1,573 @@
+/* MDI (Microprocessor Debug Interface) definitions.
+
+ Copyright (C) 2008 Free Software Foundation, Inc.
+
+ Contributed by MIPS Technologies, Inc.
+
+ This file is part of GDB.
+
+ This program is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2 of the License, or
+ (at your option) any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see <http://www.gnu.org/licenses/>. */
+
+#ifndef MDI_Specification_Definitions
+#define MDI_Specification_Definitions
+
+/* To build MDILib:
+ Define MDI_LIB before #include "mdi.h"
+ Include mdi.def in the link on Windows hosts.
+ When building an MDI application (debugger):
+ In one source file only, define MDILOAD_DEFINE before
+ #include "mdi.h" to define pointer variables for the API
+ functions. */
+
+typedef unsigned int MDIUint32;
+typedef int MDIInt32;
+#ifdef _MSC_VER
+typedef unsigned __int64 MDIUint64;
+typedef __int64 MDIInt64;
+#else
+typedef unsigned long long MDIUint64;
+typedef long long MDIInt64;
+#endif
+
+#ifndef __stdcall
+#define __stdcall
+#endif
+
+#ifndef __declspec
+#define __declspec(e)
+#endif
+
+typedef MDIUint32 MDIVersionT;
+typedef struct MDIVersionRange_struct
+{
+ MDIVersionT oldest;
+ MDIVersionT newest;
+} MDIVersionRangeT;
+
+#define MDIMajor 0x0002
+#define MDIMinor 0x0014
+#define MDIOldMajor 0x0001
+#define MDIOldMinor 0x0000
+#define MDICurrentRevision ((MDIMajor << 16 ) | MDIMinor)
+#define MDIOldestRevision ((MDIOldMajor << 16) | MDIOldMinor)
+
+typedef MDIUint32 MDIHandleT;
+#define MDINoHandle ((MDIHandleT)-1)
+
+typedef MDIUint32 MDITGIdT;
+
+typedef struct MDITGData_struct
+{
+ MDITGIdT TGId; /* MDI ID to reference this Target Group */
+ char TGName[81]; /* Descriptive string identifying this TG */
+} MDITGDataT;
+
+typedef MDIUint32 MDIDeviceIdT;
+
+typedef struct MDIDData_Struct
+{
+ MDIDeviceIdT Id; /* MDI ID to reference this device */
+ char DName[81]; /* Descriptive string identifying device */
+ char Family[15]; /* Device's Family (CPU, DSP) */
+ char FClass[15]; /* Device's Class (MIPS, X86, PPC) */
+ char FPart[15]; /* Generic Part Name */
+ char FISA[15]; /* Instruction Set Architecture */
+ char Vendor[15]; /* Vendor of Part */
+ char VFamily[15]; /* Vendor Family name */
+ char VPart[15]; /* Vendor Part Number */
+ char VPartRev[15]; /* Vendor Part Revision Number */
+ char VPartData[15]; /* Used for Part Specific Data */
+ char Endian; /* 0 Big Endian, 1 Little Endian */
+} MDIDDataT;
+
+/* Valid values for MDIDDataT.Family: */
+#define MDIFamilyCPU "CPU"
+#define MDIFamilyDSP "DSP"
+
+/* Valid values for MDIDDataT.Endian: */
+#define MDIEndianBig 0
+#define MDIEndianLittle 1
+
+/* MDI Resources */
+typedef MDIUint32 MDIResourceT;
+
+typedef MDIUint64 MDIOffsetT;
+
+typedef struct MDIRange_struct
+{
+ MDIOffsetT Start;
+ MDIOffsetT End;
+} MDIRangeT;
+
+typedef struct MDICRange_struct
+{
+ MDIOffsetT Offset;
+ MDIResourceT Resource;
+ MDIInt32 Count;
+} MDICRangeT;
+
+typedef struct MDIConfig_struct
+{
+ /* Provided By: Other Comments */
+ char User[80]; /* Host: ID of caller of MDI */
+
+ char Implementer[80]; /* MDI ID of who implemented MDI */
+ MDIUint32 MDICapability; /* MDI: Flags for optional capabilities */
+
+ /* Host: CB fn for MDI output */
+ MDIInt32 (__stdcall * MDICBOutput) (MDIHandleT Device,
+ MDIInt32 Type,
+ char *Buffer, MDIInt32 Count);
+
+ /* Host: CB fn for MDI input */
+ MDIInt32 (__stdcall * MDICBInput) (MDIHandleT Device,
+ MDIInt32 Type,
+ MDIInt32 Mode,
+ char **Buffer, MDIInt32 * Count);
+
+ /* Host: CB fn for expression eval */
+ MDIInt32 (__stdcall * MDICBEvaluate) (MDIHandleT Device,
+ char *Buffer,
+ MDIInt32 * ResultType,
+ MDIResourceT * Resource,
+ MDIOffsetT * Offset,
+ MDIInt32 * Size, void **Value);
+
+ /* Host: CB fn for sym/src lookup */
+ MDIInt32 (__stdcall * MDICBLookup) (MDIHandleT Device,
+ MDIInt32 Type,
+ MDIResourceT Resource,
+ MDIOffsetT Offset, char **Buffer);
+
+ /* Host: CB fn for Event processing */
+ MDIInt32 (__stdcall * MDICBPeriodic) (MDIHandleT Device);
+
+ /* Host: CB fn for Synchronizing */
+ MDIInt32 (__stdcall * MDICBSync) (MDIHandleT Device,
+ MDIInt32 Type, MDIResourceT Resource);
+} MDIConfigT;
+
+/* MDIConfigT.MDICapability flag values, can be OR'ed together. */
+#define MDICAP_NoParser 0x00000001 /* No command parser */
+#define MDICAP_NoDebugOutput 0x00000002 /* No Target I/O */
+#define MDICAP_TraceOutput 0x00000004 /* Supports Trace Output */
+#define MDICAP_TraceCtrl 0x00000008 /* Supports Trace Control */
+#define MDICAP_TargetGroups 0x00000010 /* Supports Target Groups */
+#define MDICAP_PDtrace 0x00000020 /* Supports PDtrace functions */
+#define MDICAP_TraceFetchI 0x00000040 /* Supports Instr Fetch during Trace */
+#define MDICAP_TC 0x00000080 /* Supports Thread Contexts */
+#define MDICAP_Teams 0x00000100 /* Supports Teams */
+
+typedef struct MDIRunState_struct
+{
+ MDIUint32 Status;
+ union u_info
+ {
+ void *ptr;
+ MDIUint32 value;
+ } Info;
+} MDIRunStateT;
+
+/* Status values: */ /* Info interpretation: */
+#define MDIStatusNotRunning 1 /* none */
+#define MDIStatusRunning 2 /* none */
+#define MDIStatusHalted 3 /* none */
+#define MDIStatusStepsDone 4 /* none */
+#define MDIStatusExited 5 /* Info.value = exit value */
+#define MDIStatusBPHit 6 /* Info.value = BpID */
+#define MDIStatusUsrBPHit 7 /* none */
+#define MDIStatusException 8 /* Info.value = which exception */
+#define MDIStatusTraceFull 9 /* none */
+#define MDIStatusDisabled 10 /* none */
+#define MDIStatusVPENoTCs 10 /* none */ /* old name */
+#define MDIStatusVPEDisabled 11 /* none */
+#define MDIStatusMask 0x00ff /* Status values are in lowest byte */
+
+/* These can be OR'ed in with MDIStatusRunning and MDIStatusNotRunning. */
+#define MDIStatusReset 0x0100 /* currently held reset */
+#define MDIStatusWasReset 0x0200 /* reset asserted & released */
+#define MDIStatusResetMask 0x0300 /* reset state mask */
+
+/* This can also be OR'ed in with MDIStatusHalted. */
+#define MDIStatusDescription 0x0400 /* Info.ptr = Descriptive string */
+
+typedef struct MDICacheInfo_struct
+{
+ MDIInt32 Type;
+ MDIUint32 LineSize; /* Bytes of data in a cache line */
+ MDIUint32 LinesPerSet; /* Number of lines in a set */
+ MDIUint32 Sets; /* Number of sets */
+} MDICacheInfoT;
+
+/* Values for MDICacheInfoT.Type (Cache types): */
+#define MDICacheTypeNone 0
+#define MDICacheTypeUnified 1
+#define MDICacheTypeInstruction 2
+#define MDICacheTypeData 3
+
+typedef MDIUint32 MDIBpT;
+
+#define MDIBPT_SWInstruction 1
+#define MDIBPT_SWOneShot 2
+#define MDIBPT_HWInstruction 3
+#define MDIBPT_HWData 4
+#define MDIBPT_HWBus 5
+#define MDIBPT_TypeMax MDIBPT_HWBus
+#define MDIBPT_TypeMask 0x0000ffff
+
+#define MDIBPT_HWType_Exec 0x00000001
+#define MDIBPT_HWType_Data 0x00000002
+#define MDIBPT_HWType_Bus 0x00000004
+#define MDIBPT_HWType_AlignMask 0x000000f0
+#define MDIBPT_HWType_AlignShift 4
+#define MDIBPT_HWType_MaxSMask 0x00003f00
+#define MDIBPT_HWType_MaxSShift 9
+#define MDIBPT_HWType_VirtAddr 0x00004000
+#define MDIBPT_HWType_ASID 0x00008000
+
+/* Hardware breakpoint types may have one or more of the following
+ flag bits OR'ed in to specify additional qualifications. */
+#define MDIBPT_HWFlg_AddrMask 0x00010000
+#define MDIBPT_HWFlg_AddrRange 0x00020000
+#define MDIBPT_HWFlg_DataValue 0x00040000
+#define MDIBPT_HWFlg_DataMask 0x00080000
+#define MDIBPT_HWFlg_DataRead 0x00100000
+#define MDIBPT_HWFlg_DataWrite 0x00200000
+#define MDIBPT_HWFlg_Trigger 0x00400000
+#define MDIBPT_HWFlg_TriggerOnly 0x00800000
+#define MDIBPT_HWFlg_TCMatch 0x01000000
+#define MDIBPT_TypeQualMask 0xffff0000
+
+typedef MDIUint32 MDIBpIdT;
+
+#define MDIAllBpID (~(MDIBpIdT)0)
+
+typedef struct MDIBpData_struct
+{
+ MDIBpIdT Id;
+ MDIBpT Type;
+ MDIUint32 Enabled; /* 0 if currently disabled, else 1 */
+ MDIResourceT Resource;
+ MDIRangeT Range; /* Range.End may be an end addr or mask */
+ MDIUint64 Data; /* valid only for data write breaks */
+ MDIUint64 DataMask; /* valid only for data write breaks */
+ MDIUint32 PassCount; /* Pass count reloaded when hit */
+ MDIUint32 PassesToGo; /* Passes to go until next hit */
+} MDIBpDataT;
+
+typedef struct MDIBpInfo_struct
+{
+ MDIInt32 Num; /* the number of breakpoints of this type */
+ MDIUint32 Type; /* the exact type of hardware breakpoint */
+} MDIBpInfoT;
+
+/* MDI Trace data type */
+typedef struct MDITrcFrame_Struct
+{
+ MDIUint32 Type;
+ MDIResourceT Resource;
+ MDIOffsetT Offset;
+ MDIUint64 Value;
+} MDITrcFrameT;
+
+#define MDITTypePC 1 /* Instruction address only */
+#define MDITTypeInst 2 /* Instruction address and value */
+#define MDITTypeRead 3 /* Data Load address only */
+#define MDITTypeWrite 4 /* Data Store address only */
+#define MDITTypeAccess 5 /* Data Access (Load/Store) address only */
+#define MDITTypeRData_8 6 /* Data Load address and 8-bit value */
+#define MDITTypeWData_8 7 /* Data Store address and 8-bit value */
+#define MDITTypeRData_16 8 /* Data Load address and 16-bit value */
+#define MDITTypeWData_16 9 /* Data Store address and 16-bit value */
+#define MDITTypeRData_32 10 /* Data Load address and 32-bit value */
+#define MDITTypeWData_32 11 /* Data Store address and 32-bit value */
+#define MDITTypeRData_64 12 /* Data Load address and 64-bit value */
+#define MDITTypeWData_64 13 /* Data Store address and 64-bit value */
+
+/* Values for Flags parameter to MDITGOpen() and MDIOpen(): */
+#define MDISharedAccess 0
+#define MDIExclusiveAccess 1
+
+/* Values for Flags parameter to MDITGClose() and MDIClose(): */
+#define MDICurrentState 0
+#define MDIResetState 1
+
+/* Values for SyncType parameter to MDICBSync(): */
+#define MDISyncBP 0
+#define MDISyncState 1
+#define MDISyncWrite 2
+
+/* Values for Direction parameter to MDIMove(): */
+#define MDIMoveForward 0
+#define MDIMoveBackward 1
+
+/* Values for Mode parameter to MDIFind(): */
+#define MDIMatchForward 0
+#define MDIMismatchForward 1
+#define MDIMatchBackward 2
+#define MDIMismatchBackward 3
+
+/* Values for Mode parameter to MDIStep(): */
+#define MDIStepInto 0
+#define MDIStepForward 1
+#define MDIStepOver 2
+#define MDINoStep ~0
+
+/* "Wait Forever" value for WaitTime parameter to MDIRunState(): */
+#define MDIWaitForever -1
+
+/* Values for Mode parameter to MDIReset(): */
+#define MDIFullReset 0
+#define MDIDeviceReset 1
+#define MDICPUReset 2
+#define MDIPeripheralReset 3
+
+/* Values for Flags parameter to MDICacheFlush(): */
+#define MDICacheWriteBack 0x01
+#define MDICacheInvalidate 0x02
+
+/* Values for Status parameter from MDITraceStatus(): */
+#define MDITraceStatusNone 1
+#define MDITraceStatusTracing 2
+#define MDITraceStatusWaiting 3
+#define MDITraceStatusFilling 4
+#define MDITraceStatusStopped 5
+
+/* Values for Type parameter to MDICBOutput() and MDICBInput(): */
+#define MDIIOTypeMDIIn 1
+#define MDIIOTypeMDIOut 2
+#define MDIIOTypeMDIErr 3
+#define MDIIOTypeTgtIn 4
+#define MDIIOTypeTgtOut 5
+#define MDIIOTypeTgtErr 6
+
+/* Values for Mode parameter to MDICBInput(): */
+#define MDIIOModeNormal 1
+#define MDIIORawBlock 2
+#define MDIIORawNoBlock 3
+
+/* Values for Type parameter to MDICBEvaluate(): */
+#define MDIEvalTypeResource 1
+#define MDIEvalTypeChar 2
+#define MDIEvalTypeInt 3
+#define MDIEvalTypeUInt 4
+#define MDIEvalTypeFloat 5
+#define MDIEvalTypeNone 6
+
+/* Values for Type parameter to MDICBLookup(): */
+#define MDILookupNearest 1
+#define MDILookupExact 2
+#define MDILookupSource 3
+
+/* MDI function return values: */
+#define MDISuccess 0 /* Success. */
+#define MDINotFound 1 /* MDIFind() did not find a match. */
+#define MDIErrFailure -1 /* Unable to perform operation. */
+#define MDIErrDevice -2 /* Invalid Device handle. */
+#define MDIErrSrcResource -3 /* Invalid Resource type. */
+#define MDIErrDstResource -4 /* 2nd Resource has invalid type. */
+#define MDIErrInvalidSrcOffset -5 /* Offset is invalid for the specified
+ resource. */
+#define MDIErrInvalidDstOffset -6 /* 2nd Offset is invalid for the 2nd
+ resource. */
+#define MDIErrSrcOffsetAlignment -7 /* Offset is not correctly aligned. */
+#define MDIErrDstOffsetAlignment -8 /* 2nd Offset is not correctly aligned
+ for the specified ObjectSize. */
+#define MDIErrSrcCount -9 /* Count causes reference outside of the
+ resources space. */
+#define MDIErrDstCount -10 /* Count causes reference outside of 2nd
+ resources space. */
+#define MDIErrBPType -13 /* Invalid breakpoint type. */
+#define MDIErrRange -14 /* Specified range is outside of the scope for
+ the resource. */
+#define MDIErrNoResource -15 /* Hardware resources are unavailable. */
+#define MDIErrBPId -16 /* Invalid Breakpoint ID. */
+#define MDIErrMore -17 /* More data available than was requested. */
+#define MDIErrParam -18 /* A parameter is in error (See specific
+ instructions). */
+#define MDIErrTGHandle -19 /* Invalid Target Group Handle. */
+#define MDIErrMDIHandle -20 /* Invalid MDI Environment Handle. */
+#define MDIErrVersion -21 /* Version not supported. */
+#define MDIErrLoadLib -22 /* Error loading library. */
+#define MDIErrModule -23 /* Unable to link required MDI functions. */
+#define MDIErrConfig -24 /* Required callback functions not present. */
+#define MDIErrDeviceId -25 /* Invalid device ID. */
+#define MDIErrAbort -26 /* Command has been aborted. */
+#define MDIErrUnsupported -27 /* Unsupported feature. */
+#define MDIErrLookupNone -28 /* Address did not match a symbol or source
+ line. */
+#define MDIErrLookupError -29 /* Invalid address for look up. */
+#define MDIErrTracing -30 /* Can't clear trace buffer while capturing
+ is in progress. */
+#define MDIErrInvalidFunction -31 /* Function pointer is invalid. */
+#define MDIErrAlreadyConnected -32 /* MDI Connection has already been
+ made for this thread. */
+#define MDIErrTGId -33 /* Invalid Target Group ID. */
+#define MDIErrDeviceHandle -34
+#define MDIErrDevicesOpen -35
+#define MDIErrInvalidData -36
+#define MDIErrDuplicateBP -37
+#define MDIErrInvalidFrames -38 /* Range of requested trace frames is
+ invalid. */
+#define MDIErrWrongThread -39
+#define MDIErrTargetRunning -40
+#define MDIErrRecursive -41 /* Recursive call from MDICDPeriodic. */
+#define MDIErrObjectSize -42 /* Invalid Object Size for Resource. */
+
+#define MDIErrTCId -43 /* The specified TC id value is not a valid TC
+ number for the VPE being debugged. */
+#define MDIErrTooManyTeams -44 /* Too many teams for MDILib. */
+#define MDIErrTeamId -45 /* Invalid team id. */
+#define MDIErrDisabled -46 /* Device is disabled. */
+#define MDIErrAlreadyMember -47 /* Device is already a team member. */
+#define MDIErrNotMember -48 /* Device is not a team member. */
+
+typedef MDIInt32 MDITCIdT;
+
+typedef struct MDITCData_struct
+{
+ MDITCIdT TCId;
+ MDIUint32 Status;
+} MDITCDataT;
+
+#define MDITCStatusHalted 0
+#define MDITCStatusFree 1
+#define MDITCStatusRunning 2
+#define MDITCStatusBlockedOnWait 3
+#define MDITCStatusBlockedOnYield 4
+#define MDITCStatusBlockedOnGS 5
+
+typedef MDIInt32 MDITeamIdT;
+
+typedef struct
+{
+ MDIHandleT MDIHandle;
+ MDITGIdT TGId;
+ MDIDeviceIdT DevId;
+} MDITMDataT;
+
+/* Function Prototypes. */
+
+#if defined (MDI_LIB)
+
+/* MDILib, do extern function declarations. */
+#define yf(str) extern int __declspec(dllexport) __stdcall str
+
+#elif defined (MDILOAD_DEFINE)
+
+/* Debugger, do function pointer definitions. */
+#define yf(str) int (__stdcall *str)
+
+#else
+
+/* Debugger, do extern function pointer declarations. */
+#define yf(str) extern int (__stdcall *str)
+
+#endif
+
+yf (MDIVersion) (MDIVersionRangeT *);
+yf (MDIConnect) (MDIVersionT, MDIHandleT *, MDIConfigT *);
+yf (MDIDisconnect) (MDIHandleT, MDIUint32);
+yf (MDITGQuery) (MDIHandleT, MDIInt32 * HowMany, MDITGDataT *);
+yf (MDITGOpen) (MDIHandleT, MDITGIdT, MDIUint32, MDIHandleT *);
+yf (MDITGClose) (MDIHandleT, MDIUint32);
+yf (MDITGExecute) (MDIHandleT);
+yf (MDITGStop) (MDIHandleT);
+yf (MDIDQuery) (MDIHandleT, MDIInt32 * HowMany, MDIDDataT *);
+yf (MDIOpen) (MDIHandleT, MDIDeviceIdT, MDIUint32, MDIHandleT *);
+yf (MDIClose) (MDIHandleT, MDIUint32);
+yf (MDIRead) (MDIHandleT, MDIResourceT SrcR, MDIOffsetT SrcO,
+ void *Buffer, MDIUint32 ObjectSize, MDIUint32 Count);
+yf (MDIWrite) (MDIHandleT, MDIResourceT DstR, MDIOffsetT DstO,
+ void *Buffer, MDIUint32 ObjectSize, MDIUint32 Count);
+yf (MDIReadList) (MDIHandleT, MDIUint32 ObjectSize, MDICRangeT * SrcList,
+ MDIUint32 ListCount, void *Buffer);
+yf (MDIWriteList) (MDIHandleT, MDIUint32 ObjectSize, MDICRangeT * DstList,
+ MDIUint32 ListCount, void *Buffer);
+yf (MDIMove) (MDIHandleT, MDIResourceT SrcR, MDIOffsetT SrcO,
+ MDIResourceT DstR, MDIOffsetT DstO, MDIUint32 ObjectSize,
+ MDIUint32 Count, MDIUint32 Flag);
+yf (MDIFill) (MDIHandleT, MDIResourceT DstR, MDIRangeT DstRng,
+ void *Buffer, MDIUint32 ObjectSize, MDIUint32 Count);
+yf (MDIFind) (MDIHandleT, MDIResourceT SrcR, MDIRangeT SrcRng,
+ void *Buffer, void *MaskBuffer, MDIUint32 ObjectSize,
+ MDIUint32 Count, MDIOffsetT * FoundOffset, MDIUint32 Mode);
+yf (MDIExecute) (MDIHandleT);
+yf (MDIStep) (MDIHandleT, MDIUint32 Steps, MDIUint32 Mode);
+yf (MDIStop) (MDIHandleT);
+yf (MDIReset) (MDIHandleT, MDIUint32 Flag);
+yf (MDICacheQuery) (MDIHandleT, MDICacheInfoT * CacheInfo);
+yf (MDICacheFlush) (MDIHandleT, MDIUint32 Type, MDIUint32 Flag);
+yf (MDIRunState) (MDIHandleT, MDIInt32 WaitTime, MDIRunStateT * runstate);
+yf (MDISetBp) (MDIHandleT, MDIBpDataT *);
+yf (MDISetSWBp) (MDIHandleT, MDIResourceT, MDIOffsetT, MDIBpIdT *);
+yf (MDIClearBp) (MDIHandleT, MDIBpIdT);
+yf (MDIEnableBp) (MDIHandleT, MDIBpIdT);
+yf (MDIDisableBp) (MDIHandleT, MDIBpIdT);
+yf (MDIBpQuery) (MDIHandleT, MDIInt32 * HowMany, MDIBpDataT *);
+yf (MDIHwBpQuery) (MDIHandleT, MDIInt32 * HowMany, MDIBpInfoT *);
+yf (MDIDoCommand) (MDIHandleT, char *Buffer);
+yf (MDIAbort) (MDIHandleT);
+yf (MDITraceEnable) (MDIHandleT);
+yf (MDITraceDisable) (MDIHandleT);
+yf (MDITraceClear) (MDIHandleT);
+yf (MDITraceStatus) (MDIHandleT, MDIUint32 *);
+yf (MDITraceCount) (MDIHandleT, MDIUint32 *);
+yf (MDITraceRead) (MDIHandleT, MDIUint32, MDIUint32, MDIUint32,
+ MDITrcFrameT *);
+yf (MDISetTC) (MDIHandleT, MDITCIdT);
+yf (MDIGetTC) (MDIHandleT, MDITCIdT *);
+yf (MDITCQuery) (MDIHandleT, MDIInt32 *, MDITCDataT *);
+yf (MDISetRunMode) (MDIHandleT, MDITCIdT, MDIUint32, MDIUint32);
+yf (MDISetTCRunMode) (MDIHandleT, MDITCIdT, MDIUint32, MDIUint32);
+yf (MDIQueryTC) (MDIHandleT, MDIInt32 *, MDITCDataT *);
+yf (MDITCSet) (MDIHandleT, MDITCIdT);
+yf (MDITCGet) (MDIHandleT, MDITCIdT *);
+yf (MDITCSetRunMode) (MDIHandleT, MDIInt32, MDIUint32, MDIUint32);
+yf (MDITeamCreate) (MDIHandleT, MDITeamIdT *);
+yf (MDIQueryTeams) (MDIHandleT, MDIInt32 *, MDITeamIdT *);
+yf (MDITeamClear) (MDIHandleT, MDITeamIdT);
+yf (MDITeamDestroy) (MDIHandleT, MDITeamIdT);
+yf (MDITMAttach) (MDIHandleT, MDITeamIdT, MDITMDataT *);
+yf (MDITMDetach) (MDIHandleT, MDITeamIdT, MDITMDataT *);
+yf (MDIQueryTM) (MDIHandleT, MDITeamIdT, MDIInt32 *, MDITMDataT *);
+yf (MDICreateTeam) (MDIHandleT, MDITeamIdT *);
+yf (MDIClearTeam) (MDIHandleT, MDITeamIdT);
+yf (MDIDestroyTeam) (MDIHandleT, MDITeamIdT);
+yf (MDIAttachTM) (MDIHandleT, MDITeamIdT, MDITMDataT *);
+yf (MDIDetachTM) (MDIHandleT, MDITeamIdT, MDITMDataT *);
+yf (MDITMQuery) (MDIHandleT, MDITeamIdT, MDIInt32 *, MDITMDataT *);
+yf (MDITeamExecute) (MDIHandleT, MDITeamIdT);
+
+/* MIPSsim special interfaces */
+yf (MIPSsim_SetConfigFile) (MDIHandleT, char *);
+yf (MIPSsim_CreateProfile) (MDIHandleT, MDIInt32 *, MDIUint64, MDIUint64);
+yf (MIPSsim_DestroyProfile) (MDIHandleT, MDIInt32);
+yf (MIPSsim_StartProfile) (MDIHandleT, MDIInt32);
+yf (MIPSsim_StopProfile) (MDIHandleT, MDIInt32);
+yf (MIPSsim_ClearProfile) (MDIHandleT, MDIInt32);
+yf (MIPSsim_FetchProfile) (MDIHandleT, MDIInt32, MDIUint32 **, MDIUint64 *);
+yf (MIPSsim_FreeProfileData) (MDIHandleT, MDIUint32 **);
+yf (MIPSsim_GetTraceLevel) (MDIHandleT, int *);
+yf (MIPSsim_SetTraceLevel) (MDIHandleT, int);
+yf (MIPSsim_GetStats) (MDIHandleT, int, MDIUint64 *);
+yf (MIPSsim_ClearStats) (MDIHandleT, int);
+yf (MIPSsim_GetPerfCounter) (MDIHandleT, int, int, int, MDIUint64 *);
+yf (MIPSsim_ZeroPerfCounter) (MDIHandleT, int, int, int);
+yf (MIPSsim_ZeroPerfCounters) (MDIHandleT);
+yf (MIPSsim_GetVersion) (MDIHandleT, MDIInt32 *, MDIInt32 *, MDIInt32 *);
+
+#undef yf
+
+#endif /* MDI_Specification_Definitions */
Index: binutils-quilt/src/gdb/defs.h
===================================================================
--- binutils-quilt.orig/src/gdb/defs.h 2008-02-14 14:22:13.000000000 +0000
+++ binutils-quilt/src/gdb/defs.h 2008-02-14 14:49:36.000000000 +0000
@@ -139,6 +139,9 @@
/* Search path for separate debug files. */
extern char *debug_file_directory;
+/* The name by which GDB was invoked. */
+extern char *gdb_program_name;
+
extern int quit_flag;
extern int immediate_quit;
extern int sevenbit_strings;
Index: binutils-quilt/src/gdb/remote-mdi.c
===================================================================
--- /dev/null 1970-01-01 00:00:00.000000000 +0000
+++ binutils-quilt/src/gdb/remote-mdi.c 2008-02-14 14:49:36.000000000 +0000
@@ -0,0 +1,8726 @@
+/* MDI (MIPS Debug Interface) interface for GDB.
+
+ Copyright (C) 2008 Free Software Foundation, Inc.
+
+ Contributed by MIPS Technologies, Inc.
+
+ This file is part of GDB.
+
+ This program is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2 of the License, or
+ (at your option) any later version.
+
+ This program is distributed in the hope that it will be useful,
+ but WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ GNU General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with this program. If not, see <http://www.gnu.org/licenses/>. */
+
+#include "defs.h"
+#include "arch-utils.h"
+#include "exceptions.h"
+#include "gdb_string.h"
+#include "gdb_wait.h"
+#include "inferior.h"
+#include "regcache.h"
+#include "version.h"
+#include <sys/types.h>
+#include "gdb_regex.h"
+#include "gmon.h"
+#include "gmon_out.h"
+#include <ctype.h>
+#include <fcntl.h>
+#include <signal.h>
+#include <setjmp.h>
+#include <errno.h>
+#include <sys/time.h>
+#include <sys/stat.h>
+
+#if defined(_WIN32) || defined(__CYGWIN32__)
+#include <windows.h>
+#else
+typedef void * HMODULE;
+#endif
+
+#ifdef __CYGWIN32__
+#include <sys/cygwin.h>
+#include <cygwin/version.h>
+#endif
+
+#ifndef MAX_PATH
+#define MAX_PATH 1024
+#endif
+
+#include "gdbthread.h"
+#include "terminal.h"
+#include "gdbcore.h"
+#include "gdbcmd.h"
+#include "block.h"
+
+#define MDILOAD_DEFINE
+#include "mdi.h"
+#include "mdimips.h"
+#include "mips-tdep.h"
+
+#ifdef GDBTK
+#include "tcl.h"
+extern Tcl_Interp *gdbtk_interp;
+#endif
+
+/* readline include files */
+#include <readline/readline.h>
+#include <readline/history.h>
+
+#define GET_PID(ptid) ptid_get_pid (ptid)
+
+/* These are pointers to hook functions that may be set in order to
+ modify resume/wait behavior for a particular architecture. */
+void (*target_resume_hook) (void);
+void (*target_wait_loop_hook) (void);
+
+static const char * mdierrcode (MDIInt32);
+
+/* The list of available "mdi", "set mdi" and "show mdi" commands. */
+static struct cmd_list_element *mdicmdlist = NULL;
+static struct cmd_list_element *setmdicmdlist = NULL;
+static struct cmd_list_element *showmdicmdlist = NULL;
+
+static HMODULE mdiModule;
+
+static char *mdi_logfile;
+static struct ui_file *mdi_logfp;
+static int mdi_logging;
+
+static int mdi_target;
+static int mdi_device;
+static int mdi_team;
+static int mdi_waittime = 10; /* XXXX 1/100th second seems very small. */
+static int mdi_stepinto = 0;
+static int mdi_threadstepall = 0;
+static int mdi_continueonclose = -1;
+static int mdi_rununcached = 1;
+static int mdi_threadviewinactive = 0;
+static unsigned int mdi_connecttimeout = 1;
+static char *mdi_library;
+static char *mdi_configfile;
+static char *mdi_devcfgfile;
+static char *mdi_ftext_syms;
+static char *mdi_etext_syms;
+static char *mdi_mcount_syms;
+static int mdi_connectreset = -1;
+static int mdi_releaseonclose = 0;
+static char *mdi_logdocommand;
+static int mdi_quiet;
+static int mdi_mem_written;
+static char **mdi_argv;
+
+static enum auto_boolean mdi_profiling = AUTO_BOOLEAN_AUTO;
+static char *mdi_gmonfile;
+static int mdi_profile_cycles;
+static int mdi_profile_mcount;
+
+static int mdi_wait_active;
+static int mdi_step_active;
+static int mdi_starting;
+
+static MDIRunStateT mdi_runstate;
+static MDIBpDataT mdi_curbpt;
+
+static char *mdi_target_prompt; /* the input prompt string */
+static char *mdi_implementer;
+
+static int mdi_found_relf;
+static int mdi_syscall_inserted;
+static CORE_ADDR mdi_syscall = 0;
+static CORE_ADDR mdi_syscall_rom = 0;
+static CORE_ADDR mdi_entrypoint = 0;
+static int mdi_loaded = 0;
+static int mdi_exited = 0;
+
+static enum target_signal mdi_lastsig;
+static int mdi_signalled = 0;
+
+/* Bitmap of missing cp registers:
+ 4 coprocessors x 8 banks x 32 registers. */
+static unsigned int mdi_cpdreg_miss[4][8];
+
+/* Bitmap of missing cp control registers:
+ 4 coprocessors x 32 registers. */
+static unsigned int mdi_cpcreg_miss[4];
+
+/* Bitmap of write protected cp registers:
+ 4 coprocessors x 8 banks x 32 registers. */
+static unsigned int mdi_cpdreg_wp[4][8];
+
+/* Bitmap of write protected cp control registers:
+ 4 coprocessors x 32 registers. */
+static unsigned int mdi_cpcreg_wp[4];
+
+static unsigned int mdi_hilo_miss;
+static unsigned int mdi_dsp_miss;
+
+/* Set if the new MDIMIPFPR resource available. */
+static int mdi_fpr_avail;
+
+/* Set if the new MDIHwBpQuery call available. */
+static int mdi_hwbpq_avail;
+
+/* Specify the address type for virtual memory accesses and
+ breakpoints. */
+
+enum mdi_asidtype
+{
+ ASIDNone, /* Use global address space. */
+ ASIDReg, /* Use current ASID in CP0 EntryHi. */
+ ASIDFixed, /* Use fixed ASID in mdi_asid. */
+ ASIDAuto /* Use global for unmapped segments,
+ or current ASID for mapped. */
+};
+
+static enum mdi_asidtype mdi_asidtype = ASIDAuto;
+
+/* ASID for for ASIDFixed type. */
+static int mdi_asid;
+
+/*extern int MDIInit (char *dllpath, HMODULE * handle);*/
+/*extern int MDIRelease (HMODULE handle);*/
+
+static ULONGEST mdi_readreg (int regno);
+static void mdi_writereg (int regno, ULONGEST val);
+
+static ULONGEST mdi_readpc (void);
+static void mdi_writepc (ULONGEST val);
+
+static void mdi_reset_breakpoints (void);
+static MDIBpDataT * mdi_find_breakpoint (MDIHandleT devhandle, MDIBpIdT id);
+static MDIBpDataT * mdi_find_usr_breakpoint (CORE_ADDR addr);
+static int mdi_insert_breakpoint1 (CORE_ADDR addr, MDIInt32);
+static int mdi_insert_breakpoint (struct bp_target_info *bp_tgt);
+static int mdi_remove_breakpoint1 (CORE_ADDR addr, MDIInt32);
+static int mdi_remove_breakpoint (struct bp_target_info *bp_tgt);
+
+static void mdi_team_status (MDIInt32 mdistat);
+static void mdi_tm_status (MDIInt32 mdistat, MDITGIdT target,
+ MDIDeviceIdT device);
+
+static int mdi_cycles_enable (PTR);
+static void mdi_cycles_update (void);
+
+static void dump_mem (void *, int, int);
+static MDIResourceT mdi_memresource (CORE_ADDR);
+static MDIOffsetT mdi_memoffset (CORE_ADDR);
+
+static void mdi_insert_syscallbreakpoint (void);
+static void mdi_remove_syscallbreakpoint (void);
+
+static void mdi_fdinit (void);
+static void mdi_fdcloseall (void);
+
+static void mdi_profiling_start (void);
+static void mdi_profiling_close (int);
+
+static void sleep_ms (long);
+
+static void mdi_switch_to_thread (void);
+static void mdi_find_new_threads (void);
+
+static ptid_t mdi_ptid;
+static ptid_t last_ptid;
+
+enum mdiTlb { NO_TLB, R3000_TLB, R4000_32TLB, R4000_64TLB };
+
+/* List of MDI team members. */
+struct mdi_tm_data_list
+{
+ MDITMDataT tmdata; /* MDI handle, TG ID, Dev ID. */
+ struct mdi_tm_data_list *next;
+};
+
+/* List of MDI group members. */
+struct mdi_gm_data
+{
+ MDITMDataT tmdata; /* MDI handle, TG ID, Dev ID. */
+ MDIHandleT TGHandle; /* Target handle. */
+ MDIHandleT DevHandle; /* Device handle. */
+ MDIDDataT DeviceData; /* Device data. */
+ MDICacheInfoT CacheInfo[4]; /* Cache information. */
+ int disabled; /* The device is disabled. */
+ int probed; /* The device has been probed. */
+ int ntlb; /* Number of TLB entries. */
+};
+
+/* MDI connection state. */
+struct mdi_state
+{
+ MDIHandleT MDIHandle; /* MDI handle */
+ MDITeamIdT gid; /* Team ID for the group */
+ struct mdi_gm_data gmdata[256];
+ /* Devices opened */
+ int gmcount; /* Number of devices opened */
+ int gmindex; /* Index of the selected device */
+
+ MDIConfigT Config; /* Configuration data */
+
+ int mipssim_p; /* Connected to MIPSsim */
+ char *cfgfile; /* MIPSsim temp config file */
+
+ enum mdiTlb tlb; /* TLB type */
+ int regsize; /* Device register size */
+};
+
+
+static struct mdi_state *mdi_desc = NULL;
+
+static void mdi_kill (void);
+
+/* Forward data declarations. */
+struct target_ops mdi_ops;
+
+#define ec(str) {str, #str}
+
+struct errorcodes_struct
+{
+ int errorcode;
+ const char *str;
+};
+
+static const struct errorcodes_struct errorcodes[] =
+{
+ ec (MDINotFound),
+ ec (MDIErrFailure),
+ ec (MDIErrDevice),
+ ec (MDIErrSrcResource),
+ ec (MDIErrDstResource),
+ ec (MDIErrInvalidSrcOffset),
+ ec (MDIErrInvalidDstOffset),
+ ec (MDIErrSrcOffsetAlignment),
+ ec (MDIErrDstOffsetAlignment),
+ ec (MDIErrSrcCount),
+ ec (MDIErrDstCount),
+ ec (MDIErrBPType),
+ ec (MDIErrRange),
+ ec (MDIErrNoResource),
+ ec (MDIErrBPId),
+ ec (MDIErrMore),
+ ec (MDIErrParam),
+ ec (MDIErrTGHandle),
+ ec (MDIErrMDIHandle),
+ ec (MDIErrVersion),
+ ec (MDIErrLoadLib),
+ ec (MDIErrModule),
+ ec (MDIErrConfig),
+ ec (MDIErrDeviceId),
+ ec (MDIErrAbort),
+ ec (MDIErrUnsupported),
+ ec (MDIErrLookupNone),
+ ec (MDIErrLookupError),
+ ec (MDIErrTracing),
+ ec (MDIErrInvalidFunction),
+ ec (MDIErrAlreadyConnected),
+ ec (MDIErrTGId),
+ ec (MDIErrDeviceHandle),
+ ec (MDIErrDevicesOpen),
+ ec (MDIErrInvalidData),
+ ec (MDIErrDuplicateBP),
+ ec (MDIErrInvalidFrames),
+ ec (MDIErrWrongThread),
+ ec (MDIErrTargetRunning),
+ ec (MDIErrRecursive),
+ ec (MDIErrObjectSize),
+ ec (MDIErrTCId),
+ ec (MDIErrTooManyTeams),
+ ec (MDIErrTeamId),
+ ec (MDIErrDisabled),
+ ec (MDIErrAlreadyMember),
+ ec (MDIErrNotMember),
+ {0, 0}
+};
+
+struct mdiresourcename_struct
+{
+ int mdiid;
+ const char *mdistr;
+};
+
+static const struct mdiresourcename_struct resrc_Names[] =
+{
+ ec (MDIMIPCPU),
+ ec (MDIMIPPC),
+ ec (MDIMIPHILO),
+ ec (MDIMIPTLB),
+ ec (MDIMIPPICACHET),
+ ec (MDIMIPPUCACHET),
+ ec (MDIMIPPDCACHET),
+ ec (MDIMIPSICACHET),
+ ec (MDIMIPSUCACHET),
+ ec (MDIMIPSDCACHET),
+ ec (MDIMIP192ACC),
+ ec (MDIMIPCP0),
+ ec (MDIMIPCP0C),
+ ec (MDIMIPCP1),
+ ec (MDIMIPCP1C),
+ ec (MDIMIPCP2),
+ ec (MDIMIPCP2C),
+ ec (MDIMIPCP3),
+ ec (MDIMIPCP3C),
+ ec (MDIMIPFP),
+ ec (MDIMIPDFP),
+ ec (MDIMIPPICACHE),
+ ec (MDIMIPPUCACHE),
+ ec (MDIMIPPDCACHE),
+ ec (MDIMIPSICACHE),
+ ec (MDIMIPSUCACHE),
+ ec (MDIMIPSDCACHE),
+ ec (MDIMIPPHYSICAL),
+ ec (MDIMIPGVIRTUAL),
+ ec (MDIMIPEJTAG),
+ ec (MDIMIPSRS),
+ ec (MDIMIPFPR),
+ ec (MDIMIPDSP),
+ {0, "Invalid Resource"}
+};
+
+
+static const struct mdiresourcename_struct status_Names[] =
+{
+ ec(MDIStatusNotRunning),
+ ec(MDIStatusRunning),
+ ec(MDIStatusHalted),
+ ec(MDIStatusStepsDone),
+ ec(MDIStatusExited),
+ ec(MDIStatusBPHit),
+ ec(MDIStatusUsrBPHit),
+ ec(MDIStatusException),
+ ec(MDIStatusTraceFull),
+ ec(MDIStatusDisabled),
+ ec(MDIStatusVPEDisabled),
+ {0, "Invalid status"}
+};
+
+static const struct mdiresourcename_struct bptype_Names[] =
+{
+ ec (MDIBPT_SWInstruction),
+ ec (MDIBPT_SWOneShot),
+ ec (MDIBPT_HWInstruction),
+ ec (MDIBPT_HWData),
+ ec (MDIBPT_HWBus),
+ {0, "Invalid bptype"}
+};
+
+static const struct mdiresourcename_struct cbtype_Names[] =
+{
+ ec(MDIIOTypeMDIIn),
+ ec(MDIIOTypeMDIOut),
+ ec(MDIIOTypeMDIErr),
+ ec(MDIIOTypeTgtIn),
+ ec(MDIIOTypeTgtOut),
+ ec(MDIIOTypeTgtErr),
+ {0, "Invalid type"}
+};
+
+struct isa_xlate_struct
+{
+ const char *isa;
+ int num;
+};
+
+static const struct isa_xlate_struct isa_xlate[] =
+{
+ {MDIMIP_FISA_M1, 1} ,
+ {MDIMIP_FISA_M2, 2} ,
+ {MDIMIP_FISA_M3, 3} ,
+ {MDIMIP_FISA_M4, 4} ,
+ {MDIMIP_FISA_M5, 5} ,
+ {MDIMIP_FISA_M32, 32} ,
+ {MDIMIP_FISA_M64, 64} ,
+ {0, -1}
+};
+
+
+static void
+show_mdi_stepinto (struct ui_file *file, int from_tty,
+ struct cmd_list_element *c, const char *value)
+{
+ fprintf_filtered (file, _("Step-into mode is %s.\n"), value);
+}
+
+static void
+show_mdi_threadstepall (struct ui_file *file, int from_tty,
+ struct cmd_list_element *c, const char *value)
+{
+ fprintf_filtered (file, _("\
+Simultaneous thread stepping mode is %s.\n"),
+ value);
+}
+
+static void
+show_mdi_connecttimeout (struct ui_file *file, int from_tty,
+ struct cmd_list_element *c, const char *value)
+{
+ fprintf_filtered (file, _("MDI connect timeout is %s s.\n"), value);
+}
+
+static void
+show_mdi_continueonclose (struct ui_file *file, int from_tty,
+ struct cmd_list_element *c, const char *value)
+{
+ fprintf_filtered (file, _("Continue on MDI close mode is %s.\n"), value);
+}
+
+static void
+show_mdi_rununcached (struct ui_file *file, int from_tty,
+ struct cmd_list_element *c, const char *value)
+{
+ fprintf_filtered (file, _("Program starts uncached is %s.\n"), value);
+}
+
+static void
+show_mdi_waittime (struct ui_file *file, int from_tty,
+ struct cmd_list_element *c, const char *value)
+{
+ fprintf_filtered (file, _("MDI poll period is %s ms.\n"), value);
+}
+
+static void
+show_mdi_releaseonclose (struct ui_file *file, int from_tty,
+ struct cmd_list_element *c, const char *value)
+{
+ fprintf_filtered (file, _("MDI release on close is %s.\n"), value);
+}
+
+static void
+show_mdi_logfile (struct ui_file *file, int from_tty,
+ struct cmd_list_element *c, const char *value)
+{
+ fprintf_filtered (file, _("MDI log file is \"%s\".\n"), value);
+}
+
+static void
+show_mdi_logdocommand (struct ui_file *file, int from_tty,
+ struct cmd_list_element *c, const char *value)
+{
+ fprintf_filtered (file, _("\
+The command for the MDI target for logging gdb commands is \"%s\".\n"),
+ value);
+}
+
+static void
+show_mdi_library (struct ui_file *file, int from_tty,
+ struct cmd_list_element *c, const char *value)
+{
+ fprintf_filtered (file, _("MDI interface library is \"%s\".\n"), value);
+}
+
+static void
+show_mdi_configfile (struct ui_file *file, int from_tty,
+ struct cmd_list_element *c, const char *value)
+{
+ fprintf_filtered (file, _("MIPSsim config file is \"%s\".\n"), value);
+}
+
+static void
+show_mdi_devcfgfile (struct ui_file *file, int from_tty,
+ struct cmd_list_element *c, const char *value)
+{
+ fprintf_filtered (file, _("MIPSsim device config file is \"%s\".\n"), value);
+}
+
+static void
+show_mdi_gmonfile (struct ui_file *file, int from_tty,
+ struct cmd_list_element *c, const char *value)
+{
+ fprintf_filtered (file, _("MIPSsim gmon profile file is \"%s\".\n"), value);
+}
+
+static void
+show_mdi_profiling (struct ui_file *file, int from_tty,
+ struct cmd_list_element *c, const char *value)
+{
+ fprintf_filtered (file, _("MIPSsim profiling is %s.\n"), value);
+}
+
+static void
+show_mdi_profile_mcount (struct ui_file *file, int from_tty,
+ struct cmd_list_element *c, const char *value)
+{
+ fprintf_filtered (file, _("Include _mcount in profile is %s.\n"), value);
+}
+
+static void
+show_mdi_profile_cycles (struct ui_file *file, int from_tty,
+ struct cmd_list_element *c, const char *value)
+{
+ fprintf_filtered (file, _("Cycle accurate profiling is %s.\n"), value);
+}
+
+static void
+show_mdi_team (struct ui_file *file, int from_tty,
+ struct cmd_list_element *c, const char *value)
+{
+ fprintf_filtered (file, _("MDI team number is %s.\n"), value);
+}
+
+static void
+show_mdi_target (struct ui_file *file, int from_tty,
+ struct cmd_list_element *c, const char *value)
+{
+ fprintf_filtered (file, _("MDI target group number is %s.\n"), value);
+}
+
+static void
+show_mdi_device (struct ui_file *file, int from_tty,
+ struct cmd_list_element *c, const char *value)
+{
+ fprintf_filtered (file, _("MDI device number is %s.\n"), value);
+}
+
+static void
+show_mdi_target_prompt (struct ui_file *file, int from_tty,
+ struct cmd_list_element *c, const char *value)
+{
+ fprintf_filtered (file, _("MDI target input prompt is \"%s\".\n"), value);
+}
+
+static void
+show_mdi_ftext_syms (struct ui_file *file, int from_tty,
+ struct cmd_list_element *c, const char *value)
+{
+ fprintf_filtered (file, _("\
+Start of code section symbols names are \"%s\".\n"),
+ value);
+}
+
+static void
+show_mdi_etext_syms (struct ui_file *file, int from_tty,
+ struct cmd_list_element *c, const char *value)
+{
+ fprintf_filtered (file, _("\
+End of code section symbols names are \"%s\".\n"),
+ value);
+}
+
+static void
+show_mdi_mcount_syms (struct ui_file *file, int from_tty,
+ struct cmd_list_element *c, const char *value)
+{
+ fprintf_filtered (file, _("\
+The mcount symbol name list is \"%s\".\n"),
+ value);
+}
+
+
+static const char *
+lookupName (const struct mdiresourcename_struct *ptr, int id)
+{
+ static char buf[64];
+ for ( ; ptr->mdiid && ptr->mdiid != id; ptr++)
+ continue;
+ if (ptr->mdiid != 0)
+ return (ptr->mdistr);
+ sprintf (buf, "%s (0x%x)", ptr->mdistr, id);
+ return buf;
+}
+
+static const char *
+resrcName (int resrc)
+{
+ if ((MDIMIPVIRTUAL <= resrc) && (resrc < (MDIMIPVIRTUAL + 0x100))) {
+ static char buf[64];
+ sprintf (buf, "MDIMIPVIRTUAL/ASID=%02x", resrc & 0xff);
+ return buf;
+ }
+ return lookupName (resrc_Names, resrc);
+}
+
+static const char *
+statusName (int status)
+{
+ return lookupName (status_Names, status & MDIStatusMask);
+}
+
+static char *
+bptypeName (int bptype)
+{
+ static char buf[64];
+ snprintf (buf, sizeof buf, "%s%s%s%s%s%s%s",
+ lookupName (bptype_Names, bptype & MDIBPT_TypeMask),
+ (bptype & MDIBPT_HWFlg_AddrMask) ? "|AddrMask" : "",
+ (bptype & MDIBPT_HWFlg_AddrRange) ? "|AddrRange" : "",
+ (bptype & MDIBPT_HWFlg_DataValue) ? "|DataValue" : "",
+ (bptype & MDIBPT_HWFlg_DataMask) ? "|DataMask" : "",
+ (bptype & MDIBPT_HWFlg_Trigger) ? "|Trigger" : "",
+ (bptype & MDIBPT_HWFlg_TriggerOnly) ? "|TriggerOnly" : "");
+
+ return buf;
+}
+
+static void
+mdiDisplayRunState (MDIRunStateT * runstate)
+{
+ MDIUint32 status = runstate->Status;
+ fprintf_unfiltered (mdi_logfp, "runstate=%s%s%s",
+ statusName (status),
+ (status & MDIStatusReset) ? ", in reset" : "",
+ (status & MDIStatusWasReset) ? ", was reset" : "");
+ switch (status & MDIStatusMask)
+ {
+ case MDIStatusExited:
+ fprintf_unfiltered (mdi_logfp, ", ec=0x%x",
+ runstate->Info.value);
+ break;
+ case MDIStatusBPHit:
+ fprintf_unfiltered (mdi_logfp, ", BpID=%u",
+ runstate->Info.value);
+ break;
+ case MDIStatusException:
+ fprintf_unfiltered (mdi_logfp, ", exc=%u",
+ runstate->Info.value);
+ break;
+ }
+ if (status & MDIStatusDescription)
+ fprintf_unfiltered (mdi_logfp, ", desc=\"%s\"",
+ (char *) runstate->Info.ptr);
+ fputc_unfiltered ('\n', mdi_logfp);
+}
+
+
+
+#include "mdilink.h"
+
+#if defined(_WIN32) || defined(__CYGWIN32__)
+#include <windows.h>
+#define DEFAULT_LIB_NAME "mdi.dll"
+#else
+#define DEFAULT_LIB_NAME "libmdi.so"
+#endif
+
+#if defined(_WIN32) && !defined(__CYGWIN32__)
+#define OpenLib(libname) \
+ LoadLibrary (libname)
+#define CloseLib(libhandle) \
+ FreeLibrary ((HMODULE) (libhandle))
+#define GetLibSymbolAddress(libhandle, symbolname) \
+ ((void*) GetProcAddress ((HMODULE) (libhandle), (symbolname)))
+#else
+#include <dlfcn.h>
+#define OpenLib(libname) \
+ dlopen (libname, RTLD_LAZY)
+#define CloseLib(libhandle) \
+ dlclose (libhandle)
+#define GetLibSymbolAddress(libhandle, symbolname) \
+ dlsym (libhandle, symbolname)
+#endif
+
+struct libsymbol
+{
+ const char *name;
+ void *funcp;
+ int required;
+};
+
+#if __STDC__
+#define sym(x, req) {F ## x, &x, req}
+#else
+#define sym(x, req) {F/**/x, &x, req}
+#endif
+
+/* List of symbols defined in MDI DLL. */
+static const struct libsymbol symbols[] = {
+ sym (MDIVersion, 1),
+ sym (MDIConnect, 1),
+ sym (MDIDisconnect, 1),
+ sym (MDITGQuery, 1),
+ sym (MDITGOpen, 1),
+ sym (MDITGClose, 1),
+ sym (MDITGExecute, 1),
+ sym (MDITGStop, 1),
+ sym (MDIDQuery, 1),
+ sym (MDIOpen, 1),
+ sym (MDIClose, 1),
+ sym (MDIRead, 1),
+ sym (MDIWrite, 1),
+ sym (MDIReadList, 1),
+ sym (MDIWriteList, 1),
+ sym (MDIMove, 1),
+ sym (MDIFill, 1),
+ sym (MDIFind, 1),
+ sym (MDIExecute, 1),
+ sym (MDIStep, 1),
+ sym (MDIStop, 1),
+ sym (MDIReset, 1),
+ sym (MDICacheQuery, 1),
+ sym (MDICacheFlush, 1),
+ sym (MDIRunState, 1),
+ sym (MDISetBp, 1),
+ sym (MDISetSWBp, 1),
+ sym (MDIClearBp, 1),
+ sym (MDIEnableBp, 1),
+ sym (MDIDisableBp, 1),
+ sym (MDIBpQuery, 1),
+ sym (MDIHwBpQuery, 0),
+ sym (MDIDoCommand, 1),
+ sym (MDIAbort, 1),
+ sym (MDITraceEnable, 1),
+ sym (MDITraceDisable, 1),
+ sym (MDITraceClear, 1),
+ sym (MDITraceStatus, 1),
+ sym (MDITraceCount, 1),
+ sym (MDITraceRead, 1),
+ /* Optional multi-threading extensions. */
+ sym (MDIGetTC, 0),
+ sym (MDISetTC, 0),
+ sym (MDITCQuery, 0),
+ sym (MDISetRunMode, 0),
+ /* Early MT MDI spec revision names. */
+ sym (MDIQueryTC, 0),
+ sym (MDITCGet, 0),
+ sym (MDITCSet, 0),
+ sym (MDITCSetRunMode, 0),
+ sym (MDISetTCRunMode, 0),
+ /* Optional team support extensions. */
+ sym (MDITeamCreate, 0),
+ sym (MDIQueryTeams, 0),
+ sym (MDITeamClear, 0),
+ sym (MDITeamDestroy, 0),
+ sym (MDITMAttach, 0),
+ sym (MDITMDetach, 0),
+ sym (MDIQueryTM, 0),
+ sym (MDITeamExecute, 0),
+ /* Early MT MDI spec revision names. */
+ sym (MDICreateTeam, 0),
+ sym (MDIClearTeam, 0),
+ sym (MDIDestroyTeam, 0),
+ sym (MDIAttachTM, 0),
+ sym (MDIDetachTM, 0),
+ sym (MDITMQuery, 0),
+ /* MIPSsim special interfaces. */
+ sym (MIPSsim_SetConfigFile, 0),
+ sym (MIPSsim_CreateProfile, 0),
+ sym (MIPSsim_DestroyProfile, 0),
+ sym (MIPSsim_StartProfile, 0),
+ sym (MIPSsim_StopProfile, 0),
+ sym (MIPSsim_ClearProfile, 0),
+ sym (MIPSsim_FetchProfile, 0),
+ sym (MIPSsim_FreeProfileData, 0),
+ sym (MIPSsim_GetTraceLevel, 0),
+ sym (MIPSsim_SetTraceLevel, 0),
+ sym (MIPSsim_GetStats, 0),
+ sym (MIPSsim_ClearStats, 0),
+ sym (MIPSsim_GetPerfCounter, 0),
+ sym (MIPSsim_ZeroPerfCounter, 0),
+ sym (MIPSsim_ZeroPerfCounters, 0),
+ sym (MIPSsim_GetVersion, 0),
+ {0, 0, 0}
+};
+
+
+#ifdef __CYGWIN32__
+/* Copy Cygwin environment variables to Windows. */
+static void
+cygwin_sync_winenv (void)
+{
+#if CYGWIN_VERSION_API_MAJOR > 0 || CYGWIN_VERSION_API_MINOR >= 154
+ /* Only available in Cygwin 1.15.20+. */
+ cygwin_internal (CW_SYNC_WINENV);
+#else
+ extern char **environ;
+ char **envp = environ;
+
+ if (!envp)
+ return;
+
+ while (*envp)
+ {
+ char *var = xmalloc (strlen (*envp) + 1);
+ char *eq;
+
+ strcpy (var, *envp);
+ eq = strchr (var, '=');
+ if (eq)
+ {
+ /* Environment variables that need special handling. */
+ static const char * const skipenv[] = {
+ "PATH", "HOME", "LD_LIBRARY_PATH", "TMPDIR", "TMP", "TEMP", NULL
+ };
+ const char **skip;
+
+ /* Split into name/value pair. */
+ *eq = '\0';
+
+ /* Check for special variables. */
+ for (skip = skipenv; *skip; skip++)
+ if (strcmp (var, *skip) == 0)
+ break;
+
+ /* Add non-special variables to Windows environment. */
+ if (!*skip)
+ SetEnvironmentVariable (var, eq + 1);
+ }
+ xfree (var);
+ ++envp;
+ }
+#endif /* CYGWIN_VERSION_API_MAJOR == 0 && CYGWIN_VERSION_API_MINOR < 154 */
+}
+#endif /* __CYGWIN__ */
+
+
+/* Debuggers and other MDILib using applications must call this
+ function prior to calling any of the MDI API functions. MDIInit()
+ loads the MDILib whose pathname is supplied as an argument, or the
+ registered "mdi.dll" if NULL is passed, and initializes the global
+ function pointers with the addresses of the API functions exported
+ from the library. */
+
+static MDIInt32
+MDIInit (char *libname, HMODULE *handle)
+{
+ char *mdilib; /* the name of the library to open */
+ HMODULE lib; /* the handle to the opened library */
+ char buffer[MAX_PATH];
+ int retvalue;
+ const struct libsymbol *sym;
+
+ mdilib = libname;
+
+#if defined(_WIN32) || defined(__CYGWIN32__)
+ if (!mdilib)
+ {
+ static int MDIDllName (char *, size_t);
+ retvalue = MDIDllName (buffer, MAX_PATH);
+ if (!retvalue)
+ mdilib = buffer;
+ }
+#endif
+
+ if (!mdilib)
+ mdilib = DEFAULT_LIB_NAME;
+
+#ifdef __CYGWIN32__
+ /* Sync Cygwin & Windows environments now, in case we're loading a
+ native Windows DLL which might needs a env variable set up within
+ the Cygwin environment. Cygwin does this automatically only when
+ spawning a new process, not when loading a DLL. */
+ cygwin_sync_winenv ();
+#endif
+
+ lib = OpenLib (mdilib);
+ if (!lib)
+ {
+#if ! (defined(_WIN32) && !defined(__CYGWIN32__))
+ char *error = dlerror ();
+ if (error)
+ fprintf_unfiltered (mdi_logfp, "DLL open error: %s\n", error);
+#endif
+ return MDIErrLoadLib;
+ }
+
+ /* The library has been opened, take all the function pointers
+ defined in mdi.h and point them into the library. */
+ for (sym = symbols; sym->name; sym++)
+ {
+ *(void **) sym->funcp = GetLibSymbolAddress (lib, sym->name);
+ if (!*(void **) sym->funcp && sym->required)
+ {
+ CloseLib (lib);
+ return MDIErrLoadLib;
+ }
+ }
+
+ *handle = (HMODULE) lib;
+ return (MDISuccess);
+}
+
+#if defined(_WIN32) || defined(__CYGWIN32__)
+
+/* MDIDllName returns the fully qualified path of the active mdi.dll.
+ If there is no registered mdi.dll or mdi.dll is incorrectly
+ registered MDIDllName will return the fully qualified path of
+ mdi.dll as it would be loaded by the OS. */
+
+static int
+MDIDllName (char *dllname, size_t size)
+{
+ int status;
+ HKEY keyHandle;
+ DWORD type;
+ DWORD bufsize;
+ unsigned char buffer[MAX_PATH];
+
+ status =
+ RegOpenKeyEx (HKEY_LOCAL_MACHINE, "SOFTWARE\\MDI", 0, KEY_READ,
+ &keyHandle);
+ if (status == ERROR_SUCCESS)
+ {
+ bufsize = MAX_PATH;
+ status =
+ RegQueryValueEx (keyHandle, "Active DLL", 0, &type, buffer, &bufsize);
+ RegCloseKey (keyHandle);
+ if (status == ERROR_SUCCESS && bufsize <= MAX_PATH)
+ {
+ status =
+ RegOpenKeyEx (HKEY_LOCAL_MACHINE, "SOFTWARE\\MDI\\MDIDLL", 0,
+ KEY_READ, &keyHandle);
+ if (status == ERROR_SUCCESS)
+ {
+ bufsize = MAX_PATH;
+ status =
+ RegQueryValueEx (keyHandle, (char *) buffer, 0, &type, buffer,
+ &bufsize);
+ RegCloseKey (keyHandle);
+ if (status == ERROR_SUCCESS && bufsize <= MAX_PATH)
+ {
+ switch (type)
+ {
+ case REG_EXPAND_SZ:
+ bufsize =
+ ExpandEnvironmentStrings ((const char *) buffer,
+ dllname, size);
+ if (bufsize > size)
+ {
+ return -1;
+ }
+ return 0;
+
+ case REG_SZ:
+ case REG_MULTI_SZ:
+ strncpy (dllname, (const char *) buffer, size);
+ if (bufsize > size)
+ {
+ return -1;
+ }
+ return 0;
+ }
+ }
+ }
+ }
+ }
+
+ bufsize = SearchPath (0, DEFAULT_LIB_NAME, 0, size, dllname, 0);
+ if (bufsize && bufsize <= MAX_PATH)
+ return 0;
+
+ return -1;
+}
+#endif /* _WIN32 || __CYGWIN32__ */
+
+static int
+MDIRelease (HMODULE lib)
+{
+ const struct libsymbol *sym;
+
+ /* Clear all the function pointers, just in case... */
+ for (sym = symbols; sym->name; sym++)
+ *(void **) sym->funcp = NULL;
+
+ CloseLib (lib);
+ return MDISuccess;
+}
+
+
+
+static MDIInt32
+mdiVersion (MDIVersionRangeT * version)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiVersion (-)\n");
+ stat = MDIVersion (version);
+ if (remote_debug > 1)
+ {
+ if (stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ else
+ fprintf_unfiltered (mdi_logfp, "returned: version = 0x%x-0x%x\n",
+ version->oldest, version->newest);
+ }
+ return stat;
+}
+
+static MDIInt32
+mdiConnect (MDIVersionT version, MDIHandleT * handle, MDIConfigT * config)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiConnect (0x%08x, -, -)\n", version);
+ stat = MDIConnect (version, handle, config);
+ if (remote_debug > 1)
+ {
+ if (stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ else
+ fprintf_unfiltered (mdi_logfp, "returned: handle = 0x%x\n", *handle);
+ }
+ return stat;
+}
+
+static MDIInt32
+mdiDisconnect (MDIHandleT MDIHandle, MDIUint32 flags)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiDisconnect (-, flags 0x%x)\n", flags);
+ stat = MDIDisconnect (MDIHandle, flags);
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+static MDIInt32
+mdiTGQuery (MDIHandleT MDIHandle, MDIInt32 * HowMany, MDITGDataT * TGData)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiTGQuery (-, &%d, %p)\n", *HowMany,
+ TGData);
+ stat = MDITGQuery (MDIHandle, HowMany, TGData);
+ if (remote_debug > 1)
+ {
+ if (stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ else
+ fprintf_unfiltered (mdi_logfp, "returned: *HowMany = %d\n", *HowMany);
+ }
+ return stat;
+}
+
+static MDIInt32
+mdiTGOpen (MDIHandleT MDIHandle, MDITGIdT TGId, MDIUint32 flags,
+ MDIHandleT * TGHandle)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp,
+ "mdiTGOpen (-, TGId 0x%x, flags 0x%x, -)\n",
+ TGId, flags);
+ stat = MDITGOpen (MDIHandle, TGId, flags, TGHandle);
+ if (remote_debug > 1)
+ {
+ if (stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ else
+ fprintf_unfiltered (mdi_logfp, "returned: *TGHandle = 0x%x\n",
+ *TGHandle);
+ }
+ return stat;
+}
+
+static MDIInt32
+mdiTGClose (MDIHandleT TGHandle, MDIUint32 flags)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiTGClose (0x%x, flags 0x%x)\n",
+ TGHandle, flags);
+ stat = MDITGClose (TGHandle, flags);
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+#if unused
+static MDIInt32
+mdiTGExecute (MDIHandleT TGHandle)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiTGExecute (0x%x)\n", TGHandle);
+ stat = MDITGExecute (TGHandle);
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+static MDIInt32
+mdiTGStop (MDIHandleT TGHandle)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiTGStop (0x%x)\n", TGHandle);
+ stat = MDITGStop (TGHandle);
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+#endif
+
+static MDIInt32
+mdiDQuery (MDIHandleT TGHandle, MDIInt32 * HowMany, MDIDDataT * DData)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiDQuery (0x%x, &%d, %p)\n",
+ TGHandle, *HowMany, DData);
+ stat = MDIDQuery (TGHandle, HowMany, DData);
+ if (remote_debug > 1)
+ {
+ if (stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ else
+ fprintf_unfiltered (mdi_logfp, "returned: *HowMany = %d\n", *HowMany);
+ }
+ return stat;
+}
+
+static MDIInt32
+mdiOpen (MDIHandleT TGHandle, MDIDeviceIdT DeviceID, MDIUint32 flags,
+ MDIHandleT * DeviceHandle)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiOpen (0x%x, 0x%x, flags 0x%0x, -)\n",
+ TGHandle, DeviceID, flags);
+ stat = MDIOpen (TGHandle, DeviceID, flags, DeviceHandle);
+ if (remote_debug > 1)
+ {
+ if (stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ else
+ fprintf_unfiltered (mdi_logfp, "returned: *DevHandle = 0x%x\n",
+ *DeviceHandle);
+ }
+ return stat;
+}
+
+static MDIInt32
+mdiClose (MDIHandleT DeviceHandle, MDIUint32 flags)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiClose (0x%x, flags 0x%x)\n",
+ DeviceHandle, flags);
+ stat = MDIClose (DeviceHandle, flags);
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+static MDIInt32
+mdiRead (MDIHandleT Device, MDIResourceT SrcR, MDIOffsetT SrcO, void *Buffer,
+ MDIUint32 ObjectSize, MDIUint32 Count)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiRead (0x%x, %s, 0x%s, -, %d, %d)\n",
+ Device, resrcName (SrcR),
+ phex_nz (SrcO, sizeof SrcO), ObjectSize, Count);
+ stat = MDIRead (Device, SrcR, SrcO, Buffer, ObjectSize, Count);
+ if (remote_debug > 1)
+ {
+ if (stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ else
+ {
+ fprintf_unfiltered (mdi_logfp, "read:");
+ dump_mem (Buffer, ObjectSize, Count);
+ }
+ }
+ return stat;
+}
+
+static MDIInt32
+mdiWrite (MDIHandleT Device, MDIResourceT DstR, MDIOffsetT DstO, void *Buffer,
+ MDIUint32 ObjectSize, MDIUint32 Count)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ {
+ fprintf_unfiltered (mdi_logfp, "mdiWrite (0x%x, %s, 0x%s, -, %d, %d)\n",
+ Device, resrcName (DstR),
+ phex_nz (DstO, sizeof DstO),
+ ObjectSize, Count);
+ fprintf_unfiltered (mdi_logfp, "write:");
+ dump_mem (Buffer, ObjectSize, Count);
+ }
+ stat = MDIWrite (Device, DstR, DstO, Buffer, ObjectSize, Count);
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+#if unused
+static MDIInt32
+mdiReadList (MDIHandleT Device, MDIUint32 ObjectSize, MDICRangeT * SrcList,
+ MDIUint32 ListCount, void *Buffer)
+{
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiReadList (-, %d, -, %d, -)\n",
+ ObjectSize, ListCount);
+ return MDIReadList (Device, ObjectSize, SrcList, ListCount, Buffer);
+}
+
+static MDIInt32
+mdiWriteList (MDIHandleT Device, MDIUint32 ObjectSize, MDICRangeT * DstList,
+ MDIUint32 ListCount, void *Buffer)
+{
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiWriteList (-, %d, -, %d, -)\n",
+ ObjectSize, ListCount);
+ return MDIWriteList (Device, ObjectSize, DstList, ListCount, Buffer);
+}
+
+static MDIInt32
+mdiMove (MDIHandleT Device, MDIResourceT SrcR, MDIOffsetT SrcO,
+ MDIResourceT DstR, MDIOffsetT DstO, MDIUint32 ObjectSize,
+ MDIUint32 Count, MDIUint32 Flag)
+{
+ if (remote_debug > 1)
+ fprintf_unfiltered
+ (mdi_logfp,
+ "mdiMove (-, %s, 0x%s, %s, 0x%s, Objsz %d, Cnt %d, Flg 0x%x)\n",
+ resrcName (SrcR), phex_nz (SrcO, sizeof SrcO),
+ resrcName (DstR), phex_nz (DstO, sizeof DstO),
+ ObjectSize, Count, Flag);
+ return MDIMove (Device, SrcR, SrcO, DstR, DstO, ObjectSize, Count, Flag);
+}
+
+static MDIInt32
+mdiFill (MDIHandleT Device, MDIResourceT DstR, MDIRangeT DstRng, void *Buffer,
+ MDIUint32 ObjectSize, MDIUint32 Count)
+{
+ if (remote_debug > 1)
+ fprintf_unfiltered
+ (mdi_logfp,
+ "mdiFill (-, %s, Rng 0x%s-0x%s, -, Objsz %d, Cnt %d)\n",
+ resrcName (DstR), phex_nz (DstRng.Start, sizeof DstRng.Start),
+ phex_nz (DstRng.End, sizeof DstRng.End), ObjectSize, Count);
+ return MDIFill (Device, DstR, DstRng, Buffer, ObjectSize, Count);
+}
+
+static MDIInt32
+mdiFind (MDIHandleT Device, MDIResourceT SrcR, MDIRangeT SrcRng, void *Buffer,
+ void *MaskBuffer, MDIUint32 ObjectSize, MDIUint32 Count,
+ MDIOffsetT * FoundOffset, MDIUint32 Mode)
+{
+ if (remote_debug > 1)
+ fprintf_unfiltered
+ (
+ mdi_logfp,
+ "mdiFind (-, %s, Rng 0x%s-0x%s, -, -, Objsz %d, Cnt %d, -, Mode %d)\n",
+ resrcName (SrcR), phex_nz (SrcRng.Start, sizeof SrcRng.Start),
+ phex_nz (SrcRng.End, sizeof SrcRng.End), ObjectSize, Count, Mode);
+ return MDIFind (Device, SrcR, SrcRng, Buffer, MaskBuffer, ObjectSize, Count,
+ FoundOffset, Mode);
+}
+#endif
+
+static MDIInt32
+mdiExecute (MDIHandleT Device)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiExecute (0x%x)\n", Device);
+ stat = MDIExecute (Device);
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+static MDIInt32
+mdiStep (MDIHandleT Device, MDIUint32 Steps, MDIUint32 Mode)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiStep (0x%x, %d, %d)\n",
+ Device, Steps, Mode);
+ stat = MDIStep (Device, Steps, Mode);
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+static MDIInt32
+mdiStop (MDIHandleT Device)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiStop (0x%x)\n", Device);
+ stat = MDIStop (Device);
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+static MDIInt32
+mdiReset (MDIHandleT Device, MDIUint32 Flag)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiReset (0x%x, Flg 0x%x)\n",
+ Device, Flag);
+ stat = MDIReset (Device, Flag);
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+static MDIInt32
+mdiCacheQuery (MDIHandleT Device, MDICacheInfoT * CacheInfo)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiCacheQuery (0x%x, -)\n", Device);
+ stat = MDICacheQuery (Device, CacheInfo);
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+static MDIInt32
+mdiCacheFlush (MDIHandleT Device, MDIUint32 Type, MDIUint32 Flag)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiCacheFlush (0x%x, Type %d, Flg 0x%x)\n",
+ Device, Type, Flag);
+ stat = MDICacheFlush (Device, Type, Flag);
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+static MDIInt32
+mdiRunState (MDIHandleT Device, MDIInt32 WaitTime, MDIRunStateT * runstate)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiRunState (0x%x, Wait %d, -)\n",
+ Device, WaitTime);
+ stat = MDIRunState (Device, WaitTime, runstate);
+ if (remote_debug > 1)
+ {
+ fprintf_unfiltered (mdi_logfp, "returned: ");
+ if (stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "%s\n", mdierrcode (stat));
+ else
+ mdiDisplayRunState (runstate);
+ }
+ return stat;
+}
+
+static MDIInt32
+mdiSetBp (MDIHandleT Device, MDIBpDataT * BpData)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "\
+mdiSetBp (0x%x, {%s, Enb %d, %s, 0x%s-0x%s, PassC %d, Pass2Go %d})\n",
+ Device,
+ bptypeName (BpData->Type), BpData->Enabled,
+ resrcName (BpData->Resource),
+ phex_nz (BpData->Range.Start,
+ sizeof BpData->Range.Start),
+ phex_nz (BpData->Range.End,
+ sizeof BpData->Range.End),
+ BpData->PassCount,
+ BpData->PassesToGo);
+ stat = MDISetBp (Device, BpData);
+ if (remote_debug > 1)
+ {
+ if (stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ else
+ fprintf_unfiltered (mdi_logfp, "returned: BpId=0x%x\n", BpData->Id);
+ }
+ return stat;
+}
+
+#if unused
+static MDIInt32
+mdiSetSWBp (MDIHandleT Device, MDIResourceT SrcResource, MDIOffsetT SrcOffset,
+ MDIBpIdT * BpId)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiSetSWBp (0x%x, %s, 0x%s, -)\n",
+ Device, resrcName (SrcResource),
+ phex_nz (SrcOffset, sizeof SrcOffset));
+ stat = MDISetSWBp (Device, SrcResource, SrcOffset, BpId);
+ if (remote_debug > 1)
+ {
+ if (stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ else
+ fprintf_unfiltered (mdi_logfp, "returned: BpId=0x%x\n", *BpId);
+ }
+ return stat;
+}
+#endif
+
+static MDIInt32
+mdiClearBp (MDIHandleT Device, MDIBpIdT BpID)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiClearBp (0x%x, BpID 0x%x)\n",
+ Device, BpID);
+ stat = MDIClearBp (Device, BpID);
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+#if unused
+static MDIInt32
+mdiEnableBp (MDIHandleT Device, MDIBpIdT BpID)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiEnableBp (0x%x, BpID 0x%x)\n",
+ Device, BpID);
+ stat = MDIEnableBp (Device, BpID);
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+static MDIInt32
+mdiDisableBp (MDIHandleT Device, MDIBpIdT BpID)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiDisableBp ()\n");
+ stat = MDIDisableBp (Device, BpID);
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+static MDIInt32
+mdiBpQuery (MDIHandleT Device, MDIInt32 * HowMany, MDIBpDataT * BpData)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiBpQuery (0x%x, &%d, -)\n",
+ Device, *HowMany);
+ stat = MDIBpQuery (Device, HowMany, BpData);
+ if (remote_debug > 1)
+ {
+ if (stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ else
+ fprintf_unfiltered (mdi_logfp, "returned: *HowMany = %d\n", *HowMany);
+ }
+ return stat;
+}
+#endif
+
+static MDIInt32
+mdiHwBpQuery (MDIHandleT Device, MDIInt32 *HowMany, MDIBpInfoT *BpInfo)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiHwBpQuery (0x%x, &%d, -)\n",
+ Device, *HowMany);
+ if (MDIHwBpQuery)
+ stat = MDIHwBpQuery (Device, HowMany, BpInfo);
+ else
+ stat = MDIErrUnsupported;
+ if (remote_debug > 1)
+ {
+ if (stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ else
+ fprintf_unfiltered (mdi_logfp, "returned: *HowMany = %d\n", *HowMany);
+ }
+ return stat;
+}
+
+static MDIInt32
+mdiDoCommand (MDIHandleT Device, char *Buffer)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiDoCommand (0x%x, \"%s\")\n",
+ Device, Buffer);
+ stat = MDIDoCommand (Device, Buffer);
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+static MDIInt32
+mdiAbort (MDIHandleT Device)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiAbort (0x%x)\n", Device);
+ stat = MDIAbort (Device);
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+#if unused
+static MDIInt32
+mdiTraceEnable (MDIHandleT Device)
+{
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiTraceEnable (-)\n");
+ return MDITraceEnable (Device);
+}
+
+static MDIInt32
+mdiTraceDisable (MDIHandleT Device)
+{
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiTraceDisable (-)\n");
+ return MDITraceDisable (Device);
+}
+
+static MDIInt32
+mdiTraceClear (MDIHandleT Device)
+{
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiTraceClear (-)\n");
+ return MDITraceClear (Device);
+}
+
+static MDIInt32
+mdiTraceStatus (MDIHandleT Device, MDIUint32 * Status)
+{
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiTraceStatus (-, -)\n");
+ return MDITraceStatus (Device, Status);
+}
+
+static MDIInt32
+mdiTraceCount (MDIHandleT Device, MDIUint32 * FrameCount)
+{
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiTraceCount (-, -)\n");
+ return MDITraceCount (Device, FrameCount);
+}
+
+static MDIInt32
+mdiTraceRead (MDIHandleT Device, MDIUint32 FirstFrame, MDIUint32 FrameCount,
+ MDIUint32 IncludeInstructions, MDITrcFrameT * Frames)
+{
+ if (remote_debug > 1)
+ fprintf_filtered
+ (mdi_logfp,
+ "mdiTraceRead (-, FirstFrame %d, FrameCnt %d, Insts? %d, -)\n",
+ FirstFrame, FrameCount, IncludeInstructions);
+ return MDITraceRead (Device, FirstFrame, FrameCount, IncludeInstructions,
+ Frames);
+}
+#endif
+
+static MDIInt32
+mdiSetTC (MDIHandleT Device, MDITCIdT TCId)
+{
+ MDIInt32 stat;
+
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiSetTC (0x%x, TCId 0x%x)\n",
+ Device, TCId);
+ if (MDISetTC)
+ stat = MDISetTC (Device, TCId);
+ else if (MDITCSet)
+ stat = MDITCSet (Device, TCId);
+ else
+ stat = MDIErrUnsupported;
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+static MDIInt32
+mdiGetTC (MDIHandleT Device, MDITCIdT *TCId)
+{
+ MDIInt32 stat;
+
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiGetTC (0x%x, -)\n", Device);
+ if (MDIGetTC)
+ stat = MDIGetTC (Device, TCId);
+ else if (MDITCGet)
+ stat = MDITCGet (Device, TCId);
+ else
+ stat = MDIErrUnsupported;
+ if (remote_debug > 1)
+ {
+ if (stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ else
+ fprintf_unfiltered (mdi_logfp, "returned: *TCId = 0x%x\n", *TCId);
+ }
+ return stat;
+}
+
+static MDIInt32
+mdiTCQuery (MDIHandleT Device, MDIInt32 *HowMany, MDITCDataT *TCData)
+{
+ MDIInt32 stat;
+
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiTCQuery (0x%x, &%d, -)\n",
+ Device, *HowMany);
+ if (MDITCQuery)
+ stat = MDITCQuery (Device, HowMany, TCData);
+ else if (MDIQueryTC)
+ stat = MDIQueryTC (Device, HowMany, TCData);
+ else
+ stat = MDIErrUnsupported;
+ if (remote_debug > 1)
+ {
+ if (stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ else
+ fprintf_unfiltered (mdi_logfp, "returned: *HowMany = %d\n", *HowMany);
+ }
+ return stat;
+}
+
+static MDIInt32
+mdiSetRunMode (MDIHandleT Device, MDITCIdT TCId, MDIUint32 StepMode,
+ MDIUint32 SuspendMode)
+{
+ MDIInt32 stat;
+
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp,
+ "mdiSetRunMode (0x%x, TCId 0x%x, %d, %u)\n",
+ Device, TCId, StepMode, SuspendMode);
+ if (MDISetRunMode)
+ stat = MDISetRunMode (Device, TCId, StepMode, SuspendMode);
+ else if (MDISetTCRunMode)
+ stat = MDISetTCRunMode (Device, TCId, StepMode != MDINoStep, SuspendMode);
+ else if (MDITCSetRunMode)
+ stat = MDITCSetRunMode (Device, TCId, StepMode != MDINoStep, SuspendMode);
+ else
+ stat = MDIErrUnsupported;
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+static MDIInt32
+mdiTeamCreate (MDIHandleT MDIHandle, MDITeamIdT *TeamId)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiTeamCreate (0x%x, -)\n", MDIHandle);
+ if (MDITeamCreate)
+ stat = MDITeamCreate (MDIHandle, TeamId);
+ else if (MDICreateTeam)
+ stat = MDICreateTeam (MDIHandle, TeamId);
+ else
+ stat = MDIErrUnsupported;
+ if (remote_debug > 1)
+ {
+ if (stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ else
+ fprintf_unfiltered (mdi_logfp, "returned: *TeamId = 0x%x\n", *TeamId);
+ }
+ return stat;
+}
+
+static MDIInt32
+mdiQueryTeams (MDIHandleT MDIHandle, MDIInt32 *HowMany, MDITeamIdT *TeamId)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiQueryTeams (0x%x, &%d, -)\n",
+ MDIHandle, *HowMany);
+ if (MDIQueryTeams)
+ stat = MDIQueryTeams (MDIHandle, HowMany, TeamId);
+ else
+ stat = MDIErrUnsupported;
+ if (remote_debug > 1)
+ {
+ if (stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ else
+ fprintf_unfiltered (mdi_logfp, "returned: *HowMany = %d\n", *HowMany);
+ }
+ return stat;
+}
+
+static MDIInt32
+mdiTeamClear (MDIHandleT MDIHandle, MDITeamIdT TeamId)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiTeamClear (0x%x, TeamId 0x%x)\n",
+ MDIHandle, TeamId);
+ if (MDITeamClear)
+ stat = MDITeamClear (MDIHandle, TeamId);
+ else if (MDIClearTeam)
+ stat = MDIClearTeam (MDIHandle, TeamId);
+ else
+ stat = MDIErrUnsupported;
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+static MDIInt32
+mdiTeamDestroy (MDIHandleT MDIHandle, MDITeamIdT TeamId)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiTeamDestroy (0x%x, TeamId 0x%x)\n",
+ MDIHandle, TeamId);
+ if (MDITeamDestroy)
+ stat = MDITeamDestroy (MDIHandle, TeamId);
+ else if (MDIDestroyTeam)
+ stat = MDIDestroyTeam (MDIHandle, TeamId);
+ else
+ stat = MDIErrUnsupported;
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+static MDIInt32
+mdiTMAttach (MDIHandleT MDIHandle, MDITeamIdT TeamId, MDITMDataT *TMData)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiTMAttach "
+ "(0x%x, TeamId 0x%x, { 0x%x, TGId 0x%x, 0x%x })\n",
+ MDIHandle, TeamId,
+ TMData->MDIHandle, TMData->TGId, TMData->DevId);
+ if (MDITMAttach)
+ stat = MDITMAttach (MDIHandle, TeamId, TMData);
+ else if (MDIAttachTM)
+ stat = MDIAttachTM (MDIHandle, TeamId, TMData);
+ else
+ stat = MDIErrUnsupported;
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+static MDIInt32
+mdiTMDetach (MDIHandleT MDIHandle, MDITeamIdT TeamId, MDITMDataT *TMData)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiTMDetach "
+ "(0x%x, TeamId 0x%x, { 0x%x, TGId 0x%x, 0x%x })\n",
+ MDIHandle, TeamId,
+ TMData->MDIHandle, TMData->TGId, TMData->DevId);
+ if (MDITMDetach)
+ stat = MDITMDetach (MDIHandle, TeamId, TMData);
+ else if (MDIDetachTM)
+ stat = MDIDetachTM (MDIHandle, TeamId, TMData);
+ else
+ stat = MDIErrUnsupported;
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+static MDIInt32
+mdiQueryTM (MDIHandleT MDIHandle, MDITeamIdT TeamId, MDIInt32 *HowMany,
+ MDITMDataT *TMData)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiQueryTM (0x%x, TeamId 0x%x, &%d, -)\n",
+ MDIHandle, TeamId, *HowMany);
+ if (MDIQueryTM)
+ stat = MDIQueryTM (MDIHandle, TeamId, HowMany, TMData);
+ else if (MDITMQuery)
+ stat = MDITMQuery (MDIHandle, TeamId, HowMany, TMData);
+ else
+ stat = MDIErrUnsupported;
+ if (remote_debug > 1)
+ {
+ if (stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ else
+ fprintf_unfiltered (mdi_logfp, "returned: *HowMany = %d\n", *HowMany);
+ }
+ return stat;
+}
+
+static MDIInt32
+mdiTeamExecute (MDIHandleT MDIHandle, MDITeamIdT TeamId)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mdiTeamExecute (0x%x, TeamId 0x%x)\n",
+ MDIHandle, TeamId);
+ if (MDITeamExecute)
+ stat = MDITeamExecute (MDIHandle, TeamId);
+ else
+ stat = MDIErrUnsupported;
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+static MDIInt32
+mipssim_SetConfigFile (MDIHandleT handle, char *name)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mipssim_SetConfigFile (0x%x, \"%s\")\n",
+ handle, name);
+ stat = MIPSsim_SetConfigFile (handle, name);
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+static MDIInt32
+mipssim_CreateProfile (MDIHandleT handle, MDIInt32 *pid,
+ MDIUint64 start, MDIUint64 size)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp,
+ "mipssim_CreateProfile (0x%x, -, 0x%s, 0x%s)\n",
+ handle,
+ phex_nz (start, sizeof start),
+ phex_nz (size, sizeof size));
+ stat = MIPSsim_CreateProfile (handle, pid, start, size);
+ if (remote_debug > 1)
+ {
+ if (stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ else
+ fprintf_unfiltered (mdi_logfp, "returned: *pid = %d\n", *pid);
+ }
+ return stat;
+}
+
+static MDIInt32
+mipssim_DestroyProfile (MDIHandleT handle, MDIInt32 id)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mipssim_DestroyProfile (0x%x, 0x%x)\n",
+ handle, id);
+ stat = MIPSsim_DestroyProfile (handle, id);
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+static MDIInt32
+mipssim_StartProfile (MDIHandleT handle, MDIInt32 id)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mipssim_StartProfile (0x%x, 0x%x)\n",
+ handle, id);
+ stat = MIPSsim_StartProfile (handle, id);
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+static MDIInt32
+mipssim_StopProfile (MDIHandleT handle, MDIInt32 id)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mipssim_StopProfile (0x%X, 0x%x)\n",
+ handle, id);
+ stat = MIPSsim_StopProfile (handle, id);
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+#if unused
+static MDIInt32
+mipssim_ClearProfile (MDIHandleT handle, MDIInt32 id)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mipssim_ClearProfile (0x%x, 0x%x)\n",
+ handle, id);
+ stat = MIPSsim_ClearProfile (handle, id);
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+#endif
+
+static MDIInt32
+mipssim_FetchProfile (MDIHandleT handle, MDIInt32 id,
+ MDIUint32 **cntbufp, MDIUint64 *cyclesp)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mipssim_FetchProfile (0x%x, 0x%x, -, -)\n",
+ handle, id);
+ stat = MIPSsim_FetchProfile (handle, id, cntbufp, cyclesp);
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+static MDIInt32
+mipssim_FreeProfileData (MDIHandleT handle, MDIUint32 **cntbufp)
+{
+ MDIInt32 stat;
+ if (remote_debug > 1)
+ fprintf_unfiltered (mdi_logfp, "mipssim_FreeProfileData (0x%x, -)\n",
+ handle);
+ stat = MIPSsim_FreeProfileData (handle, cntbufp);
+ if (remote_debug > 1 && stat != MDISuccess)
+ fprintf_unfiltered (mdi_logfp, "returned: %s\n", mdierrcode (stat));
+ return stat;
+}
+
+
+
+static void
+togdb_force_update (void)
+{
+#ifdef GDBTK
+ if (gdbtk_interp != NULL)
+ Tcl_Eval (gdbtk_interp, "gdbtk_update");
+#endif
+}
+
+static void
+check_mdi (void)
+{
+ if (mdi_desc == NULL)
+ error (_("MDI connection not opened yet, use the 'target mdi' command."));
+};
+
+static int
+isa2int (char *str)
+{
+ const struct isa_xlate_struct *p;
+
+ for (p = isa_xlate; p->isa && strcmp (p->isa, str); p++)
+ continue;
+ return p->num;
+}
+
+
+static void
+dump_mem (void *buffer, int elsize, int cnt)
+{
+ gdb_byte *buf = buffer;
+ int col = 0;
+ int width;
+ int n;
+
+ if (elsize > sizeof(ULONGEST))
+ {
+ fprintf_unfiltered (mdi_logfp, "Cannot print objects of size %d\n",
+ elsize);
+ return;
+ }
+
+ if (elsize == 0)
+ elsize = 1;
+
+ n = (cnt * elsize > 128) ? 128 / elsize : cnt;
+
+ width = 16 / elsize;
+
+ while (n-- > 0)
+ {
+ ULONGEST val = extract_unsigned_integer (buf, elsize);
+ buf += elsize;
+ cnt -= 1;
+
+ if (col == 0)
+ fprintf_unfiltered (mdi_logfp, "\t");
+
+ if (elsize > 1)
+ fprintf_unfiltered (mdi_logfp, "%s ", phex (val, elsize));
+ else
+ fprintf_unfiltered (mdi_logfp, "%02x ", (unsigned int)val & 0xff);
+
+ if (++col == width || n == 0)
+ {
+ /* Output ascii dump for byte size elements. */
+ if (elsize == 1)
+ {
+ int limit = col;
+ buf -= col; /* Backup over printed bytes. */
+ /* Space across to ascii column. */
+ for ( ; col < width + 1; col++)
+ fprintf_unfiltered (mdi_logfp, " ");
+ for (col = 0; col < limit; col++)
+ {
+ fputc_unfiltered (isprint (*buf) ? *buf : '.', mdi_logfp);
+ buf++;
+ }
+ }
+ fprintf_unfiltered (mdi_logfp, "\n");
+ col = 0;
+ }
+ }
+
+ if (col != 0)
+ fprintf_unfiltered (mdi_logfp, "\n");
+ if (cnt != 0)
+ fprintf_unfiltered (mdi_logfp, "\tetc...\n");
+}
+
+
+static const char *
+mdierrcode (MDIInt32 err)
+{
+ const char *es;
+ static char buf[64];
+ int i;
+
+ for (i = 0; (es = errorcodes[i].str) && errorcodes[i].errorcode != err; i++)
+ continue;
+
+ if (es)
+ return es;
+
+ sprintf (buf, "MDIerr=%d", err);
+ return buf;
+}
+
+static void
+mdierr (const char *file, int line, MDIInt32 err, const char *what)
+{
+ const char *es = mdierrcode (err);
+ if (remote_debug)
+ error (_("%s:%d: %s failed (%s)"), file, line, what, es);
+ else
+ error (_("MDI %s failed (%s)"), what, es);
+}
+
+#define MDIERR(op, what) \
+ do \
+ { \
+ MDIInt32 __stat = (op); \
+ if (__stat != MDISuccess) \
+ mdierr (__FILE__, __LINE__, __stat, what); \
+ } \
+ while (0)
+
+static void
+mdiwarn (char *file, int line, MDIInt32 err, const char *what)
+{
+ const char *es = mdierrcode (err);
+
+ if (remote_debug)
+ warning (_("%s:%d: %s failed (%s)"), file, line, what, es);
+ else
+ warning (_("MDI %s failed (%s)"), what, es);
+}
+
+#define MDIWARN(op, what) \
+ do \
+ { \
+ MDIInt32 __stat = (op); \
+ if (__stat != MDISuccess) \
+ mdiwarn (__FILE__, __LINE__, __stat, what); \
+ } \
+ while (0)
+
+
+
+static MDIInt32 __stdcall
+mdiPeriodic (MDIHandleT handle)
+{
+ int stop = 0;
+
+ /* Only call ui_loop_hook if this callback is from mdi_wait or
+ mdi_resume(step==1).
+
+ Unfortunately MDIRead/MDIWrite also call the periodic callback
+ and that can lead to problems where the GUI tries to refresh the
+ memory window etc. */
+
+ if (deprecated_ui_loop_hook != NULL && (mdi_wait_active || mdi_step_active))
+ stop = deprecated_ui_loop_hook (0);
+
+ if (stop)
+ quit_flag = 1;
+ if (quit_flag) /* gdb's idea of quit */
+ {
+ MDIInt32 mdistat;
+ if (mdi_step_active)
+ mdistat = mdiAbort (handle);
+ /* XXX How do we stop a normal wait? */
+ }
+
+ if (remote_debug)
+ {
+ static int progress = 0;
+ if ((progress++ % 30) == 0)
+ {
+ printf_unfiltered (".");
+ gdb_flush (gdb_stdout);
+ if (quit_flag)
+ printf_unfiltered (_("mdiPeriodic: quitting\n"));
+ }
+ }
+
+ return MDISuccess;
+}
+
+
+
+static MDIInt32
+mdi_read (MDIHandleT Device, MDIResourceT SrcR, MDIOffsetT SrcO, void *Buffer,
+ MDIUint32 ObjectSize, MDIUint32 Count)
+{
+ if (!ptid_equal (inferior_ptid, last_ptid))
+ mdi_switch_to_thread ();
+ return mdiRead (Device, SrcR, SrcO, Buffer, ObjectSize, Count);
+}
+
+static MDIInt32
+mdi_write (MDIHandleT Device, MDIResourceT DstR, MDIOffsetT DstO, void *Buffer,
+ MDIUint32 ObjectSize, MDIUint32 Count)
+{
+ if (!ptid_equal (inferior_ptid, last_ptid))
+ mdi_switch_to_thread ();
+ return mdiWrite (Device, DstR, DstO, Buffer, ObjectSize, Count);
+}
+
+
+
+static char *
+check_for_template (const char *dir)
+{
+ size_t dirlen;
+ char *buf;
+ struct stat s;
+
+ if (remote_debug)
+ fprintf_unfiltered (mdi_logfp, "checking \"%s\" for mipssim.cfg\n",
+ dir);
+
+ dirlen = strlen (dir);
+ buf = (char *) xmalloc (dirlen + sizeof("/mipssim.cfg"));
+ sprintf (buf, "%s/mipssim.cfg", dir);
+
+ if (stat (buf, &s) == 0 && S_ISREG (s.st_mode))
+ return buf;
+
+ xfree (buf);
+ return NULL;
+}
+
+
+static void
+mdi_setconfigfile (struct mdi_state *mdi, MDIDDataT *ddata, char *cfg)
+{
+ struct cleanup *cleanups = NULL;
+ MDIInt32 mdistat;
+
+ if (! MIPSsim_SetConfigFile)
+ return;
+
+ if (! cfg || ! *cfg)
+ {
+ char tmpfile[sizeof ("/tmp/gmdiXXXXXX")];
+ char devtmpfile[sizeof ("/tmp/gmddXXXXXX")];
+ char line[256];
+ int matches = 0;
+ char *template = NULL;
+ char *dname;
+ char *end;
+ int cfgfd;
+ int copy;
+ FILE *infile, *outfile;
+ size_t dlen;
+ MDIInt32 major, minor, patch;
+
+ if (remote_debug)
+ fprintf_unfiltered (mdi_logfp, "gdb_program_name=\"%s\"\n",
+ gdb_program_name);
+
+ end = strrchr (gdb_program_name, '/');
+#if defined(_WIN32) || defined(__CYGWIN32__)
+ {
+ /* We could have \foo\bar, or /foo\bar. */
+ char *bslash = strrchr (gdb_program_name, '\\');
+ if (bslash > end)
+ end = bslash;
+ }
+#endif
+
+ if (end)
+ {
+ /* Make a copy of program_name in dir.
+ Leave room for later "/../share". */
+ size_t dirlen = end - gdb_program_name;
+ char *dir = (char *) alloca (dirlen + sizeof ("/../share"));
+ strncpy (dir, gdb_program_name, dirlen);
+ dir[dirlen] = '\0';
+ template = check_for_template (dir);
+ if (! template)
+ {
+ /* Try relative path - look in /../share. */
+ strcpy (dir + dirlen, "/../share");
+ template = check_for_template (dir);
+ }
+ }
+
+ if (! template)
+ {
+ /* Try looking for it in the directories on the search path. */
+ char *path = getenv ("PATH");
+ if (path)
+ {
+ char *sp;
+ path = xstrdup (path);
+ for (sp = strtok (path, ":"); ! template && sp;
+ sp = strtok (NULL, ":"))
+ {
+ size_t dirlen = strlen (sp);
+ char *dir;
+ if (dirlen == 0)
+ continue;
+ /* look in /path/../share. */
+ dir = (char *) xmalloc (dirlen + sizeof ("/../share"));
+ strcpy (dir, sp);
+ strcpy (dir + dirlen, "/../share");
+ template = check_for_template (dir);
+ xfree (dir);
+ }
+ xfree (path);
+ }
+ }
+
+ if (! template)
+ /* Try in the "standard" directory. */
+ template = check_for_template (MIPSSIM_LIBRARY);
+
+ if (! template)
+ error (_("Cannot find MIPSsim config file template: mipssim.cfg"));
+
+ cleanups = make_cleanup (xfree, template);
+
+ infile = fopen (template, FOPEN_RT);
+ if (! infile)
+ error (_("Cannot open MIPSsim config template: %s"), template);
+
+ strcpy (tmpfile, "/tmp/gmdiXXXXXX");
+ cfgfd = mkstemp (tmpfile);
+ if (cfgfd < 0)
+ error (_("Cannot create temp MIPSsim config file"));
+
+ if (remote_debug)
+ printf_unfiltered (_("\
+Generating MIPSsim cfg from %s to %s for \"%s\"\n"),
+ template, tmpfile, ddata->DName);
+
+ mdi->cfgfile = cfg = xstrdup (tmpfile);
+
+ outfile = fdopen (cfgfd, FOPEN_WT);
+ if (! outfile)
+ error (_("Cannot write to temp MIPSsim config file"));
+
+
+ /* Get MIPSsim version number. */
+ major = MIPSsim_ZeroPerfCounter ? 4 : 3;
+ minor = 0;
+ patch = 0;
+ if (MIPSsim_GetVersion)
+ (void) MIPSsim_GetVersion (mdi->MDIHandle, &major, &minor, &patch);
+
+ dname = ddata->DName;
+
+ /* Skip unneeded leading part of name from MIPSsim 3.x. */
+ if (strncmp (dname, "MIPS32_", sizeof "MIPS32_" - 1) == 0)
+ dname += sizeof "MIPS32_" - 1;
+ else if (strncmp (dname, "MIPS64_", sizeof "MIPS64_" - 1) == 0)
+ dname += sizeof "MIPS64_" - 1;
+
+ /* Construct string to match a regexp pattern against which
+ includes MISPsim version number followed by CPU name. */
+ asprintf (&dname, "%d.%d.%d;%s", major, minor, patch, dname);
+ if (! dname)
+ nomem (0);
+
+ cleanups = make_cleanup (xfree, dname);
+ dlen = strlen (dname);
+ copy = 1;
+
+ while (fgets (line, sizeof (line), infile))
+ {
+ char *lp;
+
+ for (lp = line; *lp && isspace (*lp); lp++)
+ continue;
+ if (! *lp || *lp == '#')
+ continue;
+
+ if (*lp == '{')
+ {
+ char *ep;
+ int plen;
+ int invert = 0;
+ for (ep = ++lp; *ep && *ep != '}'; ep++)
+ continue;
+ if (*ep != '}')
+ continue;
+ if (*lp == '!')
+ {
+ ++lp;
+ invert = 1;
+ }
+ plen = ep - lp;
+ if (! strncasecmp (lp, "COMMON", plen))
+ copy = 1;
+ else if (! strncasecmp (lp, "EB", plen))
+ copy = ddata->Endian == MDIEndianBig;
+ else if (! strncasecmp (lp, "EL", plen))
+ copy = ddata->Endian == MDIEndianLittle;
+ else if (! strncasecmp (lp, "DEBUG0", plen))
+ copy = remote_debug == 0;
+ else if (! strncasecmp (lp, "DEBUG1", plen))
+ copy = remote_debug == 1;
+ else if (! strncasecmp (lp, "DEBUG2", plen))
+ copy = remote_debug >= 2;
+ else
+ {
+ char * patstr;
+ regex_t pattern;
+ int ec;
+
+ /* For input {xxx} make regex. */
+ if (asprintf (&patstr, "^(%.*s)([^-a-z0-9]|$)",
+ plen, lp) == 0)
+ nomem (0);
+
+ if ((ec = regcomp (&pattern, patstr,
+ REG_ICASE | REG_EXTENDED)) == 0)
+ {
+ copy = re_search (&pattern, dname, dlen,
+ 0, dlen, NULL) >= 0;
+ if (copy)
+ ++matches;
+ regfree (&pattern);
+ }
+ else
+ {
+ char errorbuffer[512];
+ regerror (ec, NULL, errorbuffer, sizeof errorbuffer);
+ warning (_("Error in regexp /%s/: %s"), patstr,
+ errorbuffer);
+ copy = 0;
+ }
+ free (patstr);
+ }
+ copy ^= invert;
+ continue;
+ }
+
+ if (copy)
+ fputs (line, outfile);
+ }
+
+ fclose (infile);
+
+ if (mdi_devcfgfile)
+ {
+ char *devcfg = mdi_devcfgfile;
+#ifdef __CYGWIN32__
+ /* Convert the Cygwin name to a Windows name. */
+ char winpath[MAX_PATH];
+ if (cygwin_conv_to_win32_path (devcfg, winpath) == 0)
+ devcfg = winpath;
+#endif
+ if (remote_debug)
+ printf_unfiltered (_("Adding \"set DEV_CFG %s\" to config file\n"),
+ devcfg);
+ fprintf (outfile, "set DEV_CFG %s\n", devcfg);
+ }
+
+ fclose (outfile);
+ if (matches == 0)
+ error (_("No entries matching MIPSsim CPU '%s' in %s"),
+ dname, template);
+ }
+
+#ifdef __CYGWIN32__
+ /* Convert the Cygwin name to a Windows name. */
+ {
+ char winpath[MAX_PATH];
+ if (cygwin_conv_to_win32_path (cfg, winpath) == 0)
+ cfg = winpath;
+ }
+#endif
+
+ mdistat = mipssim_SetConfigFile (mdi->MDIHandle, cfg);
+ if (mdistat != MDISuccess)
+ error (_("MIPSsim cannot access config file: \"%s\""), cfg);
+
+ if (cleanups)
+ do_cleanups (cleanups);
+}
+
+
+
+static MDIInt32
+SelectDevice (MDIDDataT * ddata, MDIInt32 n, int device)
+{
+ int i;
+ char *s;
+ unsigned long value;
+
+ if (device > n)
+ error (_("Bad device number %d, only %d devices available."), device, n);
+
+ if (device > 0 && device <= n)
+ return device - 1;
+
+ if (n == 1)
+ return (0);
+
+#ifdef GDBTK
+ /* Using command_line_input when GUI is active breaks the console window. */
+ if (gdbtk_interp != NULL)
+ error (_("Use \"set mdi device\" to select MDI device."));
+#endif
+
+retry:
+ printf_filtered (_("Select Device:\n"));
+ for (i = 0; i < n; i++)
+ {
+ /* Skip devices called "RESERVED". */
+ if (strncasecmp (ddata[i].DName, "RESERVED", sizeof "RESERVED" - 1) == 0)
+ continue;
+ printf_filtered (" %02d) %s\n", i + 1, ddata[i].DName);
+ }
+
+ reinitialize_more_filter ();
+ s = command_line_input ("Enter Number (or q to quit) > ", 0,
+ "mdidevice-choice");
+
+ if (s == NULL)
+ error (_("Unexpected EOF."));
+
+ while (*s == ' ' || *s == '\t')
+ ++s;
+ if (*s == 'q')
+ deprecated_throw_reason (RETURN_QUIT);
+
+ value = strtoul (s, &s, 0);
+ if (value < 1 || value > n || *s)
+ goto retry;
+
+ return (value - 1);
+}
+
+static MDIInt32
+SelectTarget (MDITGDataT * tgdata, MDIInt32 n, int target)
+{
+ int i;
+ char *s;
+ unsigned long value;
+
+ if (target > n)
+ error (_("Bad target number %d, only %d targets available."), target, n);
+
+ if (target > 0 && target <= n)
+ return target - 1;
+
+ if (n == 1)
+ return 0;
+
+#ifdef GDBTK
+ /* Using command_line_input when GUI is active breaks the console window. */
+ if (gdbtk_interp != NULL)
+ error (_("Use \"set mdi target\" to select MDI target group."));
+#endif
+
+retry:
+ printf_filtered (_("Select Target Group:\n"));
+ for (i = 0; i < n; i++)
+ {
+ /* Skip targets called "RESERVED" */
+ if (strncasecmp (tgdata[i].TGName, "RESERVED",
+ sizeof "RESERVED" - 1) == 0)
+ continue;
+ printf_filtered (" %02d) %s\n", i + 1, tgdata[i].TGName);
+ }
+
+ reinitialize_more_filter ();
+ s = command_line_input (_("Enter Number (or q to quit) > "), 0,
+ "mditarget-choice");
+ if (s == NULL)
+ error (_("Unexpected EOF."));
+
+ while (*s == ' ' || *s == '\t')
+ ++s;
+ if (*s == 'q')
+ deprecated_throw_reason (RETURN_QUIT);
+
+ value = strtoul (s, &s, 0);
+ if (value < 1 || value > n || *s)
+ goto retry;
+
+ return (value - 1);
+}
+
+static void (*mdi_signal (int sig, void (*handler) (int))) (int)
+{
+#if defined (HAVE_SIGACTION) && defined (SA_RESTART)
+ struct sigaction sa, osa;
+
+ sa.sa_handler = handler;
+ sigemptyset (&sa.sa_mask);
+ sa.sa_flags = 0;
+ sigaction (sig, &sa, &osa);
+ return osa.sa_handler;
+#else
+ return signal (sig, handler);
+#endif
+}
+
+static RETSIGTYPE (*ofunc) ();
+static RETSIGTYPE mdi_interrupt (int signo);
+static void (*interrupt_cleanup)(void);
+
+static void
+open_cleanup (void)
+{
+}
+
+static void
+haltDev (struct mdi_state *mdi)
+{
+ MDIInt32 mdistat;
+ MDIRunStateT runstate;
+ struct timeval now, when;
+ int timedout, interrupted, forever;
+ int stopcount;
+ int i;
+
+ /* Wait the specified number of seconds for CPU to halt. */
+ gettimeofday (&now, NULL);
+ when = now;
+ when.tv_sec += mdi_connecttimeout;
+ forever = (mdi_connecttimeout == UINT_MAX);
+ timedout = interrupted = 0;
+
+ /* Install our SIGINT signal handler. */
+ interrupt_cleanup = open_cleanup;
+ ofunc = mdi_signal (SIGINT, mdi_interrupt);
+
+ stopcount = 0;
+ i = 0;
+
+ do
+ {
+ mdistat = mdiRunState (mdi->gmdata[i].DevHandle, 100, &runstate);
+ if (mdistat != MDISuccess)
+ break;
+
+ if ((runstate.Status & MDIStatusMask) == MDIStatusRunning
+ || runstate.Status == MDIStatusDisabled
+ || runstate.Status == MDIStatusVPEDisabled)
+ {
+ mdistat = mdiStop (mdi->gmdata[i].DevHandle);
+ if (mdistat != MDISuccess)
+ break;
+
+ mdistat = mdiRunState (mdi->gmdata[i].DevHandle, 100, &runstate);
+ if (mdistat != MDISuccess)
+ break;
+ }
+
+ if (runstate.Status == MDIStatusDisabled
+ || runstate.Status == MDIStatusVPEDisabled)
+ {
+ mdi->gmdata[i].disabled = 1;
+ if (mdi->gmcount == 1)
+ forever = 1;
+ }
+ else if ((runstate.Status & MDIStatusMask) == MDIStatusRunning)
+ forever = (mdi_connecttimeout == UINT_MAX);
+ else
+ {
+ mdi->gmdata[i].disabled = 0;
+ stopcount++;
+ if (stopcount == 1)
+ mdi->gmindex = i;
+ if (stopcount == mdi->gmcount)
+ break;
+ }
+
+ i = (i + 1) % mdi->gmcount;
+
+ /* Only time out after a full poll of all devices. */
+ if (i == 0 && (!forever || stopcount > 0))
+ {
+ gettimeofday (&now, NULL);
+ if (timercmp (&now, &when, >))
+ {
+ timedout = 1;
+ break;
+ }
+ }
+ /* See if the user has asked us to stop. */
+ if (quit_flag
+ || (deprecated_ui_loop_hook && deprecated_ui_loop_hook (0)))
+ {
+ interrupted = 1;
+ break;
+ }
+ sleep_ms (100);
+ }
+ while (1);
+
+ /* Restore old SIGINT handler. */
+ signal (SIGINT, ofunc);
+
+ if (timedout && stopcount == 0)
+ error (_("Cannot halt CPU"));
+ else if (interrupted)
+ error (_("Interrupted while waiting for the device"));
+ else
+ MDIERR (mdistat, _("halting CPU"));
+}
+
+static void
+resetDev (struct mdi_state *mdi, int connreset)
+{
+ MDIInt32 mdistat;
+ MDIRunStateT runstate;
+ struct timeval now, when;
+
+ if (connreset >= 0)
+ {
+ /* Reset the device, wait "connectreset" seconds, then stop it. */
+ mdistat = mdiReset (mdi->gmdata[0].DevHandle, MDIFullReset);
+ if (mdistat == MDISuccess && connreset > 0 && ! mdi->mipssim_p)
+ {
+ /* Start CPU execution. */
+ if (mdi->gmcount > 1)
+ {
+ mdistat = mdiTeamExecute (mdi->MDIHandle, mdi->gid);
+ if (mdistat == MDIErrUnsupported)
+ {
+ int i;
+
+ for (i = 0; i < mdi->gmcount; i++)
+ {
+ mdistat = mdiExecute (mdi->gmdata[i].DevHandle);
+ if (mdistat != MDIErrDisabled)
+ MDIWARN (mdistat, _("starting execution"));
+ }
+ mdistat = MDISuccess;
+ }
+ }
+ else
+ mdistat = mdiExecute (mdi->gmdata[0].DevHandle);
+ if (mdistat == MDISuccess)
+ {
+ /* Keep polling MDI until "connectreset" seconds elapsed. */
+ gettimeofday (&now, NULL);
+ when = now;
+ when.tv_sec += connreset;
+ do
+ {
+ /* Poll MDI - may be necessary for some probes. */
+ (void) mdiRunState (mdi->gmdata[0].DevHandle,
+ 200, &runstate);
+ sleep_ms (200);
+ gettimeofday (&now, NULL);
+ }
+ while (timercmp (&now, &when, <));
+ /* Halt CPU. */
+ (void) mdiStop (mdi->gmdata[0].DevHandle);
+ }
+ }
+ }
+}
+
+static MDIInt32
+getDevs (MDIHandleT tg, int index, MDIDDataT **ddata, MDIInt32 *devices)
+{
+ MDIInt32 mdistat;
+
+ *ddata = NULL;
+ *devices = 0;
+
+ mdistat = mdiDQuery (tg, devices, NULL);
+ if (mdistat != MDISuccess)
+ return mdistat;
+
+ *ddata = (MDIDDataT *) xmalloc (*devices * sizeof (MDIDDataT));
+ mdistat = mdiDQuery (tg, devices, *ddata);
+
+ return mdistat;
+}
+
+static void
+updateDev (struct mdi_state *mdi, int index, MDIDeviceIdT device)
+{
+ struct cleanup *cleanups;
+ MDIDDataT *ddata = NULL;
+ MDIInt32 devices, i;
+ MDIInt32 mdistat;
+
+ mdistat = getDevs (mdi->gmdata[index].TGHandle, index, &ddata, &devices);
+ cleanups = make_cleanup (xfree, ddata);
+ MDIERR (mdistat, _("device query"));
+
+ for (i = 0; i < devices; i++)
+ if (ddata[i].Id == device)
+ memmove (&mdi->gmdata[index].DeviceData, ddata + i, sizeof (MDIDDataT));
+
+ do_cleanups (cleanups);
+}
+
+static void
+openDev (struct mdi_state *mdi, int index, char *configfile)
+{
+ struct cleanup *cleanups;
+ MDIDDataT *ddata = NULL;
+ MDIDDataT *dp;
+ MDIInt32 devices;
+ MDIDeviceIdT device;
+ MDIInt32 mdistat;
+
+ mdi->gmdata[index].disabled = 1;
+
+ device = mdi->gmdata[index].tmdata.DevId + 1;
+
+ mdistat = getDevs (mdi->gmdata[index].TGHandle, index, &ddata, &devices);
+ cleanups = make_cleanup (xfree, ddata);
+ MDIERR (mdistat, _("device query"));
+
+ if (devices == 0)
+ error (_("No MDI devices available"));
+
+ device = SelectDevice (ddata, devices, device);
+ dp = &ddata[device];
+
+ if (remote_debug)
+ fprintf_unfiltered (mdi_logfp, "\
+selected dname '%s' fpart '%s' vendor '%s' vfamily '%s' vpart '%s' \
+vpartrev '%s' vpartdata '%s'\n",
+ dp->DName, dp->FPart, dp->Vendor, dp->VFamily,
+ dp->VPart, dp->VPartRev, dp->VPartData);
+
+ mdi->mipssim_p = (strcmp (dp->VPartData, "MIPSsim") == 0);
+ if (mdi->mipssim_p && index == 0)
+ mdi_setconfigfile (mdi, dp, configfile);
+
+ /* Old versions used to force mdi_continueonclose to "0" for
+ MIPSsim. Not anymore, but keep this value as the default. */
+ if (mdi_continueonclose == -1)
+ {
+ if (mdi->mipssim_p)
+ mdi_continueonclose = 0;
+ else
+ mdi_continueonclose = 1;
+ }
+
+ mdistat = mdiOpen (mdi->gmdata[index].TGHandle, dp->Id, MDIExclusiveAccess,
+ &mdi->gmdata[index].DevHandle);
+ MDIERR (mdistat, _("device open"));
+
+ if (dp->VPartData[0] && strcmp (dp->VPartData, "Unknown") != 0)
+ printf_filtered (_("Selected device %s on %s %s\n"), dp->DName,
+ dp->Vendor, dp->VPartData);
+ else
+ printf_filtered (_("Selected device %s\n"), dp->DName);
+
+ updateDev (mdi, index, dp->Id);
+
+ do_cleanups (cleanups);
+}
+
+
+static void
+openTG (struct mdi_state *mdi, int index)
+{
+ struct cleanup *cleanups;
+ MDIInt32 mdistat = MDISuccess;
+ MDITGDataT *tgdata = NULL;
+ MDIInt32 targets;
+ MDITGIdT target;
+
+ if ((mdi->Config.MDICapability & MDICAP_TargetGroups) == 0)
+ {
+ mdi->gmdata[index].TGHandle = mdi->gmdata[index].tmdata.MDIHandle;
+ return;
+ }
+
+ target = mdi->gmdata[index].tmdata.TGId + 1;
+ targets = 0;
+ mdistat = mdiTGQuery (mdi->gmdata[index].tmdata.MDIHandle, &targets, NULL);
+ MDIERR (mdistat, _("target group query"));
+
+ tgdata = (MDITGDataT *) xmalloc (targets * sizeof (MDITGDataT));
+ cleanups = make_cleanup (xfree, tgdata);
+
+ mdistat = mdiTGQuery (mdi->gmdata[index].tmdata.MDIHandle, &targets, tgdata);
+ MDIERR (mdistat, _("target group query"));
+
+ target = SelectTarget (tgdata, targets, target);
+
+ mdistat = mdiTGOpen (mdi->gmdata[index].tmdata.MDIHandle,
+ tgdata[target].TGId, MDISharedAccess,
+ &mdi->gmdata[index].TGHandle);
+ if (mdistat != MDISuccess)
+ /* Failed shared access - try exclusive access. */
+ mdistat = mdiTGOpen (mdi->gmdata[index].tmdata.MDIHandle,
+ tgdata[target].TGId, MDIExclusiveAccess,
+ &mdi->gmdata[index].TGHandle);
+ MDIERR (mdistat, _("target group open"));
+
+ if (remote_debug)
+ printf_filtered (_("Selected target group %s\n"), tgdata[target].TGName);
+ mdi->gmdata[index].tmdata.TGId = tgdata[target].TGId;
+
+ do_cleanups (cleanups);
+}
+
+static int __stdcall
+mdiDbgOutput (MDIHandleT handle, MDIInt32 Type, char *Buffer, MDIInt32 Count)
+{
+ if (remote_debug > 1)
+ {
+ fprintf_unfiltered (mdi_logfp, "MDICBOutput (0x%x, %s, -, %d) called\n",
+ handle, lookupName (cbtype_Names, Type), Count);
+ fprintf_unfiltered (mdi_logfp, "data:");
+ dump_mem (Buffer, 0, Count);
+ }
+
+ if (Type == MDIIOTypeMDIErr || Type == MDIIOTypeTgtErr)
+ {
+ ui_file_write (gdb_stdtargerr, Buffer, Count);
+ gdb_flush (gdb_stdtargerr);
+ }
+ else if (! mdi_quiet)
+ {
+ ui_file_write (gdb_stdtarg, Buffer, Count);
+ gdb_flush (gdb_stdtarg);
+ }
+ return MDISuccess;
+}
+
+
+static int __stdcall
+mdiDbgInput (MDIHandleT handle, MDIInt32 Type, MDIInt32 Mode,
+ char **Buffer, MDIInt32 * Count)
+{
+ static char *lastline = NULL;
+ char *line;
+ extern FILE *instream;
+
+ if (deprecated_readline_begin_hook)
+ (*deprecated_readline_begin_hook) ("\nMDI library has requested input:\n");
+ else if (input_from_terminal_p ())
+ printf_filtered (_("\nMDI library has requested input:\n"));
+
+ /* Make sure that all output has been output. Some machines may let
+ you get away with leaving out some of the gdb_flush, but not all. */
+ wrap_here ("");
+ gdb_flush (gdb_stdout);
+ gdb_flush (gdb_stderr);
+
+ if (deprecated_readline_hook)
+ line = (*deprecated_readline_hook) ("MDILIB> ");
+ else if (input_from_terminal_p ())
+ {
+ line = gdb_readline_wrapper ("MDILIB> ");
+ if (line && *line) /* Add to command history. */
+ add_history (line);
+ }
+ else
+ line = gdb_readline (0);
+
+ if (deprecated_readline_end_hook)
+ (*deprecated_readline_end_hook) ();
+
+ /* Avoid consuming too much memory. */
+ if (lastline)
+ {
+ free (lastline);
+ lastline = line;
+ }
+
+ *Buffer = line;
+ *Count = strlen (line);
+ return MDISuccess;
+}
+
+
+
+static void
+mdi_dlopen (char *lib, struct mdi_state *mdi, int from_tty)
+{
+ MDIInt32 mdistat;
+ MDIVersionRangeT vrange;
+ MDIVersionT api;
+
+ /* MDIInit must be called to load the shared library. */
+ if (!mdiModule)
+ {
+ mdistat = MDIInit (lib, &mdiModule);
+ if (mdistat == MDIErrLoadLib)
+ {
+ if (lib)
+ error (_("Cannot load MDI library: \"%s\"."), lib);
+ if (from_tty)
+ error (_("\
+Unknown MDI library.\n\
+Please specify the library on the \"target\" command line or\n\
+by setting the 'mdi library' variable, or the $GDBMDILIB\n\
+environment variable."));
+ error (_("\
+Unknown MDI library.\n\
+Please set the 'mdi library' variable,\n\
+or the $GDBMDILIB environment variable."));
+ }
+ MDIERR (mdistat, _("MDI initialisation"));
+ }
+
+ /* Get API version range supported by library. */
+ mdistat = mdiVersion (&vrange);
+ MDIERR (mdistat, _("MDI get versions"));
+
+ /* Use the highest API compatible with library. */
+ api = ((vrange.newest < MDICurrentRevision)
+ ? vrange.newest : MDICurrentRevision);
+
+ /* Make sure it's not too old. */
+ if (api < vrange.oldest || api < MDIOldestRevision)
+ {
+ if (remote_debug)
+ {
+ fprintf_unfiltered (mdi_logfp,
+ "MDI library API: oldest=%d.%d newest=%d.%d\n",
+ vrange.oldest >> 16, vrange.oldest & 0xffff,
+ vrange.newest >> 16, vrange.newest & 0xffff);
+ fprintf_unfiltered (mdi_logfp,
+ "Our API: oldest=%d.%d current=%d.%d\n",
+ MDIOldMajor, MDIOldMinor, MDIMajor, MDIMinor);
+ }
+ error (_("MDI library API version mismatch"));
+ }
+
+ sprintf (mdi->Config.User, "GNU gdb %.*s",
+ (int) sizeof (mdi->Config.User - sizeof "GNU gdb "), version);
+ mdi->Config.MDICBOutput = mdiDbgOutput;
+ mdi->Config.MDICBInput = mdiDbgInput;
+ mdi->Config.MDICBPeriodic = mdiPeriodic;
+
+ mdistat = mdiConnect (api, &mdi->MDIHandle, &mdi->Config);
+ MDIERR (mdistat, _("MDI connect"));
+
+ if (remote_debug)
+ fprintf_unfiltered (mdi_logfp,
+ "connected to library '%s', implementer '%s'\n",
+ lib ? lib : "<default>", mdi->Config.Implementer);
+
+ if (mdi_implementer)
+ xfree (mdi_implementer);
+ mdi_implementer = xstrdup (mdi->Config.Implementer);
+}
+
+
+
+#define CFG_M 0x80000000 /* next Config implemented */
+
+/* MIPS32 Config0 register */
+#define CFG0_MTMASK 0x00000380
+#define CFG0_MT_TLB (1<<7)
+
+/* MIPS32 Config1 register */
+#define CFG1_MMUSMASK 0x7e000000 /* mmu size - 1 */
+#define CFG1_MMUSSHIFT 25
+#define CFG1_ISMASK 0x01c00000 /* icache lines 64<<n */
+#define CFG1_ISSHIFT 22
+#define CFG1_ILMASK 0x00380000 /* icache line size 2<<n */
+#define CFG1_ILSHIFT 19
+#define CFG1_IAMASK 0x00070000 /* icache ways - 1 */
+#define CFG1_IASHIFT 16
+#define CFG1_DSMASK 0x0000e000 /* dcache lines 64<<n */
+#define CFG1_DSSHIFT 13
+#define CFG1_DLMASK 0x00001c00 /* dcache line size 2<<n */
+#define CFG1_DLSHIFT 10
+#define CFG1_DAMASK 0x00000380 /* dcache ways - 1 */
+#define CFG1_DASHIFT 7
+
+/* MIPS32 Config2 register */
+#define CFG2_TUMASK 0x70000000 /* tertiary cache control */
+#define CFG2_TUSHIFT 28
+#define CFG2_TSMASK 0x0f000000 /* tcache sets per wway 64<<n */
+#define CFG2_TSSHIFT 24
+#define CFG2_TLMASK 0x00f00000 /* tcache line size 2<<n */
+#define CFG2_TLSHIFT 20
+#define CFG2_TAMASK 0x000f0000 /* tcache ways - 1 */
+#define CFG2_TASHIFT 16
+#define CFG2_SUMASK 0x0000f000 /* secondary cache control */
+#define CFG2_SUSHIFT 12
+#define CFG2_SSMASK 0x00000f00 /* scache sets per wway 64<<n */
+#define CFG2_SSSHIFT 8
+#define CFG2_SLMASK 0x000000f0 /* scache line size 2<<n */
+#define CFG2_SLSHIFT 4
+#define CFG2_SAMASK 0x0000000f /* scache ways - 1 */
+#define CFG2_SASHIFT 0
+
+static void
+mdi_probe_cpu (struct mdi_state *mdi, int index)
+{
+ enum mdiTlb tlb;
+ int regsize;
+ unsigned long cfg0 = 0, cfg1 = 0, cfg2 = 0;
+ MDIInt32 mdistat;
+ char data[4];
+ int isa;
+
+ isa = isa2int (mdi->gmdata[index].DeviceData.FISA);
+ if (isa <= 2)
+ {
+ regsize = 4;
+ tlb = R3000_TLB;
+ }
+ else if (isa == 32 || isa == 64)
+ {
+ if (isa == 32)
+ {
+ regsize = 4;
+ tlb = R4000_32TLB;
+ }
+ else
+ {
+ regsize = 8;
+ tlb = R4000_64TLB;
+ }
+ mdi->gmdata[index].ntlb = -1;
+
+ /* Determine TLB size from Config0 and Config1 registers. */
+
+ /* MIPS32 Config0 Register (CP0 Register 16, Select 0). */
+ mdistat = mdi_read (mdi->gmdata[index].DevHandle,
+ MDIMIPCP0, 16, data, 4, 1);
+ cfg0 = (unsigned long) extract_signed_integer (data, 4);
+ if (cfg0 & CFG_M)
+ {
+ /* MIPS32 Config1 Register (CP0 Register 16, Select 1). */
+ mdistat =
+ mdi_read (mdi->gmdata[index].DevHandle,
+ MDIMIPCP0, 16 | (1 << 5), data, 4, 1);
+ if (mdistat == MDISuccess)
+ cfg1 = (unsigned long) extract_signed_integer (data, 4);
+ }
+
+ if (mdistat == MDISuccess && (cfg0 & CFG0_MTMASK) == CFG0_MT_TLB
+ && cfg1 != 0)
+ mdi->gmdata[index].ntlb = ((cfg1 & CFG1_MMUSMASK) >> CFG1_MMUSSHIFT)
+ + 1;
+ }
+ else
+ {
+ regsize = 8;
+ tlb = R4000_64TLB;
+ }
+
+ if (mdi->gmdata[index].ntlb <= 0)
+ tlb = NO_TLB;
+
+ if (index != 0)
+ {
+ if (regsize != mdi->regsize)
+ error (_("\
+Cannot support multiple devices of different register size."));
+ if (tlb != mdi->tlb)
+ error (_("Cannot support multiple devices of different TLB type."));
+ }
+
+ mdi->regsize = regsize;
+ mdi->tlb = tlb;
+
+ if (mdi->gmdata[index].ntlb == 0)
+ {
+ /* Do a binary search to find the number of TLB entries. */
+ int min = 0, max = 256;
+ int half;
+ MDIInt32 mdistat;
+
+ while (max - min > 1)
+ {
+ half = (max - min + 1) >> 1;
+ switch (mdi->tlb)
+ {
+ case R3000_TLB:
+ {
+ MDIUint32 data[2];
+ mdistat = mdi_read (mdi->gmdata[index].DevHandle,
+ MDIMIPTLB, (min + half) * 2, data, 4, 2);
+ }
+ break;
+ case R4000_32TLB:
+ {
+ MDIUint32 data[4];
+ mdistat = mdi_read (mdi->gmdata[index].DevHandle,
+ MDIMIPTLB, (min + half) * 4, data, 4, 4);
+ }
+ break;
+ case R4000_64TLB:
+ {
+ MDIUint64 data[4];
+ mdistat = mdi_read (mdi->gmdata[index].DevHandle,
+ MDIMIPTLB, (min + half) * 4, data, 8, 4);
+ }
+ break;
+ default:
+ mdistat = MDIErrNoResource;
+ break;
+ }
+ if (mdistat == MDISuccess)
+ min += half;
+ else
+ max = min + half;
+ }
+
+ mdi->gmdata[index].ntlb = max;
+ }
+
+ /* Probe cache layout. */
+ if (isa == 32 || isa == 64)
+ {
+ MDICacheInfoT *cache = mdi->gmdata[index].CacheInfo;
+
+ if (cfg1 & CFG_M)
+ {
+ /* MIPS32 Config1 Register (CP0 Register 16, Select 2). */
+ mdistat = mdi_read (mdi->gmdata[index].DevHandle,
+ MDIMIPCP0, 16 | (2 << 5), data, 4, 1);
+ if (mdistat == MDISuccess)
+ cfg2 = (unsigned long) extract_signed_integer (data, 4);
+ }
+
+ if (cfg1 & CFG1_ILMASK)
+ {
+ /* I-cache */
+ cache[0].Type = MDICacheTypeInstruction;
+ cache[0].LineSize = 2 << ((cfg1 & CFG1_ILMASK) >> CFG1_ILSHIFT);
+ cache[0].LinesPerSet = 64 << ((cfg1 & CFG1_ISMASK) >> CFG1_ISSHIFT);
+ cache[0].Sets = 1 + ((cfg1 & CFG1_IAMASK) >> CFG1_IASHIFT);
+ }
+ if (cfg1 & CFG1_DLMASK)
+ {
+ /* D-cache */
+ cache[1].Type = MDICacheTypeData;
+ cache[1].LineSize = 2 << ((cfg1 & CFG1_DLMASK) >> CFG1_DLSHIFT);
+ cache[1].LinesPerSet = 64 << ((cfg1 & CFG1_DSMASK) >> CFG1_DSSHIFT);
+ cache[1].Sets = 1 + ((cfg1 & CFG1_DAMASK) >> CFG1_DASHIFT);
+ }
+ if (cfg2 & CFG2_SLMASK)
+ {
+ /* S-cache */
+ cache[2].Type = MDICacheTypeUnified;
+ cache[2].LineSize = 2 << ((cfg2 & CFG2_SLMASK) >> CFG2_SLSHIFT);
+ cache[2].LinesPerSet = 64 << ((cfg2 & CFG2_SSMASK) >> CFG2_SSSHIFT);
+ cache[2].Sets = 1 + ((cfg2 & CFG2_SAMASK) >> CFG2_SASHIFT);
+ }
+ if (cfg2 & CFG2_TLMASK)
+ {
+ /* T-cache */
+ cache[3].Type = MDICacheTypeUnified;
+ cache[3].LineSize = 2 << ((cfg2 & CFG2_TLMASK) >> CFG2_TLSHIFT);
+ cache[3].LinesPerSet = 64 << ((cfg2 & CFG2_TSMASK) >> CFG2_TSSHIFT);
+ cache[3].Sets = 1 + ((cfg2 & CFG2_TAMASK) >> CFG2_TASHIFT);
+ }
+ }
+ else
+ {
+ /* Ask MDI, but quietly ignore any error. */
+ (void) mdiCacheQuery (mdi->gmdata[index].DevHandle,
+ &mdi->gmdata[index].CacheInfo[0]);
+ }
+}
+
+
+
+static void
+mdi_cleanup (void *arg)
+{
+ struct mdi_state *mdi = arg;
+
+ if (mdi_desc)
+ {
+ mdi_desc = NULL; /* So mdi_close will do nothing. */
+ unpush_target (&mdi_ops);
+ }
+ if (mdi->cfgfile)
+ {
+ if (remote_debug == 0)
+ unlink (mdi->cfgfile);
+ xfree (mdi->cfgfile);
+ }
+ if (mdi->MDIHandle != MDINoHandle)
+ mdiDisconnect (mdi->MDIHandle, MDICurrentState);
+ xfree (mdi);
+
+ if (mdi_logging)
+ {
+ ui_file_delete (mdi_logfp);
+ mdi_logfp = gdb_stdlog;
+ mdi_logging = 0;
+ }
+}
+
+
+static int
+mdi_first_ptid (struct thread_info *tp, void *data)
+{
+ return 1;
+}
+
+static void
+mdi_set_inferior_ptid (void)
+{
+ MDIInt32 mdistat, TCId;
+ struct thread_info *tp;
+
+ inferior_ptid = mdi_ptid;
+ mdi_find_new_threads ();
+ mdistat = mdiGetTC (mdi_desc->gmdata[mdi_desc->gmindex].DevHandle, &TCId);
+ if (mdistat != MDISuccess)
+ {
+ if (mdistat != MDIErrUnsupported)
+ MDIWARN (mdistat, _("getting current thread"));
+ }
+ else
+ {
+ inferior_ptid =
+ ptid_build (GET_PID (inferior_ptid),
+ mdi_desc->gmdata[mdi_desc->gmindex].DevHandle, TCId);
+ if (!in_thread_list (inferior_ptid))
+ {
+ tp = iterate_over_threads (mdi_first_ptid, NULL);
+ if (tp)
+ {
+ inferior_ptid = tp->ptid;
+ mdi_switch_to_thread ();
+ }
+ }
+ }
+ last_ptid = inferior_ptid;
+}
+
+/* The open routine takes the rest of the parameters from the command,
+ and (if successful) pushes a new target onto the stack. Targets
+ should supply this routine, if only to provide an error message.
+ Called when selecting the simulator. EG: (gdb) target mdi name. */
+
+static void
+mdi_open (char *args, int from_tty)
+{
+ struct mdi_tm_data_list *tmdatalist = NULL, **listp = &tmdatalist;
+ int group_mode = 0, team_mode = 0;
+ struct cleanup *cleanups;
+ int len;
+ char *arg_buf;
+ char **argv;
+ MDIInt32 mdistat;
+ struct mdi_state *mdi;
+ char *lib = 0;
+ char *configfile = 0;
+ unsigned long device, target;
+ int byte_order;
+ int connreset;
+ int i, j;
+
+ if (remote_debug && mdi_logfile)
+ {
+ mdi_logfp = gdb_fopen (mdi_logfile, "w");
+ if (mdi_logfp == NULL)
+ perror_with_name (mdi_logfile);
+ else
+ mdi_logging = 1;
+ }
+
+ if (mdi_logfp == NULL)
+ mdi_logfp = gdb_stdlog;
+
+ if (remote_debug)
+ fprintf_unfiltered (mdi_logfp, "mdi_open: args \"%s\"\n",
+ args ? args : "(null)");
+
+ device = mdi_device;
+ target = mdi_target;
+ connreset = mdi_connectreset;
+
+ if (args)
+ {
+ int seendev = 0;
+ char *argscopy, *p;
+
+ argscopy = alloca (strlen (args) + 1);
+ strcpy (argscopy, args);
+ for (p = strtok (argscopy, " \t,{}"); p; p = strtok (NULL, " \t,{}"))
+ {
+ if (isdigit (*p))
+ {
+ if (seendev)
+ error (_("Multiple MDI device numbers specified."));
+ device = strtoul (p, &p, 0);
+ if (*p == ':' && isdigit (p[1]))
+ {
+ target = device;
+ device = strtoul (p + 1, &p, 0);
+ }
+ if (*p)
+ error (_("Bad [TARGET:]DEVICE number."));
+ seendev = 1;
+ }
+ else if (strncmp (p, "cfg=", sizeof "cfg=" - 1) == 0)
+ {
+ if (configfile)
+ error (_("Multiple MIPSsim config files specified."));
+ p += sizeof "cfg=" - 1;
+ if (*p)
+ configfile = p;
+ }
+ else if (strncmp (p, "group=", sizeof "group=" - 1) == 0)
+ {
+ unsigned long tm_device, tm_target;
+
+ if (team_mode)
+ error (_("Cannot mix group= and team= options."));
+
+ group_mode = 1;
+ p += sizeof "group=" - 1;
+ if (isdigit (*p))
+ {
+ tm_target = mdi_target;
+ tm_device = strtoul (p, &p, 0);
+ if (*p == ':' && isdigit (p[1]))
+ {
+ tm_target = tm_device;
+ tm_device = strtoul (p + 1, &p, 0);
+ }
+ if (*p)
+ error (_("Bad [TARGET:]DEVICE number."));
+
+ *listp = alloca (sizeof (**listp));
+ (*listp)->next = NULL;
+ (*listp)->tmdata.TGId = tm_target - 1;
+ (*listp)->tmdata.DevId = tm_device - 1;
+ listp = &(*listp)->next;
+ }
+ else
+ error (_("Bad group= option."));
+ }
+ else if (strncmp (p, "rst=", sizeof "rst=" - 1) == 0)
+ {
+ p += sizeof "rst=" - 1;
+ if (strcasecmp (p, "off") == 0)
+ connreset = -1;
+ else if (strcasecmp (p, "on") == 0)
+ connreset = 0;
+ else
+ {
+ connreset = strtol (p, &p, 0);
+ if (*p)
+ error (_("Bad rst= option."));
+ }
+ }
+ else if (strncmp (p, "team=", sizeof "team=" - 1) == 0)
+ {
+ unsigned long tm_device, tm_target;
+
+ if (group_mode)
+ error (_("Cannot mix team= and group= options."));
+
+ team_mode = 1;
+ p += sizeof "team=" - 1;
+ if (isdigit (*p))
+ {
+ tm_target = mdi_target;
+ tm_device = strtoul (p, &p, 0);
+ if (*p == ':' && isdigit (p[1]))
+ {
+ tm_target = tm_device;
+ tm_device = strtoul (p + 1, &p, 0);
+ }
+ if (*p)
+ error (_("Bad [TARGET:]DEVICE number."));
+
+ *listp = alloca (sizeof (**listp));
+ (*listp)->next = NULL;
+ (*listp)->tmdata.TGId = tm_target - 1;
+ (*listp)->tmdata.DevId = tm_device - 1;
+ listp = &(*listp)->next;
+ }
+ else
+ error (_("Bad team= option."));
+ }
+ else if (*p)
+ {
+ if (lib)
+ error (_("Multiple MDI libraries specified."));
+ lib = p;
+ }
+ }
+ }
+
+ if (!lib)
+ lib = mdi_library;
+
+ if (!configfile)
+ configfile = mdi_configfile;
+
+ /* Reread files if they've changed. */
+ reopen_exec_file ();
+ reread_symbols ();
+
+ target_preopen (from_tty);
+
+ unpush_target (&mdi_ops);
+
+ mdi = (struct mdi_state *) xmalloc (sizeof (struct mdi_state));
+ memset (mdi, 0, sizeof (struct mdi_state));
+ mdi->MDIHandle = MDINoHandle;
+
+ /* Failed coprocessor register masks. */
+ memset (mdi_cpdreg_miss, 0, sizeof (mdi_cpdreg_miss));
+ memset (mdi_cpcreg_miss, 0, sizeof (mdi_cpcreg_miss));
+ memset (mdi_cpdreg_wp, 0, sizeof (mdi_cpdreg_wp));
+ memset (mdi_cpcreg_wp, 0, sizeof (mdi_cpcreg_wp));
+ mdi_hilo_miss = 0;
+ mdi_dsp_miss = 0;
+
+ /* To avoid confusion, don't access the well known CP0 regs directly. */
+ mdi_cpdreg_miss[0][0] |= ((1 << 12) /* Status */
+ | (1 << 8) /* BadVaddr */
+ | (1 << 13)); /* Cause */
+
+ /* Availability of MDIMIPFPR resource is unknown. */
+ mdi_fpr_avail = -1;
+
+ /* Availability of MDIHwBpQuery call is unknown. */
+ mdi_hwbpq_avail = -1;
+
+ cleanups = make_cleanup (mdi_cleanup, mdi);
+
+ /* Connect to MDI library. */
+ mdi_dlopen (lib, mdi, from_tty);
+
+ /* Create a team if requested. */
+ if (tmdatalist)
+ {
+ struct mdi_tm_data_list tmdatathis;
+
+ /* Add the device to be opened too. */
+ tmdatathis.next = tmdatalist;
+ tmdatathis.tmdata.TGId = target - 1;
+ tmdatathis.tmdata.DevId = device - 1;
+ tmdatalist = &tmdatathis;
+
+ if (mdi_team <= 0 || group_mode)
+ {
+ mdistat = mdiTeamCreate (mdi->MDIHandle, &mdi_team);
+ if (mdistat != MDISuccess)
+ {
+ mdi_team = 0;
+ if (group_mode && mdistat != MDIErrUnsupported)
+ mdi_team_status (mdistat);
+ else
+ MDIWARN (mdistat, _("creating team"));
+ }
+ mdi_team += 1;
+ }
+
+ if (group_mode)
+ mdi->gid = mdi_team - 1;
+
+ for (listp = &tmdatalist; *listp; listp = &(*listp)->next)
+ {
+ (*listp)->tmdata.MDIHandle = mdi->MDIHandle;
+ mdistat = mdiTMAttach (mdi->MDIHandle, mdi_team - 1,
+ &(*listp)->tmdata);
+
+ if (group_mode && mdistat != MDIErrUnsupported)
+ mdi_tm_status (mdistat, (*listp)->tmdata.TGId + 1,
+ (*listp)->tmdata.DevId + 1);
+ else
+ MDIWARN (mdistat, _("adding team member"));
+ if (group_mode || !mdi->gmcount)
+ mdi->gmdata[mdi->gmcount++].tmdata = (*listp)->tmdata;
+ }
+ }
+ else
+ {
+ mdi->gmdata[mdi->gmcount].tmdata.MDIHandle = mdi->MDIHandle;
+ mdi->gmdata[mdi->gmcount].tmdata.TGId = target - 1;
+ mdi->gmdata[mdi->gmcount].tmdata.DevId = device - 1;
+ mdi->gmcount++;
+ }
+
+ for (i = 0; i < mdi->gmcount; i++)
+ {
+ /* Reuse the target group handle if possible. */
+ mdi->gmdata[i].TGHandle = MDINoHandle;
+ for (j = 0; j < i; j++)
+ if (mdi->gmdata[i].tmdata.TGId == mdi->gmdata[j].tmdata.TGId)
+ mdi->gmdata[i].TGHandle = mdi->gmdata[j].TGHandle;
+
+ /* Connect to target group. */
+ if (mdi->gmdata[i