Re: Need to hook INT 21h from a DJGPP TSR



> It can lead to many undesirable "PM" -> "RM" -> "PM Again"
> chain loops.

That's probably the problem. The following code shows how to work
around it for int 0x21,ax=0x4b00 to ax=0x4b05. Like I stated
before it works for PMODE/DJ w/RM and PM apps. For CWSDPMI, it
only works for RM apps, giving the "Page Fault ... in RMCB" for PM
apps. I don't know exactly what memory needs to be locked for
CWSDPMI.

Rod Pemberton


#include <stdio.h>
#include <stdlib.h>
#include <dpmi.h>
#include <go32.h>
#include <crt0.h>
#include <sys/farptr.h>
#include <string.h>
#include <pc.h>
#include <io.h>

#define hexch(x) (((x)<0x0A)?(0x30+(x)):(0x37+(x)))
extern int __djgpp_base_address; /* crt0.s */

int _crt0_startup_flags = _CRT0_FLAG_LOCK_MEMORY;
// |_CRT0_FLAG_NONMOVE_SBRK;

char ** __crt0_glob_function(char *arg) { return (char **)0; }
void __crt0_load_environment_file(char *app_name) {}
void __crt0_setup_arguments (void) {}

_go32_dpmi_registers r;
_go32_dpmi_seginfo rmint,rmold;

#if 0
__dpmi_meminfo lck;
#endif

void color_rot(unsigned char x)
{
unsigned offset = ScreenPrimary+(2*80-2*x+1-20);
_farpokeb(_dos_ds,offset,1+_farpeekb(_dos_ds,offset));
}

void intcore(_go32_dpmi_registers *r)
{
unsigned offset = ScreenPrimary+(2*80-2*7-20);
char ch[6];
int i;

ch[0] = hexch(2); // int21
ch[1] = hexch(1);
ch[2] = hexch(r->h.ah>>4);
ch[3] = hexch(r->h.ah&0x0F);
ch[4] = hexch(r->h.al>>4);
ch[5] = hexch(r->h.al&0x0F);

for (i=0;i<6;i++) {
_farpokeb(_dos_ds,offset+i*2,ch[i]);
_farpokeb(_dos_ds,offset+i*2+1,0x6F);
}
color_rot(1);
}

void inttrm(_go32_dpmi_registers *r)
{
intcore(r);
if ((r->h.ah == 0x4b) && (r->h.al < 0x05))
{
_go32_dpmi_set_real_mode_interrupt_vector(0x21, &rmold);
_go32_dpmi_simulate_int(0x21,r);
_go32_dpmi_set_real_mode_interrupt_vector(0x21, &rmint);
}
else
{
r->x.cs = rmold.rm_segment;
r->x.ip = rmold.rm_offset;
_go32_dpmi_simulate_fcall_iret(r);
}
}

int main(void)
{
memset(&r,0,sizeof(r));

_go32_dpmi_get_real_mode_interrupt_vector(0x21, &rmold);
rmint.pm_offset = (unsigned long)&inttrm;
_go32_dpmi_allocate_real_mode_callback_iret(&rmint,&r);
_go32_dpmi_set_real_mode_interrupt_vector(0x21, &rmint);

#if 0
lck.size=(unsigned long);
lck.address=(unsigned long);
__dpmi_lock_linear_region(&lck);
#endif

_write(2,"Installing DJGPP TSR\r\n",22);

r.x.ax = 0x3100;
r.x.dx = (131072) / 16; /* paragraphs (16 bytes) */
/* file size + 100 for PSP */
r.x.cs = rmold.rm_segment;
r.x.ip = rmold.rm_offset;

_go32_dpmi_simulate_fcall_iret(&r);

exit(0);
}

--
Posted via: http://www.cyberjustice.org
.



Relevant Pages