From: bd733 AT rgfn DOT epcc DOT edu (Jason M. Daniels) Newsgroups: comp.os.msdos.djgpp Subject: set vs. chain Date: 21 Mar 1997 00:27:21 GMT Organization: The Rio Grande Free-Net, El Paso Community College, El Paso, TX Lines: 123 Message-ID: <5gskl9$mjj@news.epcc.edu> NNTP-Posting-Host: rgfn.epcc.edu To: djgpp AT delorie DOT com DJ-Gateway: from newsgroup comp.os.msdos.djgpp I'm trying to learn to write interrupt handlers and use them with DJGPP. I've followed what directions I can find, but have come across an interesting problem. At first, I used _go32_dpmi_chain_protected_mode_ interrupt_vector() to set up my handler, but when I used this method, input got dumped to the command line after the program exited, because the data was never destructively read from the original handler. OK. So then I tried to follow the directions in the FAQ for using [...]_set_[...]. I saved the previous handler, allocated an iret wrapper, and set the handler. However, the interrupt will trigger once and then crash the computer. This did not happen with [...]_chain_[...]. Here's the source code: /* * Non-chaining version (crashes) */ #include #include #include #include #include #include #include #define PAUSE 300000001 int _crt0_startup_flags = _CRT0_FLAG_LOCK_MEMORY; volatile unsigned long int handler_count = 0; unsigned long int main_track_count = 0; void int1(int in) { handler_count++; } int main(void) { __dpmi_regs regs; /* Allocate register variables */ _go32_dpmi_seginfo pmint,old; /* Allocate a seginfo struct */ int x = 0; pmint.pm_selector = _my_cs(); /* Load selector with your code segment... */ pmint.pm_offset = (unsigned)&int1; /* and offset with address of function to be called. */ _go32_dpmi_get_protected_mode_interrupt_vector(9, &old); _go32_dpmi_allocate_iret_wrapper(&pmint); _go32_dpmi_set_protected_mode_interrupt_vector(9, &pmint); for(;x < PAUSE;x++) { while(main_track_count != handler_count) { main_track_count++; printf("%lu\n",main_track_count); } } /* display info about the interrupt */ printf("Interrupts made: %lu\n",handler_count); _go32_dpmi_set_protected_mode_interrupt_vector(9, &old); _go32_dpmi_free_iret_wrapper(&pmint); return(0); } /* * Chaining version */ #include #include #include #include #include #include #include #define PAUSE 3000001 int _crt0_startup_flags = _CRT0_FLAG_LOCK_MEMORY; volatile unsigned long int handler_count = 0; unsigned long int main_track_count = 0; void int1(int in) { handler_count++; } int main(void) { _go32_dpmi_seginfo pmint; /* Allocate a seginfo struct */ int x = 0; pmint.pm_selector = _my_cs(); /* Load selector with your code segment... */ pmint.pm_offset = (unsigned)&int1; /* and offset with address of function to be called. */ _go32_dpmi_chain_protected_mode_interrupt_vector(9, &pmint); for(;x < PAUSE;x++) { while(main_track_count != handler_count) { main_track_count++; printf("%lu\n",main_track_count); } } /* display info about the interrupt */ printf("Interrupts made: %lu\n",handler_count); return(0); } TIA! :-) -- Jason Daniels -- bd733 AT rgfn DOT epcc DOT edu http://www.trailerpark.com/phase2/fireside/index.htm Paradox #218: "Saying 'I'm very modest' isn't." Commodore 64 forever!