dbgutil.c
来自「开放源码的编译器open watcom 1.6.0版的源代码」· C语言 代码 · 共 678 行 · 第 1/2 页
C
678 行
/****************************************************************************
*
* Open Watcom Project
*
* Portions Copyright (c) 1983-2002 Sybase, Inc. All Rights Reserved.
*
* ========================================================================
*
* This file contains Original Code and/or Modifications of Original
* Code as defined in and that are subject to the Sybase Open Watcom
* Public License version 1.0 (the 'License'). You may not use this file
* except in compliance with the License. BY USING THIS FILE YOU AGREE TO
* ALL TERMS AND CONDITIONS OF THE LICENSE. A copy of the License is
* provided with the Original Code and Modifications, and is also
* available at www.sybase.com/developer/opensource.
*
* The Original Code and all software distributed under the License are
* distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
* EXPRESS OR IMPLIED, AND SYBASE AND ALL CONTRIBUTORS HEREBY DISCLAIM
* ALL SUCH WARRANTIES, INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF
* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE, QUIET ENJOYMENT OR
* NON-INFRINGEMENT. Please see the License for the specific language
* governing rights and limitations under the License.
*
* ========================================================================
*
* Description: Debugger utility routines.
*
****************************************************************************/
#include "dbgdefn.h"
#include "dbglit.h"
#include "dbginfo.h"
#include "dbgerr.h"
#include "dbgmem.h"
#include "dbgtoggl.h"
#include "dbginp.h"
#include "dbgreg.h"
#include "dbgitem.h"
#include "dbgio.h"
#include "trpcore.h"
#include "ldsupp.h"
#include "mad.h"
#include "dui.h"
#include <ctype.h>
#include <string.h>
#include <float.h>
#include <limits.h>
extern char *NameBuff;
extern unsigned char CurrRadix;
extern input_stack *InpStack;
extern char *Language;
extern char *TxtBuff;
extern system_config SysConfig;
extern unsigned char CurrRadix;
extern mod_handle CodeAddrMod;
extern machine_state *DbgRegs;
extern unsigned CueFile( cue_handle *ch, char *file, unsigned max );
extern unsigned long CueLine( cue_handle *ch );
extern char *StrCopy( char *, char * );
extern char *ReScan( char * );
extern char *ScanPos( void );
extern void NewLang( char * );
extern char *AddHexSpec( char * );
extern char *DupStr( char * );
extern void AddrFloat( address * );
extern void AddrFix( address * );
extern address GetCodeDot( void );
extern void GetMADTypeDefaultAt( address, mad_type_kind, mad_type_info * );
extern unsigned NewCurrRadix( unsigned );
extern image_entry *ImageEntry( mod_handle mh );
extern image_entry *ImagePrimary( void );
unsigned DefaultSize( default_kind dk )
{
type_info info;
mad_type_info mti;
if( ModDefault( CodeAddrMod, dk, &info ) != 0 ) {
info.kind = TK_NONE;
info.size = 0;
}
mti.b.kind = MTK_BASIC;
if( info.size == 0 ) {
GetMADTypeDefaultAt( GetCodeDot(),
(dk==DK_INT) ? MTK_INTEGER : MTK_ADDRESS, &mti );
info.size = mti.b.bits / BITS_PER_BYTE;
if( mti.b.kind == MTK_ADDRESS ) {
info.size -= (mti.a.seg.bits / BITS_PER_BYTE);
}
}
if( info.kind == TK_POINTER && info.modifier == TM_FAR ) {
if( mti.b.kind == MTK_BASIC ) {
/* haven't gotten the info yet */
GetMADTypeDefaultAt( GetCodeDot(), MTK_ADDRESS, &mti );
}
info.size -= (mti.a.seg.bits / BITS_PER_BYTE);
}
return( info.size );
}
static char *DoMadLongConv( char *p, unsigned long value, int radix, int size )
{
unsigned max = 50;
unsigned old;
mad_type_info mti;
old = NewCurrRadix( radix );
MADTypeInfoForHost( MTK_INTEGER, size, &mti );
MADTypeToString( radix, &mti, &value, &max, p );
NewCurrRadix( old );
return( p + max );
}
char *CnvULongHex( unsigned long value, char *p )
{
return( DoMadLongConv( p, value, 16, sizeof( value ) ) );
}
char *CnvLongDec( long value, char *p )
{
return( DoMadLongConv( p, value, 10, -(int)sizeof( value ) ) );
}
char *CnvULongDec( unsigned long value, char *p )
{
return( DoMadLongConv( p, value, 10, sizeof( value ) ) );
}
char *CnvLong( long value, char *p )
{
return( DoMadLongConv( p, value, CurrRadix, -(int)sizeof( value ) ) );
}
char *CnvULong( unsigned long value, char *p )
{
return( DoMadLongConv( p, value, CurrRadix, sizeof( value ) ) );
}
#ifdef DEAD_CODE
void CnvAddrToItem( address *a, item_mach *item, mad_type_info *mti )
{
//MAD: a bit ugly
AddrFix( a );
switch( mti->b.bits - mti->a.seg.bits ) {
case 16:
item->sa.offset = a->mach.offset;
item->sa.segment = a->mach.segment;
break;
case 32:
item->la.offset = a->mach.offset;
item->la.segment = a->mach.segment;
break;
}
}
#endif
char *AddrTypeToString( address *a, mad_type_handle th, char *p, unsigned max )
{
mad_type_info mti;
unsigned mad_max = max;
item_mach item;
mad_type_info host;
MADTypeInfo( th, &mti );
MADTypeInfoForHost( MTK_ADDRESS, sizeof( address ), &host );
AddrFix( a );
MADTypeConvert( &host, a, &mti, &item, 0 );
MADTypeToString( 16, &mti, &item, &mad_max, p );
return( p+mad_max );
}
char *AddrToIOString( address *a, char *p, unsigned max )
{
return( AddrTypeToString( a,
MADTypeDefault( MAS_IO | MTK_ADDRESS, MAF_FULL, &DbgRegs->mr, a ),
p, max ) );
}
char *AddrToString( address *a, mad_address_format af, char *p, unsigned max )
{
return( AddrTypeToString( a,
MADTypeDefault( MTK_ADDRESS, af, &DbgRegs->mr, a ),
p, max ) );
}
unsigned QualifiedSymName( sym_handle *sh, char *name, unsigned max, bool uniq )
{
mod_handle mod;
unsigned name_len;
unsigned len,rc;
sym_info sinfo;
SymInfo( sh, NULL, &sinfo );
if( sinfo.global ) {
len = 0;
} else {
mod = SymMod( sh );
name_len = ModName( mod, name, max );
if( name_len < max ) {
if( name != NULL ) {
name += name_len;
*name++ = '@';
max -= name_len + 1;
}
}
len = name_len + 1;
}
if( uniq && SymName( sh, NULL, SN_DEMANGLED, NULL, 0 ) != 0 ) {
if( name != NULL ) {
*name++ = '`';
max--;
}
len++;
name_len = SymName( sh, NULL, SN_OBJECT, name, max );
len += name_len;
if( name != NULL ) {
name += name_len;
*name++ = '`';
*name = '\0';
max -= name_len + 1;
}
len++;
} else {
rc = SymName( sh, NULL, SN_SCOPED, name, max );
if( rc == 0 ) {
rc = SymName( sh, NULL, SN_SOURCE, name, max );
}
len += rc;
}
return( len );
}
/*
* CnvAddr -- address to string convertion gut routine
*/
char *CnvAddr( address addr, cnvaddr_option cao, bool uniq,
char *p, unsigned max )
{
char off_buff[40];
unsigned str_width, name_width, off_width;
addr_off sym_offset;
search_result sr;
location_list ll;
DIPHDL( sym, sym );
off_width = 0;
AddrFloat( &addr );
sr = DeAliasAddrSym( NO_MOD, addr, sym );
switch( sr ) {
case SR_NONE:
return( NULL );
case SR_CLOSEST:
if( cao == CAO_NO_PLUS ) return( NULL );
SymLocation( sym, NULL, &ll );
sym_offset = addr.mach.offset - ll.e[0].u.addr.mach.offset;
if( cao == CAO_NORMAL_PLUS ) {
off_width = CnvULongHex( sym_offset, AddHexSpec( off_buff ) ) - off_buff + 1;
}
break;
case SR_EXACT:
break;
}
name_width = QualifiedSymName( sym, NULL, 0, uniq );
str_width = name_width + off_width;
if( max == 0 ) max = str_width;
if( str_width > max ) { /* won't fit */
if( off_width != 0 ) return( NULL );
QualifiedSymName( sym, p, max - 1, uniq );
p += max - 1;
*p++ = '>';
*p = NULLCHAR;
return( p );
}
QualifiedSymName( sym, p, name_width + 1, uniq );
p += name_width;
if( off_width != 0 ) {
--off_width;
*p++ = '+';
memcpy( p, off_buff, off_width );
p += off_width;
*p = NULLCHAR;
}
return( p );
}
char *CnvNearestAddr( address addr, char *buff, unsigned max )
{
char *p;
p = CnvAddr( addr, CAO_OMIT_PLUS, FALSE, buff, max );
if( p == NULL ) {
p = AddrToString( &addr, MAF_FULL, buff, max );
}
return( p );
}
/*
* StrAddr --
*/
char *StrAddr( address *addr, char *buff, unsigned max )
{
char *p;
p = CnvAddr( *addr, CAO_NORMAL_PLUS, FALSE, buff, max );
if( p == NULL ) {
p = AddrToString( addr, MAF_FULL, buff, max );
}
return( p );
}
char *UniqStrAddr( address *addr, char *buff, unsigned max )
{
char *p;
p = CnvAddr( *addr, CAO_NORMAL_PLUS, TRUE, buff, max );
if( p == NULL ) {
p = AddrToString( addr, MAF_FULL, buff, max );
}
return( p );
}
/*
* LineAddr
*/
char *LineAddr( address *addr, char *buff )
{
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?