plsacc.c
来自「开放源码的编译器open watcom 1.6.0版的源代码」· C语言 代码 · 共 1,153 行 · 第 1/2 页
C
1,153 行
}
//OBSOLETE - use ReqWrite_regs
unsigned ReqWrite_fpu()
{
_DBG(("AccWriteFPU\r\n"));
TaskFPExec( (ULONG)&Write387, GetInPtr(sizeof(write_fpu_req)) );
_DBG(("exit AccWriteFPU\r\n"));
return( 0 );
}
unsigned ReqRead_regs( void )
{
mad_registers *mr;
mr = GetOutPtr(0);
ReadCPU( &mr->x86.cpu );
TaskFPExec( (ULONG)&Read387, &mr->x86.fpu );
return( sizeof( mr->x86 ) );
}
unsigned ReqWrite_regs( void )
{
mad_registers *mr;
mr = GetInPtr(sizeof(write_regs_req));
WriteCPU( &mr->x86.cpu );
TaskFPExec( (ULONG)&Write387, &mr->x86.fpu );
return( 0 );
}
static int map_dbe( int err )
{
if( err == 0 ) return( err );
return( -err + DBE_BASE );
}
static void CheckForPE( char *name )
{
int handle;
unsigned_32 off;
unsigned i;
pe_object obj;
union {
dos_exe_header dos;
pe_header pe;
} head;
handle = open( name, O_BINARY | O_RDONLY, 0 );
if( handle == -1 ) return;
read( handle, &head.dos, sizeof( head.dos ) );
if( head.dos.signature != DOS_SIGNATURE ) {
close( handle );
return;
}
lseek( handle, OS2_NE_OFFSET, SEEK_SET );
read( handle, &off, sizeof( off ) );
lseek( handle, off, SEEK_SET );
read( handle, &head.pe, sizeof( head.pe ) );
switch( head.pe.signature ) {
case PE_SIGNATURE:
case PL_SIGNATURE:
for( i = 0; i < head.pe.num_objects; ++i ) {
read( handle, &obj, sizeof( obj ) );
ObjOffReloc[i] = Mach.msb_eip - head.pe.entry_rva + obj.rva;
}
break;
}
close( handle );
}
unsigned ReqProg_load()
{
char ch;
char *src;
char *dst;
char *name;
prog_load_ret *ret;
unsigned len;
_DBG(("AccLoadProg\r\n"));
memset( ObjOffReloc, 0, sizeof( ObjOffReloc ) );
AtEnd = FALSE;
ReportedAlias = FALSE;
dst = UtilBuff + 1;
name = GetInPtr( sizeof( prog_load_req ) );
src = name;
ret = GetOutPtr( 0 );
while( *src != '\0' ) ++src;
++src;
len = GetTotalSize() - (src - name) - sizeof( prog_load_req );
for( ;; ) {
if( len == 0 ) break;
ch = *src;
if( ch == '\0' ) ch = ' ';
*dst = ch;
++src;
++dst;
--len;
}
if( dst > UtilBuff ) --dst;
*dst = '\r';
UtilBuff[ 0 ] = dst - (UtilBuff + 1);
ret->err = map_dbe( dbg_load( name, NULL, UtilBuff ) );
if( ret->err == 0 ) {
HavePSP = TRUE;
}
FakeBreak = 1;
// _dil_global._action_flags |= ACT_DIS387;
FakeBreak = 0;
dbg_rdmsb( &Mach );
if( Mach.msb_protmf ) {
//loadret->flags = LD_FLAG_IS_32 | LD_FLAG_IS_FLAT | LD_FLAG_IS_PROT;
_DBG(("LD_FLAG_IS_PROT!!!\r\n"));
ret->flags = LD_FLAG_IS_32 | LD_FLAG_IS_PROT;
ret->task_id = 4;
CheckForPE( name );
} else {
_DBG(("Not Protected mode?!!!\r\n"));
ret->flags = LD_FLAG_IS_32;
ret->task_id = Mach.msb_ds;
}
ret->mod_handle = 0;
InitialSS = Mach.msb_ss;
InitialCS = Mach.msb_cs;
Mach.msb_event = -1;
return( sizeof( *ret ) );
}
#pragma aux finit = ".387" "finit" "wait"
extern void finit( void );
unsigned ReqProg_kill()
{
prog_kill_ret *ret;
_DBG(("AccKillProg\r\n"));
ret = GetOutPtr( 0 );
SaveStdIn = NIL_DOS_HANDLE;
SaveStdOut = NIL_DOS_HANDLE;
AtEnd = TRUE;
if( RealNPXType != X86_NO ) {
/* mask ALL floating point exception bits */
finit();
Mach.msb_87ctrl = 0x37f;
dbg_wrmsb( &Mach );
}
SetMSW( SaveMSW );
dbg_kill();
HavePSP = FALSE;
ret->err = 0;
Mach.msb_event = -1;
return( sizeof( *ret ) );
}
int MapReturn()
{
switch( Mach.msb_event )
{
case 1:
if( Mach.msb_dreg[ 6 ] & DR6_BS ) {
return( COND_TRACE );
} else if( Mach.msb_dreg[ 6 ] & ( DR6_B0+DR6_B1+DR6_B2+DR6_B3 ) ) {
return( COND_WATCH );
} else {
return( COND_EXCEPTION );
}
case 3:
Mach.msb_eip--;
return( COND_BREAK );
case 32:
case 33:
AtEnd = TRUE;
return( COND_TERMINATE );
case 34: /* new linear base address */
return( 0 );
default:
return( COND_EXCEPTION );
}
}
static void FixFakeBreak()
{
PTR386 addr;
addr.selector = Mach.msb_cs;
addr.offset = Mach.msb_eip;
ReadWrite( WriteMemory, &addr, (char *)&SavedByte, 1 );
}
static int Execute()
{
int err;
int trap;
if( !GrabVects() ) return( COND_EXCEPTION );
err = RunProgram();
if( err != 0 ) {
AtEnd = TRUE;
return( COND_EXCEPTION );
}
if( dbg_rdmsb( &Mach ) != 0 ) {
AtEnd = TRUE;
return( COND_EXCEPTION );
}
ReleVects();
trap = MapReturn();
if( FakeBreak ) {
FixFakeBreak();
FakeBreak = FALSE;
if( !AtEnd ) trap = COND_USER;
}
if( AtEnd ) return( COND_TERMINATE );
return( trap );
}
unsigned ReqSet_watch()
{
dword l;
watch *curr;
set_watch_req *acc;
set_watch_ret *ret;
int i,needed;
ULONG linear;
_DBG(("AccSetWatch\r\n"));
acc = GetInPtr( 0 );
ret = GetOutPtr( 0 );
ret->err = 1;
ret->multiplier = 10000;
if( WatchCount < MAX_WP ) {
ret->err = 0;
ReadMemory( &acc->watch_addr, 4UL, &l );
curr = WatchPoints + WatchCount;
curr->addr.segment = acc->watch_addr.segment;
curr->addr.offset = acc->watch_addr.offset;
curr->value = l;
dbg_ptolin( &acc->watch_addr, &linear );
curr->linear = linear;
curr->len = acc->size;
curr->linear &= ~(curr->len-1);
curr->dregs = ( linear & (curr->len-1) ) ? 2 : 1;
++WatchCount;
needed = 0;
for( i = 0; i < WatchCount; ++i ) {
needed += WatchPoints[ i ].dregs;
}
if( needed <= 4 ) ret->multiplier |= USING_DEBUG_REG;
}
return( sizeof( *ret ) );
}
unsigned ReqClear_watch()
{
WatchCount = 0;
return( 0 );
}
unsigned ReqSet_break()
{
byte ch;
set_break_req *acc;
set_break_ret *ret;
_DBG(("AccSetBreak\r\n"));
acc = GetInPtr( 0 );
ret = GetOutPtr( 0 );
ReadMemory( &acc->break_addr, 1UL, &ch );
ret->old = ch;
ch = 0xCC;
WriteMemory( &acc->break_addr, 1UL, &ch );
return( sizeof( *ret ) );
}
unsigned ReqClear_break()
{
byte ch;
clear_break_req *acc;
_DBG(("AccRestoreBreak\r\n"));
acc = GetInPtr( 0 );
ch = acc->old;
WriteMemory( &acc->break_addr, 1UL, &ch );
return( 0 );
}
static void SetDRnBW( int dr, ULONG linear, int len ) /* Set DRn for break on write */
{
Mach.msb_dreg[ dr ] = linear;
Mach.msb_dreg[ 7 ] |= ( (DRLen( len )+DR7_BWR) << DR7_RWLSHIFT( dr ) )
| ( DR7_GEMASK << DR7_GLSHIFT( dr ) );
}
static bool SetDebugRegs()
{
int needed;
int i;
int dr;
watch *wp;
needed = 0;
for( i = WatchCount, wp = WatchPoints; i != 0; --i, ++wp ) {
needed += wp->dregs;
}
if( needed > 4 ) return( FALSE );
dr = 0;
Mach.msb_dreg[ 7 ] = DR7_GE;
for( i = WatchCount, wp = WatchPoints; i != 0; --i, ++wp ) {
SetDRnBW( dr, wp->linear, wp->len );
++dr;
if( wp->dregs == 2 ) {
SetDRnBW( dr, wp->linear+wp->len, wp->len );
++dr;
}
}
return( TRUE );
}
static unsigned ProgRun( bool step )
{
watch *wp;
int i;
dword value;
prog_go_ret *ret;
ret = GetOutPtr( 0 );
Mach.msb_dreg[ 6 ] = 0;
Mach.msb_dreg[ 7 ] = 0;
if( AtEnd ) {
ret->conditions = COND_TERMINATE;
} else if( step ) {
Mach.msb_eflags |= EF_TF;
ret->conditions = Execute();
Mach.msb_eflags &= ~EF_TF;
} else if( WatchCount != 0 ) {
if( SetDebugRegs() ) {
ret->conditions = Execute();
Mach.msb_dreg[ 6 ] = 0;
Mach.msb_dreg[ 7 ] = 0;
} else {
for( ;; ) {
Mach.msb_eflags |= EF_TF;
ret->conditions = Execute();
if( ret->conditions & COND_TERMINATE ) break;
if( Mach.msb_event != 1 ) break;
if( !( Mach.msb_dreg[6] & DR6_BS ) ) break;
for( wp = WatchPoints, i = WatchCount; i > 0; ++wp, --i ) {
ReadMemory( &wp->addr, 4UL, &value );
if( value != wp->value ) {
ret->conditions = COND_WATCH;
Mach.msb_eflags &= ~EF_TF;
goto leave;
}
}
}
}
} else {
ret->conditions = Execute();
}
leave:
ret->conditions |= COND_CONFIG;
ret->program_counter.offset = Mach.msb_eip;
ret->program_counter.segment = Mach.msb_cs;
ret->stack_pointer.offset = Mach.msb_esp;
ret->stack_pointer.segment = Mach.msb_ss;
WatchCount = 0;
return( sizeof( *ret ) );
}
unsigned ReqProg_go()
{
_DBG(("AccProgGo\r\n"));
return( ProgRun( FALSE ) );
}
unsigned ReqProg_step()
{
_DBG(("AccProgStep\r\n"));
return( ProgRun( TRUE ) );
}
unsigned ReqGet_next_alias()
{
get_next_alias_ret *ret;
_DBG(("AccGetNextAlias\r\n"));
ret = GetOutPtr( 0 );
if( !ReportedAlias ) {
_DBG(("acc->seg == 0\r\n"));
ret->seg = Mach.msb_cs;
ret->alias = Mach.msb_ds;
ReportedAlias = TRUE;
} else {
_DBG(("acc->seg == other\r\n"));
ret->seg = 0;
ret->alias = 0;
}
return( sizeof( *ret ) );
}
static unsigned Redirect( bool input )
{
int std_hndl;
int *var;
int handle;
char *name;
redirect_stdout_ret *ret;
ret = GetOutPtr( 0 );
if( !HavePSP ) {
ret->err = 1;
return( sizeof( *ret ) );
}
SetPSP( _dil_global._chpsp );
name = GetInPtr( sizeof( redirect_stdout_req ) );
ret->err = 0;
if( input ) {
std_hndl = 0;
var = &SaveStdIn;
} else {
std_hndl = 1;
var = &SaveStdOut;
}
if( *name == '\0' ) {
if( *var != NIL_DOS_HANDLE ) {
if( dup2( *var, std_hndl ) == -1 ) {
ret->err = 1;
} else {
close( *var );
*var = NIL_DOS_HANDLE;
}
}
} else {
if( *var == NIL_DOS_HANDLE ) {
*var = dup( std_hndl );
}
if( input ) {
handle = open( name, O_BINARY | O_RDWR, 0 );
} else {
handle = open( name, O_BINARY | O_RDWR | O_TRUNC | O_CREAT, 0 );
}
if( handle == -1 ) {
ret->err = 1;
} else {
dup2( handle, std_hndl );
close( handle );
}
}
SetPSP( _dil_global._psp );
return( sizeof( *ret ) );
}
unsigned ReqRedirect_stdin()
{
_DBG(("AccRedirectStdin\r\n"));
return( Redirect( TRUE ) );
}
unsigned ReqRedirect_stdout()
{
_DBG(("AccRedirectStdOut\r\n"));
return( Redirect( FALSE ) );
}
unsigned ReqGet_err_text()
{
static char *DosErrMsgs[] = {
#include "dosmsgs.h"
};
int err;
get_err_text_req *acc;
char *err_txt;
#define MAX_CODE (sizeof( DosErrMsgs ) / sizeof( char * ) - 1)
_DBG(("AccErrText\r\n"));
acc = GetInPtr( 0 );
err_txt = GetOutPtr( 0 );
if( acc->err > MAX_CODE ) {
err = acc->err - DBE_BASE;
strcpy( err_txt, DBG_ERROR );
err_txt += sizeof( DBG_ERROR ) - 1;
if( err < -DBE_MIN && err > -DBE_MAX ) {
strcpy( err_txt, DBErrors[ err ] );
} else {
utoa( acc->err, (char *)err_txt, 16 );
}
} else {
strcpy( err_txt, DosErrMsgs[ acc->err ] );
}
return( strlen( GetOutPtr( 0 ) ) + 1 );
}
unsigned ReqGet_message_text()
{
get_message_text_ret *ret;
char *err_txt;
ret = GetOutPtr( 0 );
err_txt = GetOutPtr( sizeof(*ret) );
if( Mach.msb_event == (USHORT)-1 ) {
err_txt[0] = '\0';
} else {
ExceptionText( Mach.msb_event, err_txt );
Mach.msb_event = -1;
}
ret->flags = MSG_NEWLINE | MSG_ERROR;
return( sizeof( *ret ) + strlen( err_txt ) + 1 );
}
unsigned ReqGet_lib_name()
{
char *ch;
get_lib_name_ret *ret;
ret = GetOutPtr( 0 );
ret->handle = 0;
ch = GetOutPtr( sizeof( *ret ) );
*ch = '\0';
return( sizeof( *ret ) + 1 );
}
trap_version TRAPENTRY TrapInit( char *parm, char *err, bool remote )
{
trap_version ver;
int error_num;
_DBG(( "in TrapInit\r\n" ));
remote = remote; parm = parm;
err[0] = '\0'; /* all ok */
ver.major = TRAP_MAJOR_VERSION;
ver.minor = TRAP_MINOR_VERSION;
ver.remote = FALSE;
//ver.is_32 = TRUE;
SaveStdIn = NIL_DOS_HANDLE;
SaveStdOut = NIL_DOS_HANDLE;
SaveMSW = GetMSW();
RealNPXType = NPXType();
_8087 = 0;
HavePSP = FALSE;
WatchCount = 0;
FakeBreak = FALSE;
if( getenv( "DBDB" ) ) {
_DBG(( "Calling dbg_edebug()\r\n" ));
dbg_edebug();
}
_DBG(( "about to dbg_init\r\n" ));
error_num = dbg_init( &SelBlk );
_DBG(( "back from dbg_init\r\n" ));
GrabPrtScrn();
if( error_num != 0 ) {
strcpy( err, DBG_ERROR );
strcpy( err + sizeof( DBG_ERROR )-1, DBErrors[ -error_num ] );
}
Mach.msb_event = -1;
_DBG(( "outof TrapInit\r\n" ));
return( ver );
}
void TRAPENTRY TrapFini()
{
RelePrtScrn();
dbg_exit();
}
⌨️ 快捷键说明
复制代码Ctrl + C
搜索代码Ctrl + F
全屏模式F11
增大字号Ctrl + =
减小字号Ctrl + -
显示快捷键?