<html><body>
<p><font size="2" face="sans-serif">1. There is a FEX (Floating-Point Enabled Exception Summary) status bit in the PowerPC FPSCR (Floating-Point Status and Control Register) that is the OR of all enabled exception status bits.</font><br>
<font size="2" face="sans-serif">2. Every floating-point instruction has a control bit that slightly changes its name and semantics. For example, the "fadd" (Floating-Point Add Double Precision) instruction has a corresponding "fadd</font><font size="2" face="sans-serif"><b>.</b></font><font size="2" face="sans-serif">" (with a period on the end) (Floating-Point Add Double Precision) instruction that does the same thing as fadd and also copies a 4 bit portion of the FPSCR to Condition Register Field 1 (cr1). The FEX bit is the second bit of that.</font><br>
<font size="2" face="sans-serif">3. A standard branch on true or branch on false instruction can test any bit of the 32 bit Condition Register and branch or not.</font><br>
<font size="2" face="sans-serif">4. When precisely detecting floating-point exceptions is enabled, the compiler generates the "</font><font size="2" face="sans-serif"><b>.</b></font><font size="2" face="sans-serif">" version of all floating-point instructions, and also generates the "</font><font size="2" face="sans-serif"><b>.</b></font><font size="2" face="sans-serif">" version of </font><font size="2" face="sans-serif">a floating-point register copy instruction after each call. That ensures that FEX is copied to cr1 after every operation and every call.</font><br>
<font size="2" face="sans-serif">5. When imprecise detection is enabled for smaller faster code, the normal floating-point instructions are generated, but the "</font><font size="2" face="sans-serif"><b>.</b></font><font size="2" face="sans-serif">" version of a floating-point register copy instruction is generated before the function returns. That ensures that FEX is copied to cr1 before the return, instead of after every floating-point operation.</font><br>
<font size="2" face="sans-serif">6. In both precise (#4) and imprecise (#5) cases</font><font size="2" face="sans-serif">, the compiler generates a branch on false around a trap instruction after each of the "</font><font size="2" face="sans-serif"><b>.</b></font><font size="2" face="sans-serif">" instructions.<br>
If there was no enabled exception, the cr1 copy of the FEX bit is false, the branch on false around the trap is taken, and the program continues.</font><br>
<font size="2" face="sans-serif"> If there was an enabled exception, the cr1 copy of the FEX bit is true, the branch on false around the trap is not taken, and the trap is executed.</font><br>
<font size="2" face="sans-serif"> The conditional branch should be predicted as taken, so the next instruction after the trap can be fetched and dispatched without waiting.</font><br>
<font size="2" face="sans-serif">7. If it is executed the trap causes a trap interrupt, and the operating system activates the trap signal handler if there is one.</font><br>
<br>
<font size="2" face="sans-serif">The code pattern for precise detection is</font><br>
<font size="2" face="sans-serif">        add</font><font size="2" face="sans-serif"><b>.</b></font><font size="2" face="sans-serif"> fprR=fprA,fprB</font><br>
<font size="2" face="sans-serif">        bf cr1,FEXbit,*+4</font><br>
<font size="2" face="sans-serif">        trap</font><br>
<br>
<font size="2" face="sans-serif">For catching an exception in an exception try block (or whatever equivalent we choose), I expect #6 and #7 of the mechanism would be changed:</font><br>
<font size="2" face="sans-serif">6. The compiler would generate a branch on false around a block of exception decoding code.<br>
Knowing that at least one enabled exception must have occurred if it's reached, that code would copy exception status bits into one or more condition register fields, then execute conditional branch on true instructions testing the status bits of interest and if set branching to the catch block corresponding to that status bit. For example, if the overflow and invalid operation exceptions were to be caught, one branch would go to the overflow catch handler if the overflow status bit was set, and a second branch would go to the invalid operation catch handler.<br>
The catch handler reached would handle that exception as requested. If for example overflow occured, and the overflow catch handler said to substitute a value (eg, the maximum finite value), the catch code would have to put the new value into the register or variable the expression result should be in, then continue execution.</font><br>
<font size="2" face="sans-serif">7. No trap would occur so the trap signal handler would not be involved.</font><br>
<br>
<font size="2" face="sans-serif">The code pattern for precise detection would be:</font><br>
<font size="2" face="sans-serif">        add</font><font size="2" face="sans-serif"><b>.</b></font><font size="2" face="sans-serif"> fprR=fprA,fprB</font><br>
<font size="2" face="sans-serif">        bt cr1,FEXbit,catch_decode</font><br>
<font size="2" face="sans-serif">        . . .</font><br>
<font size="2" face="sans-serif">        sub</font><font size="2" face="sans-serif"><b>.</b></font><font size="2" face="sans-serif"> fprX=fprY,fprZ</font><br>
<font size="2" face="sans-serif">        bt cr1,FEXbit,catch_decode</font><br>
<font size="2" face="sans-serif">        . . . other operations . . .</font><br>
<br>
<font size="2" face="sans-serif"> catchdecode:</font><br>
<font size="2" face="sans-serif">        /* decode exceptions */</font><br>
<font size="2" face="sans-serif">        copy fpscr overflow bit to crM</font><br>
<font size="2" face="sans-serif">        bt crM,OVERFLOWbit,catch_overflow</font><br>
<font size="2" face="sans-serif">        copy fpscr invalid bit to crN</font><br>
<font size="2" face="sans-serif">        bt crN,INVALIDbit,catch_invalid</font><br>
<font size="2" face="sans-serif">        . . .</font><br>
<font size="2" face="sans-serif">catch_overflow:</font><br>
<font size="2" face="sans-serif">        . . .</font><br>
<font size="2" face="sans-serif">catch_invalid:</font><br>
<font size="2" face="sans-serif">        . . .</font><br>
<br>
<font size="2" face="sans-serif">Only tests for the enabled exceptions are needed, and the last can be omitted and just fall through into that catch handler because it must be the cause.</font><br>
<font size="2" face="sans-serif">Instead of a branch on true to the catch handler, a branch on false around it could be used.</font><br>
<br>
<font size="2" face="sans-serif">The code pattern for imprecise detection would be slightly simpler:</font><br>
<font size="2" face="sans-serif">        add fprR=fprA,fprB</font><br>
<font size="2" face="sans-serif">        sub</font><font size="2" face="sans-serif"><b> </b></font><font size="2" face="sans-serif"> fprX=fprY,fprZ</font><br>
<font size="2" face="sans-serif">        . . . other operations . . .</font><br>
<br>
<font size="2" face="sans-serif">        /* At end of try block: */</font><br>
<font size="2" face="sans-serif">        copy fpscr FEX bit to cr1</font><br>
<font size="2" face="sans-serif">        bf cr1,FEXbit,noexceptions</font><br>
<br>
<font size="2" face="sans-serif">        /* decode exceptions */</font><br>
<font size="2" face="sans-serif">        copy fpscr overflow bit to crM</font><br>
<font size="2" face="sans-serif">        bt crM,OVERFLOWbit,catch_overflow</font><br>
<font size="2" face="sans-serif">        copy fpscr invalid bit to crN</font><br>
<font size="2" face="sans-serif">        bt crN,INVALIDbit,catch_invalid</font><br>
<font size="2" face="sans-serif">        . . .</font><br>
<font size="2" face="sans-serif">catch_overflow:</font><br>
<font size="2" face="sans-serif">        . . .</font><br>
<font size="2" face="sans-serif">catch_invalid:</font><br>
<font size="2" face="sans-serif">        . . .</font><br>
<br>
<font size="2" face="sans-serif">Advantages include that the system call to set up the trap handler is avoided, and if an exception occurs the cost of activating the trap handler and having it decode the cause is avoided.</font><br>
<font size="2" face="sans-serif">Disadvantages include that with precise detection the program code would run slower due to the branches.</font><br>
<br>
<font size="2" face="sans-serif">- Ian McIntosh IBM Canada Lab Compiler Back End Support and Development<br>
</font><br>
<br>
<img width="16" height="16" src="cid:1__=0ABBF663DF9F32D68f9e8a93df938@ca.ibm.com" border="0" alt="Inactive hide details for David Hough CFP ---2014-06-06 06:00:32 PM---> the PowerPC architecture allows compilers to detect any"><font size="2" color="#424282" face="sans-serif">David Hough CFP ---2014-06-06 06:00:32 PM---> the PowerPC architecture allows compilers to detect any exceptions including underflow by using a</font><br>
<br>
<table width="100%" border="0" cellspacing="0" cellpadding="0">
<tr valign="top"><td width="1%"><img width="96" height="1" src="cid:2__=0ABBF663DF9F32D68f9e8a93df938@ca.ibm.com" border="0" alt=""><br>
<ul style="padding-left: 4pt"><font size="1" color="#5F5F5F" face="sans-serif">From:</font></ul>
</td><td width="100%"><img width="1" height="1" src="cid:2__=0ABBF663DF9F32D68f9e8a93df938@ca.ibm.com" border="0" alt=""><br>
<font size="1" face="sans-serif">David Hough CFP <pcfp@oakapple.net></font></td></tr>
<tr valign="top"><td width="1%"><img width="96" height="1" src="cid:2__=0ABBF663DF9F32D68f9e8a93df938@ca.ibm.com" border="0" alt=""><br>
<ul style="padding-left: 4pt"><font size="1" color="#5F5F5F" face="sans-serif">To:</font></ul>
</td><td width="100%"><img width="1" height="1" src="cid:2__=0ABBF663DF9F32D68f9e8a93df938@ca.ibm.com" border="0" alt=""><br>
<font size="1" face="sans-serif">Ian McIntosh/Toronto/IBM@IBMCA, </font></td></tr>
<tr valign="top"><td width="1%"><img width="96" height="1" src="cid:2__=0ABBF663DF9F32D68f9e8a93df938@ca.ibm.com" border="0" alt=""><br>
<ul style="padding-left: 4pt"><font size="1" color="#5F5F5F" face="sans-serif">Date:</font></ul>
</td><td width="100%"><img width="1" height="1" src="cid:2__=0ABBF663DF9F32D68f9e8a93df938@ca.ibm.com" border="0" alt=""><br>
<font size="1" face="sans-serif">2014-06-06 06:00 PM</font></td></tr>
<tr valign="top"><td width="1%"><img width="96" height="1" src="cid:2__=0ABBF663DF9F32D68f9e8a93df938@ca.ibm.com" border="0" alt=""><br>
<ul style="padding-left: 4pt"><font size="1" color="#5F5F5F" face="sans-serif">Subject:</font></ul>
</td><td width="100%"><img width="1" height="1" src="cid:2__=0ABBF663DF9F32D68f9e8a93df938@ca.ibm.com" border="0" alt=""><br>
<font size="1" face="sans-serif">Re: [Cfp-interest] exceptions and flags</font></td></tr>
</table>
<hr width="100%" size="2" align="left" noshade style="color:#8091A5; "><br>
<br>
<br>
<tt><font size="2">> the PowerPC architecture allows compilers to<br>
detect any exceptions including underflow by using a slightly different<br>
opcode then a conditional branch<br>
<br>
<br>
So this is a branch on exception rather than branch on flag?<br>
Does it refer to the most recent fp op code or is it some kind<br>
of cumulative register like the flags, so the branch is taken if the<br>
exception has arisen since the register was last reset?<br>
<br>
I would suppose that, in analogy to comparison condition-codes, it<br>
refers to the result of the last fp op code to execute. If out of <br>
order, does the conditional wait for all pending instructions to complete?<br>
<br>
</font></tt><br>
<br>
</body></html>