2022-07-12 01:31:51 +00:00
///////////////////////////////////////////
//
// Written: me@KatherineParry.com
// Modified: 7/5/2022
//
// Purpose: special case selection
//
// A component of the Wally configurable RISC-V project.
//
// Copyright (C) 2021 Harvey Mudd College & Oklahoma State University
//
// MIT LICENSE
// Permission is hereby granted, free of charge, to any person obtaining a copy of this
// software and associated documentation files (the "Software"), to deal in the Software
// without restriction, including without limitation the rights to use, copy, modify, merge,
// publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons
// to whom the Software is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or
// substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
// INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
// PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS
// BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
// TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE
// OR OTHER DEALINGS IN THE SOFTWARE.
////////////////////////////////////////////////////////////////////////////////////////////////
`include " wally-config.vh "
module specialcase (
input logic Xs , // input signs
input logic [ `NF : 0 ] Xm , Ym , Zm , // input mantissas
input logic XNaN , YNaN , ZNaN , // inputs are NaN
input logic [ 2 : 0 ] Frm , // rounding mode 000 = rount to nearest, ties to even 001 = round twords zero 010 = round down 011 = round up 100 = round to nearest, ties to max magnitude
input logic [ `FMTBITS - 1 : 0 ] OutFmt , // output format
input logic InfIn ,
input logic NaNIn ,
input logic XInf , YInf ,
input logic XZero ,
input logic IntZero ,
input logic IntToFp ,
input logic Int64 ,
input logic Signed ,
input logic CvtOp ,
input logic DivOp ,
input logic FmaOp ,
input logic Plus1 ,
input logic DivByZero ,
input logic [ `NE : 0 ] CvtCe , // the calculated expoent
input logic Ws , // the res's sign
input logic IntInvalid , Invalid , Overflow , // flags
input logic CvtResUf ,
input logic [ `NE - 1 : 0 ] Re , // Res exponent
input logic [ `NE + 1 : 0 ] FullRe , // Res exponent
input logic [ `NF - 1 : 0 ] Rf , // Res fraction
input logic [ `XLEN + 1 : 0 ] CvtNegRes , // the negation of the result
output logic [ `FLEN - 1 : 0 ] PostProcRes , // final res
output logic [ `XLEN - 1 : 0 ] FCvtIntRes // final res
) ;
logic [ `FLEN - 1 : 0 ] XNaNRes , YNaNRes , ZNaNRes , InvalidRes , OfRes , UfRes , NormRes ; // possible results
logic OfResMax ;
logic [ `XLEN - 1 : 0 ] OfIntRes ; // the overflow result for integer output
logic KillRes ;
logic SelOfRes ;
// does the overflow result output the maximum normalized floating point number
// output infinity if the input is infinity
assign OfResMax = ( ~ InfIn | ( IntToFp & CvtOp ) ) & ~ DivByZero & ( ( Frm [ 1 : 0 ] = = 2 'b01 ) | ( Frm [ 1 : 0 ] = = 2 'b10 & ~ Ws ) | ( Frm [ 1 : 0 ] = = 2 'b11 & Ws ) ) ;
if ( `FPSIZES = = 1 ) begin
//NaN res selection depending on standard
if ( `IEEE754 ) begin
assign XNaNRes = { 1 'b0 , { `NE { 1 'b1 } } , 1 'b1 , Xm [ `NF - 2 : 0 ] } ;
assign YNaNRes = { 1 'b0 , { `NE { 1 'b1 } } , 1 'b1 , Ym [ `NF - 2 : 0 ] } ;
assign ZNaNRes = { 1 'b0 , { `NE { 1 'b1 } } , 1 'b1 , Zm [ `NF - 2 : 0 ] } ;
assign InvalidRes = { 1 'b0 , { `NE { 1 'b1 } } , 1 'b1 , { `NF - 1 { 1 'b0 } } } ;
end else begin
assign InvalidRes = { 1 'b0 , { `NE { 1 'b1 } } , 1 'b1 , { `NF - 1 { 1 'b0 } } } ;
end
assign OfRes = OfResMax ? { Ws , { `NE - 1 { 1 'b1 } } , 1 'b0 , { `NF { 1 'b1 } } } : { Ws , { `NE { 1 'b1 } } , { `NF { 1 'b0 } } } ;
assign UfRes = { Ws , { `FLEN - 2 { 1 'b0 } } , Plus1 & Frm [ 1 ] & ~ ( DivOp & YInf ) } ;
assign NormRes = { Ws , Re , Rf } ;
end else if ( `FPSIZES = = 2 ) begin //will the format conversion in killprod work in other conversions?
if ( `IEEE754 ) begin
assign XNaNRes = OutFmt ? { 1 'b0 , { `NE { 1 'b1 } } , 1 'b1 , Xm [ `NF - 2 : 0 ] } : { { `FLEN - `LEN1 { 1 'b1 } } , 1 'b0 , { `NE1 { 1 'b1 } } , 1 'b1 , Xm [ `NF - 2 : `NF - `NF1 ] } ;
assign YNaNRes = OutFmt ? { 1 'b0 , { `NE { 1 'b1 } } , 1 'b1 , Ym [ `NF - 2 : 0 ] } : { { `FLEN - `LEN1 { 1 'b1 } } , 1 'b0 , { `NE1 { 1 'b1 } } , 1 'b1 , Ym [ `NF - 2 : `NF - `NF1 ] } ;
assign ZNaNRes = OutFmt ? { 1 'b0 , { `NE { 1 'b1 } } , 1 'b1 , Zm [ `NF - 2 : 0 ] } : { { `FLEN - `LEN1 { 1 'b1 } } , 1 'b0 , { `NE1 { 1 'b1 } } , 1 'b1 , Zm [ `NF - 2 : `NF - `NF1 ] } ;
assign InvalidRes = OutFmt ? { 1 'b0 , { `NE { 1 'b1 } } , 1 'b1 , { `NF - 1 { 1 'b0 } } } : { { `FLEN - `LEN1 { 1 'b1 } } , 1 'b0 , { `NE1 { 1 'b1 } } , 1 'b1 , ( `NF1 - 1 ) ' ( 0 ) } ;
end else begin
assign InvalidRes = OutFmt ? { 1 'b0 , { `NE { 1 'b1 } } , 1 'b1 , { `NF - 1 { 1 'b0 } } } : { { `FLEN - `LEN1 { 1 'b1 } } , 1 'b0 , { `NE1 { 1 'b1 } } , 1 'b1 , ( `NF1 - 1 ) ' ( 0 ) } ;
end
2022-07-19 23:44:37 +00:00
always_comb
if ( OutFmt )
if ( OfResMax ) OfRes = { Ws , { `NE - 1 { 1 'b1 } } , 1 'b0 , { `NF { 1 'b1 } } } ;
else OfRes = { Ws , { `NE { 1 'b1 } } , { `NF { 1 'b0 } } } ;
else
if ( OfResMax ) OfRes = { { `FLEN - `LEN1 { 1 'b1 } } , Ws , { `NE1 - 1 { 1 'b1 } } , 1 'b0 , { `NF1 { 1 'b1 } } } ;
else OfRes = { { `FLEN - `LEN1 { 1 'b1 } } , Ws , { `NE1 { 1 'b1 } } , ( `NF1 ) ' ( 0 ) } ;
2022-07-12 01:31:51 +00:00
assign UfRes = OutFmt ? { Ws , ( `FLEN - 2 ) ' ( 0 ) , Plus1 & Frm [ 1 ] & ~ ( DivOp & YInf ) } : { { `FLEN - `LEN1 { 1 'b1 } } , Ws , ( `LEN1 - 2 ) ' ( 0 ) , Plus1 & Frm [ 1 ] & ~ ( DivOp & YInf ) } ;
assign NormRes = OutFmt ? { Ws , Re , Rf } : { { `FLEN - `LEN1 { 1 'b1 } } , Ws , Re [ `NE1 - 1 : 0 ] , Rf [ `NF - 1 : `NF - `NF1 ] } ;
end else if ( `FPSIZES = = 3 ) begin
always_comb
case ( OutFmt )
`FMT : begin
if ( `IEEE754 ) begin
XNaNRes = { 1 'b0 , { `NE { 1 'b1 } } , 1 'b1 , Xm [ `NF - 2 : 0 ] } ;
YNaNRes = { 1 'b0 , { `NE { 1 'b1 } } , 1 'b1 , Ym [ `NF - 2 : 0 ] } ;
ZNaNRes = { 1 'b0 , { `NE { 1 'b1 } } , 1 'b1 , Zm [ `NF - 2 : 0 ] } ;
InvalidRes = { 1 'b0 , { `NE { 1 'b1 } } , 1 'b1 , { `NF - 1 { 1 'b0 } } } ;
end else begin
InvalidRes = { 1 'b0 , { `NE { 1 'b1 } } , 1 'b1 , { `NF - 1 { 1 'b0 } } } ;
end
OfRes = OfResMax ? { Ws , { `NE - 1 { 1 'b1 } } , 1 'b0 , { `NF { 1 'b1 } } } : { Ws , { `NE { 1 'b1 } } , { `NF { 1 'b0 } } } ;
UfRes = { Ws , ( `FLEN - 2 ) ' ( 0 ) , Plus1 & Frm [ 1 ] & ~ ( DivOp & YInf ) } ;
NormRes = { Ws , Re , Rf } ;
end
`FMT1 : begin
if ( `IEEE754 ) begin
XNaNRes = { { `FLEN - `LEN1 { 1 'b1 } } , 1 'b0 , { `NE1 { 1 'b1 } } , 1 'b1 , Xm [ `NF - 2 : `NF - `NF1 ] } ;
YNaNRes = { { `FLEN - `LEN1 { 1 'b1 } } , 1 'b0 , { `NE1 { 1 'b1 } } , 1 'b1 , Ym [ `NF - 2 : `NF - `NF1 ] } ;
ZNaNRes = { { `FLEN - `LEN1 { 1 'b1 } } , 1 'b0 , { `NE1 { 1 'b1 } } , 1 'b1 , Zm [ `NF - 2 : `NF - `NF1 ] } ;
InvalidRes = { { `FLEN - `LEN1 { 1 'b1 } } , 1 'b0 , { `NE1 { 1 'b1 } } , 1 'b1 , ( `NF1 - 1 ) ' ( 0 ) } ;
end else begin
InvalidRes = { { `FLEN - `LEN1 { 1 'b1 } } , 1 'b0 , { `NE1 { 1 'b1 } } , 1 'b1 , ( `NF1 - 1 ) ' ( 0 ) } ;
end
OfRes = OfResMax ? { { `FLEN - `LEN1 { 1 'b1 } } , Ws , { `NE1 - 1 { 1 'b1 } } , 1 'b0 , { `NF1 { 1 'b1 } } } : { { `FLEN - `LEN1 { 1 'b1 } } , Ws , { `NE1 { 1 'b1 } } , ( `NF1 ) ' ( 0 ) } ;
UfRes = { { `FLEN - `LEN1 { 1 'b1 } } , Ws , ( `LEN1 - 2 ) ' ( 0 ) , Plus1 & Frm [ 1 ] & ~ ( DivOp & YInf ) } ;
NormRes = { { `FLEN - `LEN1 { 1 'b1 } } , Ws , Re [ `NE1 - 1 : 0 ] , Rf [ `NF - 1 : `NF - `NF1 ] } ;
end
`FMT2 : begin
if ( `IEEE754 ) begin
XNaNRes = { { `FLEN - `LEN2 { 1 'b1 } } , 1 'b0 , { `NE2 { 1 'b1 } } , 1 'b1 , Xm [ `NF - 2 : `NF - `NF2 ] } ;
YNaNRes = { { `FLEN - `LEN2 { 1 'b1 } } , 1 'b0 , { `NE2 { 1 'b1 } } , 1 'b1 , Ym [ `NF - 2 : `NF - `NF2 ] } ;
ZNaNRes = { { `FLEN - `LEN2 { 1 'b1 } } , 1 'b0 , { `NE2 { 1 'b1 } } , 1 'b1 , Zm [ `NF - 2 : `NF - `NF2 ] } ;
InvalidRes = { { `FLEN - `LEN2 { 1 'b1 } } , 1 'b0 , { `NE2 { 1 'b1 } } , 1 'b1 , ( `NF2 - 1 ) ' ( 0 ) } ;
end else begin
InvalidRes = { { `FLEN - `LEN2 { 1 'b1 } } , 1 'b0 , { `NE2 { 1 'b1 } } , 1 'b1 , ( `NF2 - 1 ) ' ( 0 ) } ;
end
OfRes = OfResMax ? { { `FLEN - `LEN2 { 1 'b1 } } , Ws , { `NE2 - 1 { 1 'b1 } } , 1 'b0 , { `NF2 { 1 'b1 } } } : { { `FLEN - `LEN2 { 1 'b1 } } , Ws , { `NE2 { 1 'b1 } } , ( `NF2 ) ' ( 0 ) } ;
UfRes = { { `FLEN - `LEN2 { 1 'b1 } } , Ws , ( `LEN2 - 2 ) ' ( 0 ) , Plus1 & Frm [ 1 ] & ~ ( DivOp & YInf ) } ;
NormRes = { { `FLEN - `LEN2 { 1 'b1 } } , Ws , Re [ `NE2 - 1 : 0 ] , Rf [ `NF - 1 : `NF - `NF2 ] } ;
end
default : begin
if ( `IEEE754 ) begin
XNaNRes = ( `FLEN ) ' ( 0 ) ;
YNaNRes = ( `FLEN ) ' ( 0 ) ;
ZNaNRes = ( `FLEN ) ' ( 0 ) ;
InvalidRes = ( `FLEN ) ' ( 0 ) ;
end else begin
InvalidRes = ( `FLEN ) ' ( 0 ) ;
end
OfRes = ( `FLEN ) ' ( 0 ) ;
UfRes = ( `FLEN ) ' ( 0 ) ;
NormRes = ( `FLEN ) ' ( 0 ) ;
end
endcase
end else if ( `FPSIZES = = 4 ) begin
always_comb
case ( OutFmt )
2 'h3 : begin
if ( `IEEE754 ) begin
XNaNRes = { 1 'b0 , { `NE { 1 'b1 } } , 1 'b1 , Xm [ `NF - 2 : 0 ] } ;
YNaNRes = { 1 'b0 , { `NE { 1 'b1 } } , 1 'b1 , Ym [ `NF - 2 : 0 ] } ;
ZNaNRes = { 1 'b0 , { `NE { 1 'b1 } } , 1 'b1 , Zm [ `NF - 2 : 0 ] } ;
InvalidRes = { 1 'b0 , { `NE { 1 'b1 } } , 1 'b1 , { `NF - 1 { 1 'b0 } } } ;
end else begin
InvalidRes = { 1 'b0 , { `NE { 1 'b1 } } , 1 'b1 , { `NF - 1 { 1 'b0 } } } ;
end
OfRes = OfResMax ? { Ws , { `NE - 1 { 1 'b1 } } , 1 'b0 , { `NF { 1 'b1 } } } : { Ws , { `NE { 1 'b1 } } , { `NF { 1 'b0 } } } ;
UfRes = { Ws , ( `FLEN - 2 ) ' ( 0 ) , Plus1 & Frm [ 1 ] & ~ ( DivOp & YInf ) } ;
NormRes = { Ws , Re , Rf } ;
end
2 'h1 : begin
if ( `IEEE754 ) begin
XNaNRes = { { `FLEN - `D_LEN { 1 'b1 } } , 1 'b0 , { `D_NE { 1 'b1 } } , 1 'b1 , Xm [ `NF - 2 : `NF - `D_NF ] } ;
YNaNRes = { { `FLEN - `D_LEN { 1 'b1 } } , 1 'b0 , { `D_NE { 1 'b1 } } , 1 'b1 , Ym [ `NF - 2 : `NF - `D_NF ] } ;
ZNaNRes = { { `FLEN - `D_LEN { 1 'b1 } } , 1 'b0 , { `D_NE { 1 'b1 } } , 1 'b1 , Zm [ `NF - 2 : `NF - `D_NF ] } ;
InvalidRes = { { `FLEN - `D_LEN { 1 'b1 } } , 1 'b0 , { `D_NE { 1 'b1 } } , 1 'b1 , ( `D_NF - 1 ) ' ( 0 ) } ;
end else begin
InvalidRes = { { `FLEN - `D_LEN { 1 'b1 } } , 1 'b0 , { `D_NE { 1 'b1 } } , 1 'b1 , ( `D_NF - 1 ) ' ( 0 ) } ;
end
OfRes = OfResMax ? { { `FLEN - `D_LEN { 1 'b1 } } , Ws , { `D_NE - 1 { 1 'b1 } } , 1 'b0 , { `D_NF { 1 'b1 } } } : { { `FLEN - `D_LEN { 1 'b1 } } , Ws , { `D_NE { 1 'b1 } } , ( `D_NF ) ' ( 0 ) } ;
UfRes = { { `FLEN - `D_LEN { 1 'b1 } } , Ws , ( `D_LEN - 2 ) ' ( 0 ) , Plus1 & Frm [ 1 ] & ~ ( DivOp & YInf ) } ;
NormRes = { { `FLEN - `D_LEN { 1 'b1 } } , Ws , Re [ `D_NE - 1 : 0 ] , Rf [ `NF - 1 : `NF - `D_NF ] } ;
end
2 'h0 : begin
if ( `IEEE754 ) begin
XNaNRes = { { `FLEN - `S_LEN { 1 'b1 } } , 1 'b0 , { `S_NE { 1 'b1 } } , 1 'b1 , Xm [ `NF - 2 : `NF - `S_NF ] } ;
YNaNRes = { { `FLEN - `S_LEN { 1 'b1 } } , 1 'b0 , { `S_NE { 1 'b1 } } , 1 'b1 , Ym [ `NF - 2 : `NF - `S_NF ] } ;
ZNaNRes = { { `FLEN - `S_LEN { 1 'b1 } } , 1 'b0 , { `S_NE { 1 'b1 } } , 1 'b1 , Zm [ `NF - 2 : `NF - `S_NF ] } ;
InvalidRes = { { `FLEN - `S_LEN { 1 'b1 } } , 1 'b0 , { `S_NE { 1 'b1 } } , 1 'b1 , ( `S_NF - 1 ) ' ( 0 ) } ;
end else begin
InvalidRes = { { `FLEN - `S_LEN { 1 'b1 } } , 1 'b0 , { `S_NE { 1 'b1 } } , 1 'b1 , ( `S_NF - 1 ) ' ( 0 ) } ;
end
OfRes = OfResMax ? { { `FLEN - `S_LEN { 1 'b1 } } , Ws , { `S_NE - 1 { 1 'b1 } } , 1 'b0 , { `S_NF { 1 'b1 } } } : { { `FLEN - `S_LEN { 1 'b1 } } , Ws , { `S_NE { 1 'b1 } } , ( `S_NF ) ' ( 0 ) } ;
UfRes = { { `FLEN - `S_LEN { 1 'b1 } } , Ws , ( `S_LEN - 2 ) ' ( 0 ) , Plus1 & Frm [ 1 ] & ~ ( DivOp & YInf ) } ;
NormRes = { { `FLEN - `S_LEN { 1 'b1 } } , Ws , Re [ `S_NE - 1 : 0 ] , Rf [ `NF - 1 : `NF - `S_NF ] } ;
end
2 'h2 : begin
if ( `IEEE754 ) begin
XNaNRes = { { `FLEN - `H_LEN { 1 'b1 } } , 1 'b0 , { `H_NE { 1 'b1 } } , 1 'b1 , Xm [ `NF - 2 : `NF - `H_NF ] } ;
YNaNRes = { { `FLEN - `H_LEN { 1 'b1 } } , 1 'b0 , { `H_NE { 1 'b1 } } , 1 'b1 , Ym [ `NF - 2 : `NF - `H_NF ] } ;
ZNaNRes = { { `FLEN - `H_LEN { 1 'b1 } } , 1 'b0 , { `H_NE { 1 'b1 } } , 1 'b1 , Zm [ `NF - 2 : `NF - `H_NF ] } ;
InvalidRes = { { `FLEN - `H_LEN { 1 'b1 } } , 1 'b0 , { `H_NE { 1 'b1 } } , 1 'b1 , ( `H_NF - 1 ) ' ( 0 ) } ;
end else begin
InvalidRes = { { `FLEN - `H_LEN { 1 'b1 } } , 1 'b0 , { `H_NE { 1 'b1 } } , 1 'b1 , ( `H_NF - 1 ) ' ( 0 ) } ;
end
OfRes = OfResMax ? { { `FLEN - `H_LEN { 1 'b1 } } , Ws , { `H_NE - 1 { 1 'b1 } } , 1 'b0 , { `H_NF { 1 'b1 } } } : { { `FLEN - `H_LEN { 1 'b1 } } , Ws , { `H_NE { 1 'b1 } } , ( `H_NF ) ' ( 0 ) } ;
// zero is exact fi dividing by infinity so don't add 1
UfRes = { { `FLEN - `H_LEN { 1 'b1 } } , Ws , ( `H_LEN - 2 ) ' ( 0 ) , Plus1 & Frm [ 1 ] & ~ ( DivOp & YInf ) } ;
NormRes = { { `FLEN - `H_LEN { 1 'b1 } } , Ws , Re [ `H_NE - 1 : 0 ] , Rf [ `NF - 1 : `NF - `H_NF ] } ;
end
endcase
end
// determine if you shoould kill the res - Cvt
// - do so if the res underflows, is zero (the exp doesnt calculate correctly). or the integer input is 0
// - dont set to zero if fp input is zero but not using the fp input
// - dont set to zero if int input is zero but not using the int input
assign KillRes = CvtOp ? ( CvtResUf | ( XZero & ~ IntToFp ) | ( IntZero & IntToFp ) ) : FullRe [ `NE + 1 ] | ( ( ( YInf & ~ XInf ) | XZero ) & DivOp ) ; //Underflow & ~ResDenorm & (Re!=1);
assign SelOfRes = Overflow | DivByZero | ( InfIn & ~ ( YInf & DivOp ) ) ;
// output infinity with result sign if divide by zero
2022-07-19 23:44:37 +00:00
if ( `IEEE754 )
always_comb
if ( XNaN & ~ ( IntToFp & CvtOp ) ) PostProcRes = XNaNRes ;
else if ( YNaN & ~ CvtOp ) PostProcRes = YNaNRes ;
else if ( ZNaN & FmaOp ) PostProcRes = ZNaNRes ;
else if ( Invalid ) PostProcRes = InvalidRes ;
else if ( SelOfRes ) PostProcRes = OfRes ;
else if ( KillRes ) PostProcRes = UfRes ;
else PostProcRes = NormRes ;
else
always_comb
if ( NaNIn | Invalid ) PostProcRes = InvalidRes ;
else if ( SelOfRes ) PostProcRes = OfRes ;
else if ( KillRes ) PostProcRes = UfRes ;
else PostProcRes = NormRes ;
2022-07-12 01:31:51 +00:00
///////////////////////////////////////////////////////////////////////////////////////
//
// ||||||||||| ||| ||| |||||||||||||
// ||| |||||| ||| |||
// ||| ||| ||| ||| |||
// ||| ||| |||||| |||
// ||||||||||| ||| ||| |||
//
///////////////////////////////////////////////////////////////////////////////////////
// *** probably can optimize the negation
// select the overflow integer res
// - negitive infinity and out of range negitive input
// | int | long |
// signed | -2^31 | -2^63 |
// unsigned | 0 | 0 |
//
// - positive infinity and out of range positive input and NaNs
// | int | long |
// signed | 2^31-1 | 2^63-1 |
// unsigned | 2^32-1 | 2^64-1 |
//
// other: 32 bit unsinged res should be sign extended as if it were a signed number
2022-07-19 23:44:37 +00:00
always_comb
if ( Signed )
2022-07-21 01:20:06 +00:00
if ( Xs & ~ NaNIn ) // signed negitive
2022-07-19 23:44:37 +00:00
if ( Int64 ) OfIntRes = { 1 'b1 , { `XLEN - 1 { 1 'b0 } } } ;
else OfIntRes = { { `XLEN - 32 { 1 'b1 } } , 1 'b1 , { 31 { 1 'b0 } } } ;
else // signed positive
if ( Int64 ) OfIntRes = { 1 'b0 , { `XLEN - 1 { 1 'b1 } } } ;
else OfIntRes = { { `XLEN - 32 { 1 'b0 } } , 1 'b0 , { 31 { 1 'b1 } } } ;
else
2022-07-21 01:20:06 +00:00
if ( Xs & ~ NaNIn ) OfIntRes = { `XLEN { 1 'b0 } } ; // unsigned negitive
2022-07-19 23:44:37 +00:00
else OfIntRes = { `XLEN { 1 'b1 } } ; // unsigned positive
2022-07-12 01:31:51 +00:00
// select the integer output
// - if the input is invalid (out of bounds NaN or Inf) then output overflow res
// - if the input underflows
// - if rounding and signed opperation and negitive input, output -1
// - otherwise output a rounded 0
// - otherwise output the normal res (trmined and sign extended if nessisary)
2022-07-19 23:44:37 +00:00
always_comb
if ( IntInvalid ) FCvtIntRes = OfIntRes ;
else if ( CvtCe [ `NE ] )
if ( Xs & Signed & Plus1 ) FCvtIntRes = { { `XLEN { 1 'b1 } } } ;
else FCvtIntRes = { { `XLEN - 1 { 1 'b0 } } , Plus1 } ;
else if ( Int64 ) FCvtIntRes = CvtNegRes [ `XLEN - 1 : 0 ] ;
else FCvtIntRes = { { `XLEN - 32 { CvtNegRes [ 31 ] } } , CvtNegRes [ 31 : 0 ] } ;
2022-07-12 01:31:51 +00:00
endmodule