PRODUCT : Borland C++ NUMBER : 722 VERSION : 2.0 OS : DOS DATE : September 18, 1991 PAGE : 1/2 TITLE : Using Floating Points in ISR's QUESTION: How do I use floating point within an interrupt service routine? ANSWER: The floating point emulator in Turbo C is NOT re-entrant. 8087 instructions can only be used in interrupt routines if the chip is present, and all programs with 8087 interrupt handlers should be compiled without emulation. Within the interrupt handler, the FNSAVE instruction should be used to save the state of the 8087 chip into a 94 byte state record. After saving the state, an implicit FINIT is executed to bring the chip into its default state. In this state, exceptions are masked, so divide-by-zeros, overflows, etc. will produce NANs and INFs, not run-time errors. It so happens that this is exactly what we want (a run-time error during an interrupt would completely crash the system), so no FLDCW is required to load a different control word. The FNSAVE must be executed before the STI that re-enables interrupts. Furthermore, an FWAIT must precede STI to make sure that the state has been completely saved. The FRSTOR must be followed by an FWAIT to ensure that the state has been completely reloaded before the state variable is removed from the stack. EXAMPLE: #include #include #include double x = 0; void interrupt (*save)(void); void interrupt func(void) { unsigned char state87[94]; __emit__( 0xDD,0x76,state87, /* FNSAVE [BP+ interrupt. */ setvect(5, func); while (ch != 'q') { cprintf("%f\r\n", x); /* Each time you hit */ if (kbhit()) /* x will get incremented. */ ch = getch(); } setvect(5, save); /* restore original vector for INT 5 */ return(0); }