mad_status MADIMPENTRY( UnexpectedBreak )( mad_registers *mr, char *buff, size_t *buff_size_p ) { address a; union { byte b[9]; addr32_ptr a32; addr48_ptr a48; } data; size_t buff_size; size_t len; buff_size = *buff_size_p; *buff_size_p = 0; if( buff_size > 0 ) buff[0] = '\0'; a = GetRegIP( mr ); memset( &data, 0, sizeof( data ) ); MCReadMem( a, sizeof( data.b ), data.b ); if( data.b[0] != BRK_POINT ) return( MS_FAIL ); mr->x86.cpu.eip += 1; if( data.b[1] != JMP_SHORT ) return( MS_OK ); if( memcmp( data.b + 3, "WVIDEO", 6 ) != 0 ) return( MS_OK ); a = GetRegSP( mr ); MCReadMem( a, sizeof( addr_ptr ), &data ); if( BIG_SEG( a ) ) { a.mach = data.a48; } else { ConvAddr32ToAddr48( data.a32, a.mach ); } len = 0; while( MCReadMem( a, sizeof( data.b[0] ), data.b ) != 0 ) { a.mach.offset++; if( len + 1 < buff_size ) buff[len] = data.b[0]; if( data.b[0] == '\0' ) break; ++len; } *buff_size_p = len; if( buff_size > 0 ) { --buff_size; if( buff_size > len ) buff_size = len; buff[buff_size] = '\0'; } return( MS_OK ); }
mad_status DIGENTRY MIUnexpectedBreak( mad_registers *mr, unsigned *maxp, char *buff ) { address a; union { byte b[9]; addr32_ptr a32; addr48_ptr a48; } data; unsigned max; unsigned len; max = *maxp; *maxp = 0; if( max > 0 ) buff[0] = '\0'; a = GetRegIP( mr ); memset( &data, 0, sizeof( data ) ); MCReadMem( a, sizeof( data.b ), &data ); if( data.b[0] != BRK_POINT ) return( MS_FAIL ); mr->x86.cpu.eip += 1; if( data.b[1] != JMP_SHORT ) return( MS_OK ); if( memcmp( &data.b[3], "WVIDEO", 6 ) != 0 ) return( MS_OK ); a = GetRegSP( mr ); MCReadMem( a, sizeof( addr_ptr ), &data ); if( BIG_SEG( a ) ) { a.mach = data.a48; } else { ConvAddr32ToAddr48( data.a32, a.mach ); } len = 0; for( ;; ) { if( MCReadMem( a, sizeof( data.b[0] ), &data.b[0] ) == 0 ) break; a.mach.offset++; if( len < max ) buff[len] = data.b[0]; if( data.b[0] == '\0' ) break; ++len; } if( max > 0 ) buff[max] = '\0'; *maxp = len; return( MS_OK ); }
void InitCache( address start, unsigned len ) { Cache.start = start; if( len > sizeof( Cache.data ) ) len = sizeof( Cache.data ); Cache.want = len; Cache.len = MCReadMem( start, len, Cache.data ); }
mad_status MADIMPENTRY( UnexpectedBreak )( mad_registers *mr, char *buff, size_t *buff_size_p ) { address a; struct { unsigned_32 brk; unsigned_32 br; unsigned_8 name[8]; } data; char ch; size_t buff_size; size_t len; buff_size = *buff_size_p; *buff_size_p = 0; if( buff_size > 0 ) buff[0] = '\0'; memset( &a, 0, sizeof( a ) ); a.mach.offset = mr->ppc.iar.u._32[I64LO32]; memset( &data, 0, sizeof( data ) ); MCReadMem( a, sizeof( data ), &data ); if( data.brk != BRK_POINT ) return( MS_FAIL ); mr->ppc.iar.u._32[I64LO32] += sizeof( unsigned_32 ); if( data.br != JMP_SHORT ) return( MS_OK ); if( memcmp( data.name, "WVIDEO\0\0", 8 ) != 0 ) return( MS_OK ); a.mach.offset = mr->ppc.r3.u._32[I64LO32]; len = 0; while( MCReadMem( a, sizeof( ch ), &ch ) != 0 ) { if( len + 1 < buff_size ) buff[len] = ch; if( ch == '\0' ) break; a.mach.offset++; ++len; } *buff_size_p = len; if( buff_size > 0 ) { --buff_size; if( buff_size > len ) buff_size = len; buff[buff_size] = '\0'; } return( MS_OK ); }
static int GetAnOffset( addr_off in, addr_off *off ) { address a; memset( &a, 0, sizeof( a ) ); a.mach.offset = in; return( MCReadMem( a, sizeof( *off ), off ) == sizeof( *off ) ); }
dis_return DisCliGetData( void *d, unsigned off, unsigned int size, void *data ) { mad_disasm_data *dd = d; address addr; addr = dd->addr; addr.mach.offset += off; if( MCReadMem( addr, size, data ) == 0 ) return( DR_FAIL ); return( DR_OK ); }
static void BreakRet( mad_trace_data *td, mad_disasm_data *dd, const mad_registers *mr ) { address sp; union { addr32_off off32; addr48_off off48; } off; sp = GetRegSP( mr ); switch( dd->ins.type ) { case DI_X86_iret: MCReadMem( sp, sizeof( off.off32 ), &off.off32 ); sp.mach.offset += sizeof( off.off32 ); td->brk.mach.offset = off.off32; MCReadMem( sp, sizeof( td->brk.mach.segment ), &td->brk.mach.segment ); sp.mach.offset += sizeof( td->brk.mach.segment ); break; case DI_X86_iretd: MCReadMem( sp, sizeof( off.off48 ), &off.off48 ); sp.mach.offset += sizeof( off.off48 ); td->brk.mach.offset = off.off48; MCReadMem( sp, sizeof( td->brk.mach.segment ), &td->brk.mach.segment ); sp.mach.offset += sizeof( td->brk.mach.segment ); break; default: if( dd->characteristics & X86AC_BIG ) { MCReadMem( sp, sizeof( off.off48 ), &off.off48 ); sp.mach.offset += sizeof( off.off48 ); td->brk.mach.offset = off.off48; } else { MCReadMem( sp, sizeof( off.off32 ), &off.off32 ); sp.mach.offset += sizeof( off.off32 ); td->brk.mach.offset = off.off32; } switch( td->prev_ins_type ) { case DI_X86_call: case DI_X86_call2: case DI_X86_ret: case DI_X86_ret2: td->brk.mach.segment = mr->x86.cpu.cs; break; case DI_X86_call3: case DI_X86_call4: case DI_X86_int: case DI_X86_into: case DI_X86_iret: case DI_X86_iretd: case DI_X86_retf: case DI_X86_retf2: MCReadMem( sp, sizeof( td->brk.mach.segment ), &td->brk.mach.segment ); sp.mach.offset += sizeof( td->brk.mach.segment ); break; default: break; } } MCAddrSection( &td->brk ); }
static int GetAnOffset( addr_off in, addr_off *off ) { address a; int rc; memset( &a, 0, sizeof( a ) ); a.mach.offset = in; rc = MCReadMem( a, sizeof( *off ), off ) == sizeof( *off ); if( rc ) { CONV_BE_32( *off ); // NYI: dynamic endian switching } return( rc ); }
mad_status DIGENTRY MIUnexpectedBreak( mad_registers *mr, unsigned *maxp, char *buff ) { address a; struct { unsigned_32 brk; unsigned_32 br; unsigned_8 name[8]; } data; char ch; unsigned max; unsigned len; max = *maxp; *maxp = 0; if( max > 0 ) buff[0] = '\0'; memset( &a, 0, sizeof( a ) ); a.mach.offset = mr->ppc.iar.u._32[I64LO32]; memset( &data, 0, sizeof( data ) ); MCReadMem( a, sizeof( data ), &data ); if( data.brk != BRK_POINT ) return( MS_FAIL ); mr->ppc.iar.u._32[I64LO32] += sizeof( unsigned_32 ); if( data.br != JMP_SHORT ) return( MS_OK ); if( memcmp( data.name, "WVIDEO\0\0", 8 ) != 0 ) return( MS_OK ); a.mach.offset = mr->ppc.r3.u._32[I64LO32]; len = 0; for( ;; ) { if( MCReadMem( a, sizeof( ch ), &ch ) == 0 ) break; if( len < max ) buff[len] = ch; if( ch == '\0' ) break; a.mach.offset++; ++len; } if( max > 0 ) buff[max] = '\0'; *maxp = len; return( MS_OK ); }
int VariableFrame( addr_off off ) { axp_pdata pdata; unsigned_32 ins; address a; if( GetPData( off, &pdata ) != MS_OK ) return( 0 ); if( pdata.pro_end_addr.u._32[0] == pdata.beg_addr.u._32[0] ) { return( 0 ); } memset( &a, 0, sizeof( a ) ); a.mach.offset = pdata.pro_end_addr.u._32[0] - sizeof( ins ); MCReadMem( a, sizeof( ins ), &ins ); return( ins == INS_MOV_SP_FP ); }
/* The client has run into a breakpoint that it didn't plant. Check to see if it's got the particular code pattern that the C library uses to indicate a breakpoint with a message (see enterdb.h in the WATCOM project). If so, fill in 'buff' with the text of the message and return MS_OK. If not, return MS_FAIL. On entry '*maxp' should contain the length of the buffer. On exit it will be set to the true length of the message, even if the message did not all fit into the buffer provided. */ mad_status DIGENTRY MIUnexpectedBreak( mad_registers *mr, unsigned *maxp, char *buff ) { unsigned max; char data; address a; max = *maxp; *maxp = 0; if( max > 0 ) buff[0] = '\0'; a.mach.offset = mr->jvm.pc.offset; a.mach.segment = mr->jvm.pc.segment; memset( &data, 0, sizeof( data ) ); MCReadMem( a, sizeof( data ), &data ); if( data != 202 ) return( MS_FAIL ); return( MS_OK ); }
static void ReadMem( address a, unsigned s, void *d ) { if( a.sect_id == Cache.start.sect_id && a.mach.segment == Cache.start.mach.segment && a.mach.offset >= Cache.start.mach.offset && ( a.mach.offset + s ) < ( Cache.start.mach.offset + Cache.len ) ) { memcpy( d, &Cache.data[a.mach.offset-Cache.start.mach.offset], s ); return; } #if 0 InitCache( a, Cache.want ); if( a.sect_id == Cache.start.sect_id && a.mach.segment == Cache.start.mach.segment && a.mach.offset >= Cache.start.mach.offset && (a.mach.offset+s) < (Cache.start.mach.offset+Cache.len) ) { memcpy( d, &Cache.data[a.mach.offset-Cache.start.mach.offset], s ); return; } #endif MCReadMem( a, s, d ); }