クラス sc_dt::scfx_rep

#include <scfx_rep.h>

すべてのメンバ一覧

Public メソッド

 scfx_rep ()
 scfx_rep (int)
 scfx_rep (unsigned int)
 scfx_rep (long)
 scfx_rep (unsigned long)
 scfx_rep (double)
 scfx_rep (const char *)
 scfx_rep (int64)
 scfx_rep (uint64)
 scfx_rep (const sc_signed &)
 scfx_rep (const sc_unsigned &)
 scfx_rep (const scfx_rep &)
 ~scfx_rep ()
void * operator new (std::size_t)
void operator delete (void *, std::size_t)
void from_string (const char *, int)
double to_double () const
const char * to_string (sc_numrep, int, sc_fmt, const scfx_params *=0) const
void operator= (const scfx_rep &)
void lshift (int)
void rshift (int)
void cast (const scfx_params &, bool &, bool &)
bool is_neg () const
bool is_zero () const
bool is_nan () const
bool is_inf () const
bool is_normal () const
void set_zero (int=1)
void set_nan ()
void set_inf (int)
bool get_bit (int) const
bool set (int, const scfx_params &)
bool clear (int, const scfx_params &)
bool get_slice (int, int, const scfx_params &, sc_bv_base &) const
bool set_slice (int, int, const scfx_params &, const sc_bv_base &)
void print (::std::ostream &) const
void dump (::std::ostream &) const
void get_type (int &, int &, sc_enc &) const
bool rounding_flag () const

Private 型

enum  state { normal, infinity, not_a_number }

Private メソッド

unsigned int divide_by_ten ()
int find_lsw () const
int find_msw () const
void find_sw ()
void multiply_by_ten ()
void normalize (int)
scfx_mantresize (int, int) const
void set_bin (int)
void set_oct (int, int)
void set_hex (int, int)
void shift_left (int)
void shift_right (int)
const scfx_index calc_indices (int) const
void o_extend (const scfx_index &, sc_enc)
bool o_bit_at (const scfx_index &) const
bool o_zero_left (const scfx_index &) const
bool o_zero_right (const scfx_index &) const
void o_set_low (const scfx_index &, sc_enc)
void o_set_high (const scfx_index &, const scfx_index &, sc_enc, int=1)
void o_set (const scfx_index &, const scfx_index &, sc_enc, bool)
void o_invert (const scfx_index &)
bool q_bit (const scfx_index &) const
void q_clear (const scfx_index &)
void q_incr (const scfx_index &)
bool q_odd (const scfx_index &) const
bool q_zero (const scfx_index &) const
void resize_to (int, int=0)
int size () const
void toggle_tc ()
void quantization (const scfx_params &, bool &)
void overflow (const scfx_params &, bool &)
void round (int)

Private 変数

scfx_mant m_mant
int m_wp
int m_sign
state m_state
int m_msw
int m_lsw
bool m_r_flag

フレンド

void multiply (scfx_rep &, const scfx_rep &, const scfx_rep &, int=SC_DEFAULT_MAX_WL_)
scfx_repneg_scfx_rep (const scfx_rep &)
scfx_repmult_scfx_rep (const scfx_rep &, const scfx_rep &, int=SC_DEFAULT_MAX_WL_)
scfx_repdiv_scfx_rep (const scfx_rep &, const scfx_rep &, int=SC_DEFAULT_DIV_WL_)
scfx_repadd_scfx_rep (const scfx_rep &, const scfx_rep &, int=SC_DEFAULT_MAX_WL_)
scfx_repsub_scfx_rep (const scfx_rep &, const scfx_rep &, int=SC_DEFAULT_MAX_WL_)
scfx_replsh_scfx_rep (const scfx_rep &, int)
scfx_reprsh_scfx_rep (const scfx_rep &, int)
int cmp_scfx_rep (const scfx_rep &, const scfx_rep &)
scfx_repquantization_scfx_rep (const scfx_rep &, const scfx_params &, bool &)
scfx_repoverflow_scfx_rep (const scfx_rep &, const scfx_params &, bool &)
void align (const scfx_rep &, const scfx_rep &, int &, int &, scfx_mant_ref &, scfx_mant_ref &)
int compare_msw (const scfx_rep &, const scfx_rep &)
int compare_msw_ff (const scfx_rep &lhs, const scfx_rep &rhs)
void print_dec (scfx_string &, const scfx_rep &, int, sc_fmt)
void print_other (scfx_string &, const scfx_rep &, sc_numrep, int, sc_fmt, const scfx_params *)
int compare_abs (const scfx_rep &, const scfx_rep &)


説明

scfx_rep.h121 行で定義されています。


列挙型

enum sc_dt::scfx_rep::state [private]

列挙型の値:
normal 
infinity 
not_a_number 

scfx_rep.h123 行で定義されています。

00124     {
00125         normal,
00126         infinity,
00127         not_a_number
00128     };


コンストラクタとデストラクタ

sc_dt::scfx_rep::scfx_rep (  ) 

scfx_rep.cpp83 行で定義されています。

00084 : m_mant( min_mant ), m_r_flag( false )
00085 {
00086     set_zero();
00087 }

sc_dt::scfx_rep::scfx_rep ( int  a  )  [explicit]

scfx_rep.cpp89 行で定義されています。

00090 : m_mant( min_mant ), m_r_flag( false )
00091 {
00092     if( a != 0 )
00093     {
00094         m_mant.clear();
00095         m_wp = m_msw = m_lsw = 2;
00096         m_state = normal;
00097         if( a > 0 )
00098         {
00099             m_mant[2] = a;
00100             m_sign = 1;
00101         }
00102         else
00103         {
00104             m_mant[2] = -a;
00105             m_sign = -1;
00106         }
00107     }
00108     else
00109         set_zero();
00110 }

sc_dt::scfx_rep::scfx_rep ( unsigned int  a  )  [explicit]

scfx_rep.cpp112 行で定義されています。

00113 : m_mant( min_mant ), m_r_flag( false )
00114 {
00115     if( a != 0 )
00116     {
00117         m_mant.clear();
00118         m_wp = m_msw = m_lsw = 2;
00119         m_state = normal;
00120         m_mant[2] = a;
00121         m_sign = 1;
00122     }
00123     else
00124         set_zero();
00125 }

sc_dt::scfx_rep::scfx_rep ( long  a  )  [explicit]

scfx_rep.cpp127 行で定義されています。

00128 : m_mant( min_mant ), m_r_flag( false )
00129 {
00130     if( a != 0 )
00131     {
00132         m_mant.clear();
00133         m_state = normal;
00134         if ( a > 0 )
00135         {
00136             m_sign = 1;
00137         }
00138         else
00139         {
00140             a = -a;
00141             m_sign = -1;
00142         } 
00143 #       if defined(SC_LONG_64)
00144             m_wp = 1;
00145             m_mant[1] = static_cast<word>( a );
00146             m_mant[2] = static_cast<word>( a >> bits_in_word );
00147             find_sw();
00148 #       else
00149             m_wp = 2;
00150             m_msw = 2;
00151             m_lsw = 2;
00152             m_mant[2] = a;
00153 #       endif
00154 
00155     }
00156     else
00157         set_zero();
00158 }

sc_dt::scfx_rep::scfx_rep ( unsigned long  a  )  [explicit]

scfx_rep.cpp160 行で定義されています。

00161 : m_mant( min_mant ), m_r_flag( false )
00162 {
00163     if( a != 0 )
00164     {
00165         m_mant.clear();
00166         m_wp = m_msw = m_lsw = 2;
00167         m_state = normal;
00168 #       if defined(SC_LONG_64)
00169             m_wp = 1;
00170             m_mant[1] = static_cast<word>( a );
00171             m_mant[2] = static_cast<word>( a >> bits_in_word );
00172             find_sw();
00173 #       else
00174             m_wp = 2;
00175             m_msw = 2;
00176             m_lsw = 2;
00177             m_mant[2] = a;
00178 #       endif
00179         m_sign = 1;
00180     }
00181     else
00182         set_zero();
00183 }

sc_dt::scfx_rep::scfx_rep ( double  a  )  [explicit]

scfx_rep.cpp185 行で定義されています。

00186 : m_mant( min_mant ), m_wp( 0 ), m_state( normal ), m_msw( 0 ), m_lsw( 0 ),
00187   m_r_flag( false )
00188 {
00189     m_mant.clear();
00190 
00191     scfx_ieee_double id( a );
00192 
00193     m_sign = id.negative() ? -1 : 1;
00194 
00195     if( id.is_nan() )
00196         m_state = not_a_number;
00197     else if( id.is_inf() )
00198         m_state = infinity;
00199     else if( id.is_subnormal() )
00200     {
00201         m_mant[0] = id.mantissa1();
00202         m_mant[1] = id.mantissa0();
00203         normalize( id.exponent() + 1 - SCFX_IEEE_DOUBLE_M_SIZE );
00204     }
00205     else if( id.is_normal() )
00206     {
00207         m_mant[0] = id.mantissa1();
00208         m_mant[1] = id.mantissa0() | ( 1 << mantissa0_size );
00209         normalize( id.exponent() - SCFX_IEEE_DOUBLE_M_SIZE );
00210     }
00211 }

sc_dt::scfx_rep::scfx_rep ( const char *  s  )  [inline, explicit]

scfx_rep.h324 行で定義されています。

00325 : m_mant( min_mant ), m_wp( 2 ), m_sign( 1 ), m_state( normal ),
00326   m_r_flag( false )
00327 {
00328     from_string( s, SC_DEFAULT_CTE_WL_ );
00329 }

sc_dt::scfx_rep::scfx_rep ( int64  a  )  [explicit]

scfx_rep.cpp213 行で定義されています。

00214 : m_mant( min_mant ), m_r_flag( false )
00215 {
00216     if( a != 0 )
00217     {
00218         m_mant.clear();
00219         m_wp = 1;
00220         m_state = normal;
00221         if( a > 0 )
00222         {
00223             m_mant[1] = static_cast<word>( a );
00224             m_mant[2] = static_cast<word>( a >> bits_in_word );
00225             m_sign = 1;
00226         }
00227         else
00228         {
00229             m_mant[1] = static_cast<word>( -a );
00230             m_mant[2] = static_cast<word>( (-a) >> bits_in_word );
00231             m_sign = -1;
00232         }
00233         find_sw();
00234     }
00235     else
00236         set_zero();
00237 }

sc_dt::scfx_rep::scfx_rep ( uint64  a  )  [explicit]

scfx_rep.cpp239 行で定義されています。

00240 : m_mant( min_mant ), m_r_flag( false )
00241 {
00242     if( a != 0 )
00243     {
00244         m_mant.clear();
00245         m_wp = 1;
00246         m_state = normal;
00247         m_mant[1] = static_cast<word>( a );
00248         m_mant[2] = static_cast<word>( a >> bits_in_word );
00249         m_sign = 1;
00250         find_sw();
00251     }
00252     else
00253         set_zero();
00254 }

sc_dt::scfx_rep::scfx_rep ( const sc_signed a  )  [explicit]

scfx_rep.cpp256 行で定義されています。

00257 : m_mant( min_mant ), m_r_flag( false )
00258 {
00259     if( a.iszero() )
00260         set_zero();
00261     else
00262     {
00263         int words = n_word( a.length() );
00264         if( words > size() )
00265             resize_to( words );
00266         m_mant.clear();
00267         m_wp = 0;
00268         m_state = normal;
00269         if( a.sign() )
00270         {
00271             sc_signed a2 = -a;
00272             for( int i = 0; i < a2.length(); ++ i )
00273             {
00274                 if( a2[i] )
00275                 {
00276                     scfx_index x = calc_indices( i );
00277                     m_mant[x.wi()] |= 1 << x.bi();
00278                 }
00279             }
00280             m_sign = -1;
00281         }
00282         else
00283         {
00284             for( int i = 0; i < a.length(); ++ i )
00285             {
00286                 if( a[i] )
00287                 {
00288                     scfx_index x = calc_indices( i );
00289                     m_mant[x.wi()] |= 1 << x.bi();
00290                 }
00291             }
00292             m_sign = 1;
00293         }
00294         find_sw();
00295     }
00296 }

sc_dt::scfx_rep::scfx_rep ( const sc_unsigned a  )  [explicit]

scfx_rep.cpp298 行で定義されています。

00299 : m_mant( min_mant ), m_r_flag( false )
00300 {
00301     if( a.iszero() )
00302         set_zero();
00303     else
00304     {
00305         int words = n_word( a.length() );
00306         if( words > size() )
00307             resize_to( words );
00308         m_mant.clear();
00309         m_wp = 0;
00310         m_state = normal;
00311         for( int i = 0; i < a.length(); ++ i )
00312         {
00313             if( a[i] )
00314             {
00315                 scfx_index x = calc_indices( i );
00316                 m_mant[x.wi()] |= 1 << x.bi();
00317             }
00318         }
00319         m_sign = 1;
00320         find_sw();
00321     }
00322 }

sc_dt::scfx_rep::scfx_rep ( const scfx_rep a  ) 

scfx_rep.cpp327 行で定義されています。

00328 : m_mant( a.m_mant ), m_wp( a.m_wp ), m_sign( a.m_sign ), m_state( a.m_state ),
00329   m_msw( a.m_msw ), m_lsw( a.m_lsw ), m_r_flag( false )
00330 {}

sc_dt::scfx_rep::~scfx_rep (  )  [inline]

scfx_rep.h335 行で定義されています。

00336 {}


関数

void * sc_dt::scfx_rep::operator new ( std::size_t  size  ) 

scfx_rep.cpp350 行で定義されています。

00351 {
00352     const int ALLOC_SIZE = 1024;
00353 
00354     if( size != sizeof( scfx_rep ) )
00355         return ::operator new( size );
00356 
00357     if( ! list )
00358     {
00359         list = new scfx_rep_node[ALLOC_SIZE];
00360         for( int i = 0; i < ALLOC_SIZE - 1; i ++ )
00361             list[i].next = list + i + 1;
00362         list[ALLOC_SIZE - 1].next = 0;
00363     }
00364 
00365     scfx_rep* ptr = reinterpret_cast<scfx_rep*>( list->data );
00366     list = list->next;
00367 
00368     return ptr;
00369 }

void sc_dt::scfx_rep::operator delete ( void *  ptr,
std::size_t  size 
)

scfx_rep.cpp372 行で定義されています。

00373 {
00374     if( size != sizeof( scfx_rep ) )
00375     {
00376         ::operator delete( ptr );
00377         return;
00378     }
00379 
00380     scfx_rep_node* node = static_cast<scfx_rep_node*>( ptr );
00381     node->next = list;
00382     list = node;
00383 }

void sc_dt::scfx_rep::from_string ( const char *  s,
int  cte_wl 
)

scfx_rep.cpp404 行で定義されています。

00405 {
00406     SCFX_FAIL_IF_( s == 0 || *s == 0 );
00407 
00408     scfx_string s2;
00409     s2 += s;
00410     s2 += '\0';
00411 
00412     bool sign_char;
00413     m_sign = scfx_parse_sign( s, sign_char );
00414 
00415     sc_numrep numrep = scfx_parse_prefix( s );
00416 
00417     int base = 0;
00418 
00419     switch( numrep )
00420     {
00421         case SC_DEC:
00422         {
00423             base = 10;
00424             if( scfx_is_nan( s ) )
00425             {   // special case: NaN
00426                 m_state = not_a_number;
00427                 m_mant.clear(); /* to avoid Purify UMRs during assignment */
00428                 return;
00429             }
00430             if( scfx_is_inf( s ) )
00431             {   // special case: Infinity
00432                 m_state = infinity;
00433                 m_mant.clear(); /* to avoid Purify UMRs during assignment */
00434                 return;
00435             }
00436             break;
00437         }
00438         case SC_BIN:
00439         case SC_BIN_US:
00440         {
00441             SCFX_FAIL_IF_( sign_char );
00442             base = 2;
00443             break;
00444         }
00445         
00446         case SC_BIN_SM:
00447         {
00448             base = 2;
00449             break;
00450         }
00451         case SC_OCT:
00452         case SC_OCT_US:
00453         {
00454             SCFX_FAIL_IF_( sign_char );
00455             base = 8;
00456             break;
00457         }
00458         case SC_OCT_SM:
00459         {
00460             base = 8;
00461             break;
00462         }
00463         case SC_HEX:
00464         case SC_HEX_US:
00465         {
00466             SCFX_FAIL_IF_( sign_char );
00467             base = 16;
00468             break;
00469         }
00470         case SC_HEX_SM:
00471         {
00472             base = 16;
00473             break;
00474         }
00475         case SC_CSD:
00476         {
00477             SCFX_FAIL_IF_( sign_char );
00478             base = 2;
00479             scfx_csd2tc( s2 );
00480             s = (const char*) s2 + 4;
00481             numrep = SC_BIN;
00482             break;
00483         }
00484         default:;
00485     }
00486 
00487     //
00488     // find end of mantissa and count the digits and points
00489     //
00490 
00491     const char *end = s;
00492     bool based_point = false;
00493     int int_digits = 0;
00494     int frac_digits = 0;
00495 
00496     while( *end )
00497     {
00498         if( scfx_exp_start( end ) )
00499             break;
00500         
00501         if( *end == '.' )
00502         {
00503             SCFX_FAIL_IF_( based_point );
00504             based_point = true;
00505         }
00506         else
00507         {
00508             SCFX_FAIL_IF_( ! scfx_is_digit( *end, numrep ) );
00509             if( based_point )
00510                 frac_digits ++;
00511             else
00512                 int_digits ++;
00513         }
00514 
00515         ++ end;
00516     }
00517 
00518     SCFX_FAIL_IF_( int_digits == 0 && frac_digits == 0 );
00519 
00520     // [ exponent ]
00521     
00522     int exponent = 0;
00523 
00524     if( *end )
00525     {
00526         for( const char *e = end + 2; *e; ++ e )
00527             SCFX_FAIL_IF_( ! scfx_is_digit( *e, SC_DEC ) );
00528         exponent = atoi( end + 1 );
00529     }
00530 
00531     //
00532     // check if the mantissa is negative
00533     //
00534 
00535     bool mant_is_neg = false;
00536 
00537     switch( numrep )
00538     {
00539         case SC_BIN:
00540         case SC_OCT:
00541         case SC_HEX:
00542         {
00543             const char* p = s;
00544             if( *p == '.' )
00545                 ++ p;
00546 
00547             mant_is_neg = ( scfx_to_digit( *p, numrep ) >= ( base >> 1 ) );
00548 
00549             break;
00550         }
00551         default:
00552             ;
00553     }
00554 
00555     //
00556     // convert the mantissa
00557     //
00558 
00559     switch( base )
00560     {
00561         case 2:
00562         {
00563             int bit_offset = exponent % bits_in_word;
00564             int word_offset = exponent / bits_in_word;
00565 
00566             int_digits += bit_offset;
00567             frac_digits -= bit_offset;
00568 
00569             int words = n_word( int_digits ) + n_word( frac_digits );
00570             if( words > size() )
00571                 resize_to( words );
00572             m_mant.clear();
00573 
00574             int j = n_word( frac_digits ) * bits_in_word + int_digits - 1;
00575             
00576             for( ; s < end; s ++ )
00577             {
00578                 switch( *s )
00579                 {
00580                     case '1':
00581                         set_bin( j );
00582                     case '0':
00583                         j --;
00584                     case '.':
00585                         break;
00586                     default:
00587                         SCFX_FAIL_IF_( true );  // should not happen
00588                 }
00589             }
00590 
00591             m_wp = n_word( frac_digits ) - word_offset;
00592             break;
00593         }
00594         case 8:
00595         {
00596             exponent *= 3;
00597             int_digits *= 3;
00598             frac_digits *= 3;
00599 
00600             int bit_offset = exponent % bits_in_word;
00601             int word_offset = exponent / bits_in_word;
00602 
00603             int_digits += bit_offset;
00604             frac_digits -= bit_offset;
00605 
00606             int words = n_word( int_digits ) + n_word( frac_digits );
00607             if( words > size() )
00608                 resize_to( words );
00609             m_mant.clear();
00610 
00611             int j = n_word( frac_digits ) * bits_in_word + int_digits - 3;
00612             
00613             for( ; s < end; s ++ )
00614             {
00615                 switch( *s )
00616                 {
00617                     case '7': case '6': case '5': case '4':
00618                     case '3': case '2': case '1':
00619                         set_oct( j, *s - '0' );
00620                     case '0':
00621                         j -= 3;
00622                     case '.':
00623                         break;
00624                     default:
00625                         SCFX_FAIL_IF_( true );  // should not happen
00626                 }
00627             }
00628 
00629             m_wp = n_word( frac_digits ) - word_offset;
00630             break;
00631         }
00632         case 10:
00633         {
00634             word carry, temp;
00635             int length = int_digits + frac_digits;
00636             resize_to( sc_max( min_mant, n_word( 4 * length ) ) );
00637 
00638             m_mant.clear();
00639             m_msw = m_lsw = 0;
00640             
00641             for( ; s < end; s ++ )
00642             {
00643                 switch( *s )
00644                 {
00645                     case '9': case '8': case '7': case '6': case '5':
00646                     case '4': case '3': case '2': case '1': case '0':
00647                         multiply_by_ten();
00648                         carry = *s - '0';
00649                         for ( int i = 0; carry && i < m_mant.size(); i++ )
00650                         {
00651                             temp = m_mant[i];
00652                             temp += carry;                          
00653                             carry = temp < m_mant[i];
00654                             m_mant[i] = temp;
00655                         }
00656                     case '.':
00657                         break;
00658                     default:
00659                         SCFX_FAIL_IF_( true );  // should not happen
00660                 }
00661             }
00662             
00663             m_wp = 0;
00664             find_sw();
00665 
00666             int denominator = frac_digits - exponent;
00667             
00668             if( denominator )
00669             {
00670                 scfx_rep frac_num = pow10_fx( denominator );
00671                 scfx_rep* temp_num =
00672                     div_scfx_rep( const_cast<const scfx_rep&>( *this ),
00673                                    frac_num, cte_wl );
00674                 *this = *temp_num;
00675                 delete temp_num;
00676             }
00677 
00678             break;
00679         }
00680         case 16:
00681         {
00682             exponent *= 4;
00683             int_digits *= 4;
00684             frac_digits *= 4;
00685 
00686             int bit_offset = exponent % bits_in_word;
00687             int word_offset = exponent / bits_in_word;
00688 
00689             int_digits += bit_offset;
00690             frac_digits -= bit_offset;
00691 
00692             int words = n_word( int_digits ) + n_word( frac_digits );
00693             if( words > size() )
00694                 resize_to( words );
00695             m_mant.clear();
00696 
00697             int j = n_word( frac_digits ) * bits_in_word + int_digits - 4;
00698             
00699             for( ; s < end; s ++ )
00700             {
00701                 switch( *s )
00702                 {
00703                     case 'f': case 'e': case 'd': case 'c': case 'b': case 'a':
00704                        set_hex( j, *s - 'a' + 10 );
00705                        j -= 4;
00706                        break;
00707                     case 'F': case 'E': case 'D': case 'C': case 'B': case 'A':
00708                        set_hex( j, *s - 'A' + 10 );
00709                        j -= 4;
00710                        break;
00711                     case '9': case '8': case '7': case '6': case '5':
00712                     case '4': case '3': case '2': case '1':
00713                        set_hex( j, *s - '0' );
00714                     case '0':
00715                        j -= 4;
00716                     case '.':
00717                        break;
00718                    default:
00719                        SCFX_FAIL_IF_( true );  // should not happen
00720                 }
00721             }
00722 
00723             m_wp = n_word( frac_digits ) - word_offset;
00724             break;
00725         }
00726     }
00727 
00728     m_state = normal;
00729     find_sw();
00730 
00731     //
00732     // two's complement of mantissa if it is negative
00733     //
00734 
00735     if( mant_is_neg )
00736     {
00737         m_mant[m_msw] |=  -1 << scfx_find_msb( m_mant[m_msw] );
00738         for( int i = m_msw + 1; i < m_mant.size(); ++ i )
00739             m_mant[i] = static_cast<word>( -1 );
00740         complement( m_mant, m_mant, m_mant.size() );
00741         inc( m_mant );
00742         m_sign *= -1;
00743         find_sw();
00744     }
00745 }

double sc_dt::scfx_rep::to_double (  )  const

scfx_rep.cpp758 行で定義されています。

00759 {
00760     scfx_ieee_double id;
00761 
00762     // handle special cases
00763 
00764     if( is_nan() )
00765     {
00766         id.set_nan();
00767         return id;
00768     }
00769 
00770     if( is_inf() )
00771     {
00772         id.set_inf();
00773         id.negative( m_sign < 0 );
00774         return id;
00775     }
00776 
00777     if( is_zero() )
00778     {
00779         id = 0.;
00780         id.negative( m_sign < 0 );
00781         return id;
00782     }
00783 
00784     int msb = scfx_find_msb( m_mant[m_msw] );
00785 
00786     int exp = (m_msw - m_wp) * bits_in_word + msb;
00787 
00788     if( exp > SCFX_IEEE_DOUBLE_E_MAX )
00789     {
00790         id.set_inf();
00791         id.negative( m_sign < 0 );
00792         return id;
00793     }
00794 
00795     if( exp < SCFX_IEEE_DOUBLE_E_MIN
00796         - static_cast<int>( SCFX_IEEE_DOUBLE_M_SIZE ) )
00797     {
00798         id = 0.;
00799         return id;
00800     }
00801  
00802     int shift = mantissa0_size - msb;
00803 
00804     unsigned int m0;
00805     unsigned int m1 = 0;
00806     unsigned int guard = 0;
00807 
00808     if( shift == 0 )
00809     {
00810         m0 = m_mant[m_msw] & ~( 1 << mantissa0_size );
00811         if( m_msw > m_lsw )
00812         {
00813             m1 = m_mant[m_msw - 1];
00814             if( m_msw - 1 > m_lsw )
00815                 guard = m_mant[m_msw - 2] >> ( bits_in_word - 1 );
00816         }
00817     }
00818     else if( shift < 0 )
00819     {
00820         m0 = ( m_mant[m_msw] >> -shift ) & ~( 1 << mantissa0_size );
00821         m1 = m_mant[m_msw] << ( bits_in_word + shift );
00822         if( m_msw > m_lsw )
00823         {
00824             m1 |= m_mant[m_msw - 1] >> -shift;
00825             guard = ( m_mant[m_msw - 1] >> ( -shift - 1 ) ) & 1;
00826         }
00827     }
00828     else
00829     {
00830         m0 = ( m_mant[m_msw] << shift ) & ~( 1 << mantissa0_size );
00831         if( m_msw > m_lsw )
00832         {
00833             m0 |= m_mant[m_msw - 1] >> ( bits_in_word - shift );
00834             m1 = m_mant[m_msw - 1] << shift;
00835             if( m_msw - 1 > m_lsw )
00836             {
00837                 m1 |= m_mant[m_msw - 2] >> ( bits_in_word - shift );
00838                 guard = ( m_mant[m_msw - 2] >> (bits_in_word - shift - 1) )
00839                       & 1;
00840             }      
00841         }
00842     }
00843 
00844     if( exp < SCFX_IEEE_DOUBLE_E_MIN )
00845     {
00846         m0 |= ( 1 << mantissa0_size );
00847 
00848         int subnormal_shift = SCFX_IEEE_DOUBLE_E_MIN - exp;
00849 
00850         if( subnormal_shift < bits_in_word )
00851         {
00852             m1 = m1 >> subnormal_shift
00853                | m0 << ( bits_in_word - subnormal_shift );
00854             m0 = m0 >> subnormal_shift;
00855         }
00856         else
00857         {
00858             m1 = m0 >> ( subnormal_shift - bits_in_word );
00859             m0 = 0;
00860         }
00861 
00862         guard = 0;
00863 
00864         exp = SCFX_IEEE_DOUBLE_E_MIN - 1;
00865     }
00866 
00867     id.mantissa0( m0 );
00868     id.mantissa1( m1 );
00869     id.exponent( exp );
00870     id.negative( m_sign < 0 );
00871 
00872     double result = id;
00873 
00874     if( guard != 0 )
00875         result += m_sign * scfx_pow2( exp - SCFX_IEEE_DOUBLE_M_SIZE );
00876 
00877     return result;
00878 }

const char * sc_dt::scfx_rep::to_string ( sc_numrep  numrep,
int  w_prefix,
sc_fmt  fmt,
const scfx_params params = 0 
) const

scfx_rep.cpp1193 行で定義されています。

01195 {
01196     static scfx_string s;
01197 
01198     s.clear();
01199 
01200     if( is_nan() )
01201         scfx_print_nan( s );
01202     else if( is_inf() )
01203         scfx_print_inf( s, is_neg() );
01204     else if( is_neg() && ! is_zero() &&
01205              ( numrep == SC_BIN_US ||
01206                numrep == SC_OCT_US ||
01207                numrep == SC_HEX_US ) )
01208         s += "negative";
01209     else if( numrep == SC_DEC || numrep == SC_NOBASE )
01210         sc_dt::print_dec( s, *this, w_prefix, fmt );
01211     else
01212         sc_dt::print_other( s, *this, numrep, w_prefix, fmt, params );
01213 
01214     return s;
01215 }

void sc_dt::scfx_rep::operator= ( const scfx_rep f  )  [inline]

scfx_rep.h343 行で定義されています。

00344 {
00345     if( &f != this )
00346     {
00347         m_mant  = f.m_mant;
00348         m_wp    = f.m_wp;
00349         m_sign  = f.m_sign;
00350         m_state = f.m_state;
00351         m_msw   = f.m_msw;
00352         m_lsw   = f.m_lsw;
00353         round( SC_DEFAULT_MAX_WL_ );
00354     }
00355 }

void sc_dt::scfx_rep::lshift ( int  n  ) 

scfx_rep.cpp1704 行で定義されています。

01705 {
01706     if( n == 0 )
01707         return;
01708 
01709     if( n < 0 )
01710     {
01711         rshift( -n );
01712         return;
01713     }
01714 
01715     if( is_normal() )
01716     {
01717         int shift_bits  = n % bits_in_word;
01718         int shift_words = n / bits_in_word;
01719 
01720         // resize if needed
01721         if( m_msw == size() - 1 &&
01722             scfx_find_msb( m_mant[m_msw] ) >= bits_in_word - shift_bits )
01723             resize_to( size() + 1, 1 );
01724 
01725         // do it
01726         m_wp -= shift_words;
01727         shift_left( shift_bits );
01728         find_sw();
01729     }
01730 }

void sc_dt::scfx_rep::rshift ( int  n  ) 

scfx_rep.cpp1738 行で定義されています。

01739 {
01740     if( n == 0 )
01741         return;
01742 
01743     if( n < 0 )
01744     {
01745         lshift( -n );
01746         return;
01747     }
01748 
01749     if( is_normal() )
01750     {
01751         int shift_bits  = n % bits_in_word;
01752         int shift_words = n / bits_in_word;
01753 
01754         // resize if needed
01755         if( m_lsw == 0 && scfx_find_lsb( m_mant[m_lsw] ) < shift_bits )
01756             resize_to( size() + 1, -1 );
01757 
01758         // do it
01759         m_wp += shift_words;
01760         shift_right( shift_bits );
01761         find_sw();
01762     }
01763 }

void sc_dt::scfx_rep::cast ( const scfx_params params,
bool &  q_flag,
bool &  o_flag 
)

scfx_rep.cpp2202 行で定義されています。

02203 {
02204     q_flag = false;
02205     o_flag = false;
02206 
02207     // check for special cases
02208     
02209     if( is_zero() )
02210     {
02211         if( is_neg() )
02212             m_sign = 1;
02213         return;
02214     }
02215 
02216     // perform casting
02217 
02218     quantization( params, q_flag );
02219     overflow( params, o_flag );
02220 
02221     // check for special case: -0
02222 
02223     if( is_zero() && is_neg() )
02224         m_sign = 1;
02225 }

bool sc_dt::scfx_rep::is_neg (  )  const [inline]

scfx_rep.h402 行で定義されています。

00403 {
00404     return ( m_sign == -1 );
00405 }

bool sc_dt::scfx_rep::is_zero (  )  const [inline]

scfx_rep.h409 行で定義されています。

00410 {
00411     if( m_state != normal )
00412         return false;
00413 
00414     for( int i = 0; i < size(); i ++ )
00415     {
00416         if( m_mant[i] )
00417             return false;
00418     }
00419 
00420     return true;
00421 }

bool sc_dt::scfx_rep::is_nan (  )  const [inline]

scfx_rep.h425 行で定義されています。

00426 {
00427     return ( m_state == not_a_number );
00428 }

bool sc_dt::scfx_rep::is_inf (  )  const [inline]

scfx_rep.h432 行で定義されています。

00433 {
00434     return ( m_state == infinity );
00435 }

bool sc_dt::scfx_rep::is_normal (  )  const [inline]

scfx_rep.h439 行で定義されています。

00440 {
00441     return ( m_state == normal );
00442 }

void sc_dt::scfx_rep::set_zero ( int  sign = 1  )  [inline]

scfx_rep.h295 行で定義されています。

00296 {
00297     m_mant.clear();
00298     m_wp = m_msw = m_lsw = 0;
00299     m_sign = sign;
00300     m_state = normal;
00301 }

void sc_dt::scfx_rep::set_nan (  )  [inline]

scfx_rep.h305 行で定義されています。

00306 {
00307     m_mant.resize_to( min_mant );
00308     m_state = not_a_number;
00309 }

void sc_dt::scfx_rep::set_inf ( int  sign  )  [inline]

scfx_rep.h313 行で定義されています。

00314 {
00315     m_mant.resize_to( min_mant );
00316     m_state = infinity;
00317     m_sign = sign;
00318 }

bool sc_dt::scfx_rep::get_bit ( int  i  )  const

scfx_rep.cpp2582 行で定義されています。

02583 {
02584     if( ! is_normal() )
02585         return false;
02586 
02587     scfx_index x = calc_indices( i );
02588 
02589     if( x.wi() >= size() )
02590         return is_neg();
02591 
02592     if( x.wi() < 0 )
02593         return false;
02594 
02595     const_cast<scfx_rep*>( this )->toggle_tc();
02596 
02597     bool result = ( m_mant[x.wi()] & ( 1 << x.bi() ) ) != 0;
02598 
02599     const_cast<scfx_rep*>( this )->toggle_tc();
02600 
02601     return result;
02602 }

bool sc_dt::scfx_rep::set ( int  i,
const scfx_params params 
)

scfx_rep.cpp2612 行で定義されています。

02613 {
02614     if( ! is_normal() )
02615         return false;
02616 
02617     scfx_index x = calc_indices( i );
02618 
02619     if( x.wi() >= size() )
02620     {
02621         if( is_neg() )
02622             return true;
02623         else
02624             resize_to( x.wi() + 1, 1 );
02625     }
02626     else if( x.wi() < 0 )
02627     {
02628         resize_to( size() - x.wi(), -1 );
02629         x.wi( 0 );
02630     }
02631 
02632     toggle_tc();
02633 
02634     m_mant[x.wi()] |= 1 << x.bi();
02635 
02636     if( i == params.iwl() - 1 )
02637         o_extend( x, params.enc() );  // sign extension
02638 
02639     toggle_tc();
02640 
02641     find_sw();
02642 
02643     return true;
02644 }

bool sc_dt::scfx_rep::clear ( int  i,
const scfx_params params 
)

scfx_rep.cpp2654 行で定義されています。

02655 {
02656     if( ! is_normal() )
02657         return false;
02658 
02659     scfx_index x = calc_indices( i );
02660 
02661     if( x.wi() >= size() )
02662     {
02663         if( ! is_neg() )
02664             return true;
02665         else
02666             resize_to( x.wi() + 1, 1 );
02667     }
02668     else if( x.wi() < 0 )
02669         return true;
02670 
02671     toggle_tc();
02672 
02673     m_mant[x.wi()] &= ~( 1 << x.bi() );
02674 
02675     if( i == params.iwl() - 1 )
02676         o_extend( x, params.enc() );  // sign extension
02677 
02678     toggle_tc();
02679 
02680     find_sw();
02681 
02682     return true;
02683 }

bool sc_dt::scfx_rep::get_slice ( int  i,
int  j,
const scfx_params ,
sc_bv_base bv 
) const

scfx_rep.cpp2691 行で定義されています。

02693 {
02694     if( is_nan() || is_inf() )
02695         return false;
02696 
02697     // get the bits
02698 
02699     int l = j;
02700     for( int k = 0; k < bv.length(); ++ k )
02701     {
02702         bv[k] = get_bit( l );
02703 
02704         if( i >= j )
02705             ++ l;
02706         else
02707             -- l;
02708     }
02709 
02710     return true;
02711 }

bool sc_dt::scfx_rep::set_slice ( int  i,
int  j,
const scfx_params params,
const sc_bv_base bv 
)

scfx_rep.cpp2714 行で定義されています。

02716 {
02717     if( is_nan() || is_inf() )
02718         return false;
02719 
02720     // set the bits
02721 
02722     int l = j;
02723     for( int k = 0; k < bv.length(); ++ k )
02724     {
02725         if( bv[k].to_bool() )
02726             set( l, params );
02727         else
02728             clear( l, params );
02729 
02730         if( i >= j )
02731             ++ l;
02732         else
02733             -- l;
02734     }
02735 
02736     return true;
02737 }

void sc_dt::scfx_rep::print ( ::std::ostream &  os  )  const

scfx_rep.cpp2745 行で定義されています。

02746 {
02747     os << to_string( SC_DEC, -1, SC_E );
02748 }

void sc_dt::scfx_rep::dump ( ::std::ostream &  os  )  const

scfx_rep.cpp2756 行で定義されています。

02757 {
02758     os << "scfx_rep" << ::std::endl;
02759     os << "(" << ::std::endl;
02760 
02761     os << "mant  =" << ::std::endl;
02762     for( int i = size() - 1; i >= 0; i -- )
02763     {
02764         char buf[BUFSIZ];
02765         std::sprintf( buf, " %d: %10u (%8x)", i, (int) m_mant[i], (int) m_mant[i] );
02766         os << buf << ::std::endl;
02767     }
02768 
02769     os << "wp    = " << m_wp << ::std::endl;
02770     os << "sign  = " << m_sign << ::std::endl;
02771 
02772     os << "state = ";
02773     switch( m_state )
02774     {
02775         case normal:
02776             os << "normal";
02777             break;
02778         case infinity:
02779             os << "infinity";
02780             break;
02781         case not_a_number:
02782             os << "not_a_number";
02783             break;
02784         default:
02785             os << "unknown";
02786     }
02787     os << ::std::endl;
02788 
02789     os << "msw   = " << m_msw << ::std::endl;
02790     os << "lsw   = " << m_lsw << ::std::endl;
02791 
02792     os << ")" << ::std::endl;
02793 }

void sc_dt::scfx_rep::get_type ( int &  wl,
int &  iwl,
sc_enc enc 
) const

scfx_rep.cpp2801 行で定義されています。

02802 {
02803     if( is_nan() || is_inf() )
02804     {
02805         wl  = 0;
02806         iwl = 0;
02807         enc = SC_TC_;
02808         return;
02809     }
02810 
02811     if( is_zero() )
02812     {
02813         wl  = 1;
02814         iwl = 1;
02815         enc = SC_US_;
02816         return;
02817     }
02818 
02819     int msb = ( m_msw - m_wp ) * bits_in_word
02820             + scfx_find_msb( m_mant[ m_msw ] ) + 1;
02821     while( get_bit( msb ) == get_bit( msb - 1 ) )
02822     {
02823         -- msb;
02824     }
02825 
02826     int lsb = ( m_lsw - m_wp ) * bits_in_word
02827             + scfx_find_lsb( m_mant[ m_lsw ] );
02828 
02829     if( is_neg() )
02830     {
02831         wl  = msb - lsb + 1;
02832         iwl = msb + 1;
02833         enc = SC_TC_;
02834     }
02835     else
02836     {
02837         wl  = msb - lsb;
02838         iwl = msb;
02839         enc = SC_US_;
02840     }
02841 }

bool sc_dt::scfx_rep::rounding_flag (  )  const [inline]

scfx_rep.h468 行で定義されています。

00469 {
00470     return m_r_flag;
00471 }

unsigned int sc_dt::scfx_rep::divide_by_ten (  )  [private]

scfx_rep.cpp2339 行で定義されています。

02340 {
02341 #if defined( SC_BIG_ENDIAN )
02342     half_word* hw = (half_word*) &m_mant[m_msw];
02343 #elif defined( SC_LITTLE_ENDIAN )
02344     half_word* hw = ( (half_word*) &m_mant[m_msw] ) + 1;
02345 #endif
02346 
02347     unsigned int remainder = 0;
02348 
02349     word_short ls;
02350     ls.l = 0;
02351 
02352 #if defined( SC_BIG_ENDIAN )
02353     for( int i = 0, end = ( m_msw - m_wp + 1 ) * 2; i < end; i ++ )
02354 #elif defined( SC_LITTLE_ENDIAN )
02355     for( int i = 0, end = -( m_msw - m_wp + 1 ) * 2; i > end; i -- )
02356 #endif
02357     {
02358         ls.s.u = static_cast<half_word>( remainder );
02359         ls.s.l = hw[i];
02360         remainder = ls.l % 10;
02361         ls.l /= 10;
02362         hw[i] = ls.s.l;
02363     }
02364 
02365     return remainder;
02366 }

int sc_dt::scfx_rep::find_lsw (  )  const [inline, private]

scfx_rep.h778 行で定義されています。

00779 {
00780     for( int i = 0; i < size(); i ++ )
00781     {
00782         if( m_mant[i] )
00783             return i;
00784     }
00785     return 0;
00786 }

int sc_dt::scfx_rep::find_msw (  )  const [inline, private]

scfx_rep.h790 行で定義されています。

00791 {
00792     for( int i = size() - 1; i >= 0; i -- )
00793     {
00794         if( m_mant[i] )
00795             return i;
00796     }
00797     return 0;
00798 }

void sc_dt::scfx_rep::find_sw (  )  [inline, private]

scfx_rep.h802 行で定義されています。

00803 {
00804     m_lsw = find_lsw();
00805     m_msw = find_msw();
00806 }

void sc_dt::scfx_rep::multiply_by_ten (  )  [private]

scfx_rep.cpp2374 行で定義されています。

02375 {
02376     int size = m_mant.size() + 1;
02377 
02378     scfx_mant mant8( size );
02379     scfx_mant mant2( size );
02380 
02381     size --;
02382 
02383     mant8[size] = (m_mant[size - 1] >> (bits_in_word - 3));
02384     mant2[size] = (m_mant[size - 1] >> (bits_in_word - 1));
02385 
02386     while( -- size )
02387     {
02388         mant8[size] = ( m_mant[size] << 3 ) |
02389                       ( m_mant[size - 1] >> ( bits_in_word - 3 ) );
02390         mant2[size] = ( m_mant[size] << 1 ) |
02391                       ( m_mant[size - 1] >> ( bits_in_word - 1 ) );
02392     }
02393 
02394     mant8[0] = ( m_mant[0] << 3 );
02395     mant2[0] = ( m_mant[0] << 1 );
02396 
02397     add_mants( m_mant.size(), m_mant, mant8, mant2 );
02398 
02399 #if 0
02400     for( int i = size() - 1; i > 0; i -- )
02401     {
02402         m_mant[i] = ( m_mant[i] << 3 ) |
02403                     ( m_mant[i-1] >> ( bits_in_word - 3 ) )
02404                   + ( m_mant[i] << 1 ) |
02405                     ( m_mant[i-1] >> ( bits_in_word - 1 ) );
02406     }
02407     m_mant[0] = ( m_mant[0] << 3 ) + ( m_mant[0] << 1 );
02408 #endif
02409 }

void sc_dt::scfx_rep::normalize ( int  exponent  )  [private]

scfx_rep.cpp2417 行で定義されています。

02418 {
02419     int shift = exponent % bits_in_word;
02420     if( shift < 0 )
02421     {
02422         shift += bits_in_word;
02423     }
02424 
02425     if( shift )
02426     {
02427         shift_left( shift );
02428     }
02429 
02430     find_sw();
02431 
02432     m_wp = (shift - exponent) / bits_in_word;
02433 }

scfx_mant * sc_dt::scfx_rep::resize ( int  new_size,
int  new_wp 
) const [private]

scfx_rep.cpp2441 行で定義されています。

02442 {
02443     scfx_mant *result = new scfx_mant( new_size );
02444 
02445     result->clear();
02446 
02447     int shift = new_wp - m_wp;
02448 
02449     for( int j = m_lsw; j <= m_msw; j ++ )
02450     {
02451         (*result)[j+shift] = m_mant[j];
02452     }
02453 
02454     return result;
02455 }

void sc_dt::scfx_rep::set_bin ( int  i  )  [private]

scfx_rep.cpp2463 行で定義されています。

02464 {
02465     m_mant[i >> 5] |= 1 << ( i & 31 );
02466 }

void sc_dt::scfx_rep::set_oct ( int  i,
int  n 
) [private]

scfx_rep.cpp2474 行で定義されています。

02475 {
02476     if( n & 1 )
02477     {
02478         m_mant[i >> 5] |= 1 << ( i & 31 );
02479     }
02480     i ++;
02481     if( n & 2 )
02482     {
02483         m_mant[i >> 5] |= 1 << ( i & 31 );
02484     }
02485     i ++;
02486     if( n & 4 )
02487     {
02488         m_mant[i >> 5] |= 1 << ( i & 31 );
02489     }
02490 }

void sc_dt::scfx_rep::set_hex ( int  i,
int  n 
) [private]

scfx_rep.cpp2498 行で定義されています。

02499 {
02500     if( n & 1 )
02501     {
02502         m_mant[i >> 5] |= 1 << ( i & 31 );
02503     }
02504     i ++;
02505     if( n & 2 )
02506     {
02507         m_mant[i >> 5] |= 1 << ( i & 31 );
02508     }
02509     i ++;
02510     if( n & 4 )
02511     {
02512         m_mant[i >> 5] |= 1 << ( i & 31 );
02513     }
02514     i ++;
02515     if( n & 8 )
02516     {
02517         m_mant[i >> 5] |= 1 << ( i & 31 );
02518     }
02519 }

void sc_dt::scfx_rep::shift_left ( int  n  )  [private]

scfx_rep.cpp2529 行で定義されています。

02530 {
02531     if( n != 0 )
02532     {
02533         int shift_left  = n;
02534         int shift_right = bits_in_word - n;
02535 
02536         SC_ASSERT_( !(m_mant[size()-1] >> shift_right),
02537                     "shift_left overflow" );
02538 
02539         for( int i = size() - 1; i > 0; i -- )
02540         {
02541             m_mant[i] = ( m_mant[i] << shift_left ) |
02542                        ( m_mant[i-1] >> shift_right );
02543         }
02544         m_mant[0] <<= shift_left;
02545     }
02546 }

void sc_dt::scfx_rep::shift_right ( int  n  )  [private]

scfx_rep.cpp2556 行で定義されています。

02557 {
02558     if( n != 0 )
02559     {
02560         int shift_left  = bits_in_word - n;
02561         int shift_right = n;
02562 
02563         SC_ASSERT_( !(m_mant[0] << shift_left), "shift_right overflow" );
02564 
02565         for( int i = 0; i < size() - 1; i ++ )
02566         {
02567             m_mant[i] = ( m_mant[i] >> shift_right ) |
02568                        ( m_mant[i+1] << shift_left );
02569         }
02570         m_mant[size()-1] >>= shift_right;
02571     }
02572 }

const scfx_index sc_dt::scfx_rep::calc_indices ( int  n  )  const [inline, private]

scfx_rep.h489 行で定義されています。

00490 {
00491     int wi = n / bits_in_word + m_wp;
00492     int bi = n % bits_in_word;
00493 
00494     if( bi < 0 )
00495     {
00496         bi += bits_in_word;
00497         -- wi;
00498     }
00499 
00500     return scfx_index( wi, bi );
00501 }

void sc_dt::scfx_rep::o_extend ( const scfx_index x,
sc_enc  enc 
) [inline, private]

scfx_rep.h505 行で定義されています。

00506 {
00507     int wi = x.wi();
00508     int bi = x.bi();
00509 
00510     SC_ASSERT_( wi >= 0 && wi < size(), "word index out of range" );
00511     
00512     if( enc == SC_US_ || ( m_mant[wi] & ( ((word)1) << bi ) ) == 0 )
00513     {
00514         if( bi != bits_in_word - 1 )
00515             m_mant[wi] &= ~( ((word)-1) << ( bi + 1 ) );
00516         for( int i = wi + 1; i < size(); ++ i )
00517             m_mant[i] = 0;
00518         m_sign = 1;
00519     }
00520     else
00521     {
00522         if( bi != bits_in_word - 1 )
00523             m_mant[wi] |= ( ((word)-1) << ( bi + 1 ) );
00524         for( int i = wi + 1; i < size(); ++ i )
00525             m_mant[i] = static_cast<word>( -1 );
00526         m_sign = -1;
00527     }
00528 }

bool sc_dt::scfx_rep::o_bit_at ( const scfx_index x  )  const [inline, private]

scfx_rep.h532 行で定義されています。

00533 {
00534     int wi = x.wi();
00535     int bi = x.bi();
00536     
00537     SC_ASSERT_( wi >= 0 && wi < size(), "word index out of range" );
00538 
00539     return ( m_mant[wi] & ( ((word)1) << bi ) ) != 0;
00540 }

bool sc_dt::scfx_rep::o_zero_left ( const scfx_index x  )  const [inline, private]

scfx_rep.h544 行で定義されています。

00545 {
00546     int wi = x.wi();
00547     int bi = x.bi();
00548 
00549     SC_ASSERT_( wi >= 0 && wi < size(), "word index out of range" );
00550 
00551     bool zero = true;
00552     if( bi != bits_in_word - 1 )
00553         zero = ( m_mant[wi] & ( ((word)-1) << ( bi + 1 ) ) ) == 0;
00554     for( int i = wi + 1; i < size(); ++ i )
00555         zero = zero && m_mant[i] == 0;
00556 
00557     return zero;
00558 }

bool sc_dt::scfx_rep::o_zero_right ( const scfx_index x  )  const [inline, private]

scfx_rep.h562 行で定義されています。

00563 {
00564     int wi = x.wi();
00565     int bi = x.bi();
00566 
00567     SC_ASSERT_( wi >= 0 && wi < size(), "word index out of range" );
00568 
00569     bool zero = ( m_mant[wi] & ~( ((word)-1) << bi ) ) == 0;
00570     for( int i = wi - 1; i >= 0; -- i )
00571         zero = zero && m_mant[i] == 0;
00572 
00573     return zero;
00574 }

void sc_dt::scfx_rep::o_set_low ( const scfx_index x,
sc_enc  enc 
) [inline, private]

scfx_rep.h578 行で定義されています。

00579 {
00580     int wi = x.wi();
00581     int bi = x.bi();
00582 
00583     SC_ASSERT_( wi >= 0 && wi < size(), "word index out of range" );
00584 
00585     m_mant.clear();
00586 
00587     if( enc == SC_TC_ )
00588     {
00589         m_mant[wi] |= ( ((word)1) << bi );
00590         m_sign = -1;
00591     }
00592     else
00593         m_sign = 1;
00594 }

void sc_dt::scfx_rep::o_set_high ( const scfx_index x,
const scfx_index x2,
sc_enc  enc,
int  sign = 1 
) [inline, private]

scfx_rep.h598 行で定義されています。

00600 {
00601     int wi = x.wi();
00602     int bi = x.bi();
00603     int wi2 = x2.wi();
00604     int bi2 = x2.bi();
00605 
00606     SC_ASSERT_( wi >= 0 && wi < size(), "word index out of range" );
00607     SC_ASSERT_( wi2 >= 0 && wi2 < size(), "word index out of range" );
00608     
00609     int i;
00610 
00611     for( i = 0; i < size(); ++ i )
00612         m_mant[i] = static_cast<word>( -1 );
00613 
00614     m_mant[wi] &= ~( ((word)-1) << bi );
00615     for( i = wi + 1; i < size(); ++ i )
00616         m_mant[i] = 0;
00617 
00618     m_mant[wi2] &= ( ((word)-1) << bi2 );
00619     for( i = wi2 - 1; i >= 0; -- i )
00620         m_mant[i] = 0;
00621     
00622     if( enc == SC_TC_ )
00623         m_sign = sign;
00624     else
00625     {
00626         m_mant[wi] |= ( ((word)1) << bi );
00627         m_sign = 1;
00628     }
00629 }

void sc_dt::scfx_rep::o_set ( const scfx_index x,
const scfx_index x3,
sc_enc  enc,
bool  under 
) [inline, private]

scfx_rep.h633 行で定義されています。

00635 {
00636     int wi = x.wi();
00637     int bi = x.bi();
00638     int wi3 = x3.wi();
00639     int bi3 = x3.bi();
00640     
00641     SC_ASSERT_( wi >= 0 && wi < size(), "word index out of range" );
00642     SC_ASSERT_( wi3 >= 0 && wi3 < size(), "word index out of range" );
00643 
00644     if( bi3 != bits_in_word - 1 )
00645     {
00646         if( under )
00647             m_mant[wi3] &= ~( ((word)-1) << ( bi3 + 1 ) );
00648         else
00649             m_mant[wi3] |= ( ((word)-1) << ( bi3 + 1 ) );
00650     }
00651     for( int i = wi3 + 1; i < size(); ++ i )
00652     {
00653         if( under )
00654             m_mant[i] = 0;
00655         else
00656             m_mant[i] = static_cast<word>( -1 );
00657     }
00658         
00659     if( enc == SC_TC_ )
00660     {
00661         if( under )
00662             m_mant[wi] |= ( ((word)1) << bi );
00663         else
00664             m_mant[wi] &= ~( ((word)1) << bi );
00665     }
00666 }

void sc_dt::scfx_rep::o_invert ( const scfx_index x2  )  [inline, private]

scfx_rep.h670 行で定義されています。

00671 {
00672     int wi2 = x2.wi();
00673     int bi2 = x2.bi();
00674 
00675     m_mant[wi2] ^= ( ((word)-1) << bi2 );
00676     for( int i = wi2 + 1; i < size(); ++ i )
00677         m_mant[i] = ~ m_mant[i];
00678 }

bool sc_dt::scfx_rep::q_bit ( const scfx_index x  )  const [inline, private]

scfx_rep.h682 行で定義されています。

00683 {
00684     int wi = x.wi();
00685     int bi = x.bi();
00686 
00687     SC_ASSERT_( wi >= 0 && wi < size(), "word index out of range" );
00688 
00689     if( bi != 0 )
00690         return ( m_mant[wi] & ( ((word)1) << ( bi - 1 ) ) ) != 0;
00691     else if( wi != 0 )
00692         return ( m_mant[wi - 1] & ( ((word)1) << ( bits_in_word - 1 ) ) ) != 0;
00693     else
00694         return false;
00695 }

void sc_dt::scfx_rep::q_clear ( const scfx_index x  )  [inline, private]

scfx_rep.h699 行で定義されています。

00700 {
00701     int wi = x.wi();
00702     int bi = x.bi();
00703     
00704     SC_ASSERT_( wi >= 0 && wi < size(), "word index out of range" );
00705 
00706     m_mant[wi] &= ( ((word)-1) << bi );
00707     for( int i = wi - 1; i >= 0; -- i )
00708         m_mant[i] = 0;
00709 }

void sc_dt::scfx_rep::q_incr ( const scfx_index x  )  [inline, private]

scfx_rep.h713 行で定義されています。

00714 {
00715     int wi = x.wi();
00716     int bi = x.bi();
00717     
00718     SC_ASSERT_( wi >= 0 && wi < size(), "word index out of range" );
00719 
00720     word old_val = m_mant[wi];
00721     m_mant[wi] += ( ((word)1) << bi );
00722     if( m_mant[wi] <= old_val )
00723     {
00724         if( wi + 1 == size() )
00725           resize_to( size() + 1, 1 );
00726 
00727         for( int i = wi + 1; i < size(); ++ i )
00728         {
00729             if( ++ m_mant[i] != 0 )
00730                 break;
00731         }
00732     }
00733 }

bool sc_dt::scfx_rep::q_odd ( const scfx_index x  )  const [inline, private]

scfx_rep.h737 行で定義されています。

00738 {
00739     int wi = x.wi();
00740     int bi = x.bi();
00741 
00742     SC_ASSERT_( wi >= 0 && wi < size(), "word index out of range" );
00743 
00744     return ( m_mant[wi] & ( ((word)1) << bi ) ) != 0;
00745 }

bool sc_dt::scfx_rep::q_zero ( const scfx_index x  )  const [inline, private]

scfx_rep.h749 行で定義されています。

00750 {
00751     int wi = x.wi();
00752     int bi = x.bi();
00753 
00754     SC_ASSERT_( wi >= 0 && wi < size(), "word index out of range" );
00755 
00756     bool zero;
00757 
00758     if( bi != 0 )
00759     {
00760         zero = ( m_mant[wi] & ~( ((word)-1) << (bi - 1) ) ) == 0;
00761         for( int i = wi - 1; i >= 0; -- i )
00762             zero = zero && m_mant[i] == 0;
00763     }
00764     else if( wi != 0 )
00765     {
00766         zero = ( m_mant[wi - 1] & ~( ((word)-1) << (bits_in_word - 1) ) ) == 0;
00767         for( int i = wi - 2; i >= 0; -- i )
00768             zero = zero && m_mant[i] == 0;
00769     }
00770     else
00771         zero = true;
00772 
00773     return zero;
00774 }

void sc_dt::scfx_rep::resize_to ( int  new_size,
int  restore = 0 
) [inline, private]

scfx_rep.h475 行で定義されています。

00476 {
00477     if( restore == -1 )
00478     {
00479         int size_incr = new_size - size();
00480         m_wp += size_incr;
00481         m_msw += size_incr;
00482         m_lsw += size_incr;
00483     }
00484     m_mant.resize_to( new_size, restore );
00485 }

int sc_dt::scfx_rep::size (  )  const [inline, private]

scfx_rep.h395 行で定義されています。

00396 {
00397     return m_mant.size();
00398 }

void sc_dt::scfx_rep::toggle_tc (  )  [inline, private]

scfx_rep.h810 行で定義されています。

00811 {
00812     if( is_neg() )
00813     {
00814         complement( m_mant, m_mant, m_mant.size() );
00815         inc( m_mant );
00816     }
00817 }

void sc_dt::scfx_rep::quantization ( const scfx_params params,
bool &  q_flag 
) [private]

scfx_rep.cpp1928 行で定義されています。

01929 {
01930     scfx_index x = calc_indices( params.iwl() - params.wl() );
01931 
01932     if( x.wi() < 0 )
01933         return;
01934 
01935     if( x.wi() >= size() )
01936         resize_to( x.wi() + 1, 1 );
01937 
01938     bool qb = q_bit( x );
01939     bool qz = q_zero( x );
01940 
01941     q_flag = ( qb || ! qz );
01942 
01943     if( q_flag )
01944     {
01945         switch( params.q_mode() )
01946         {
01947             case SC_TRN:                        // truncation
01948             {
01949                 if( is_neg() )
01950                     q_incr( x );
01951                 break;
01952             }
01953             case SC_RND:                        // rounding to plus infinity
01954             {
01955                 if( ! is_neg() )
01956                 {
01957                     if( qb )
01958                         q_incr( x );
01959                 }
01960                 else
01961                 {
01962                     if( qb && ! qz )
01963                         q_incr( x );
01964                 }
01965                 break;
01966             }
01967             case SC_TRN_ZERO:                   // truncation to zero
01968             {
01969                 break;
01970             }
01971             case SC_RND_INF:                    // rounding to infinity
01972             {
01973                 if( qb )
01974                     q_incr( x );
01975                 break;
01976             }
01977             case SC_RND_CONV:                   // convergent rounding
01978             {
01979                 if( qb && ! qz || qb && qz && q_odd( x ) )
01980                     q_incr( x );
01981                 break;
01982             }
01983             case SC_RND_ZERO:                   // rounding to zero
01984             {
01985                 if( qb && ! qz )
01986                     q_incr( x );
01987                 break;
01988             }
01989             case SC_RND_MIN_INF:                // rounding to minus infinity
01990             {
01991                 if( ! is_neg() )
01992                 {
01993                     if( qb && ! qz )
01994                         q_incr( x );
01995                 }
01996                 else
01997                 {
01998                     if( qb )
01999                         q_incr( x );
02000                 }
02001                 break;
02002             }
02003             default:
02004                 ;
02005         }
02006         q_clear( x );
02007         
02008         find_sw();
02009     }
02010 }

void sc_dt::scfx_rep::overflow ( const scfx_params params,
bool &  o_flag 
) [private]

scfx_rep.cpp2020 行で定義されています。

02021 {
02022     scfx_index x = calc_indices( params.iwl() - 1 );
02023 
02024     if( x.wi() >= size() )
02025         resize_to( x.wi() + 1, 1 );
02026 
02027     if( x.wi() < 0 )
02028     {
02029         resize_to( size() - x.wi(), -1 );
02030         x.wi( 0 );
02031     }
02032 
02033     bool zero_left = o_zero_left( x );
02034     bool bit_at = o_bit_at( x );
02035     bool zero_right = o_zero_right( x );
02036 
02037     bool under = false;
02038     bool over = false;
02039 
02040     sc_enc enc = params.enc();
02041 
02042     if( enc == SC_TC_ )
02043     {
02044         if( is_neg() )
02045         {
02046             if( params.o_mode() == SC_SAT_SYM )
02047                 under = ( ! zero_left || bit_at );
02048             else
02049                 under = ( ! zero_left || zero_left && bit_at && ! zero_right );
02050         }
02051         else
02052             over = ( ! zero_left || bit_at );
02053     }
02054     else
02055     {
02056         if( is_neg() )
02057             under = ( ! is_zero() );
02058         else
02059             over = ( ! zero_left );
02060     }
02061 
02062     o_flag = ( under || over );
02063 
02064     if( o_flag )
02065     {
02066         scfx_index x2 = calc_indices( params.iwl() - params.wl() );
02067 
02068         if( x2.wi() < 0 )
02069         {
02070             resize_to( size() - x2.wi(), -1 );
02071             x.wi( x.wi() - x2.wi() );
02072             x2.wi( 0 );
02073         }
02074 
02075         switch( params.o_mode() )
02076         {
02077             case SC_WRAP:                       // wrap-around
02078             {
02079                 int n_bits = params.n_bits();
02080 
02081                 if( n_bits == 0 )
02082                 {
02083                     // wrap-around all 'wl' bits
02084                     toggle_tc();
02085                     o_extend( x, enc );
02086                     toggle_tc();
02087                 }
02088                 else if( n_bits < params.wl() )
02089                 {
02090                     scfx_index x3 = calc_indices( params.iwl() - 1 - n_bits );
02091 
02092                     // wrap-around least significant 'wl - n_bits' bits;
02093                     // saturate most significant 'n_bits' bits
02094                     toggle_tc();
02095                     o_set( x, x3, enc, under );
02096                     o_extend( x, enc );
02097                     toggle_tc();
02098                 }
02099                 else
02100                 {
02101                     // saturate all 'wl' bits
02102                     if( under )
02103                         o_set_low( x, enc );
02104                     else
02105                         o_set_high( x, x2, enc );
02106                 }
02107                 break;
02108             }
02109             case SC_SAT:                        // saturation
02110             {
02111                 if( under )
02112                     o_set_low( x, enc );
02113                 else
02114                     o_set_high( x, x2, enc );
02115                 break;
02116             }
02117             case SC_SAT_SYM:                    // symmetrical saturation
02118             {
02119                 if( under )
02120                 {
02121                     if( enc == SC_TC_ )
02122                         o_set_high( x, x2, SC_TC_, -1 );
02123                     else
02124                         o_set_low( x, SC_US_ );
02125                 }
02126                 else
02127                     o_set_high( x, x2, enc );
02128                 break;
02129             }
02130             case SC_SAT_ZERO:                   // saturation to zero
02131             {
02132                 set_zero();
02133                 break;
02134             }
02135             case SC_WRAP_SM:                    // sign magnitude wrap-around
02136             {
02137                 SC_ERROR_IF_( enc == SC_US_,
02138                               sc_core::SC_ID_WRAP_SM_NOT_DEFINED_ );
02139 
02140                 int n_bits = params.n_bits();
02141 
02142                 if( n_bits == 0 )
02143                 {
02144                     scfx_index x4 = calc_indices( params.iwl() );
02145 
02146                     if( x4.wi() >= size() )
02147                         resize_to( x4.wi() + 1, 1 );
02148 
02149                     toggle_tc();
02150                     if( o_bit_at( x4 ) != o_bit_at( x ) )
02151                         o_invert( x2 );
02152                     o_extend( x, SC_TC_ );
02153                     toggle_tc();
02154                 }
02155                 else if( n_bits == 1 )
02156                 {
02157                     toggle_tc();
02158                     if( is_neg() != o_bit_at( x ) )
02159                         o_invert( x2 );
02160                     o_extend( x, SC_TC_ );
02161                     toggle_tc();
02162                 }
02163                 else if( n_bits < params.wl() )
02164                 {
02165                     scfx_index x3 = calc_indices( params.iwl() - 1 - n_bits );
02166                     scfx_index x4 = calc_indices( params.iwl() - n_bits );
02167 
02168                     // wrap-around least significant 'wl - n_bits' bits;
02169                     // saturate most significant 'n_bits' bits
02170                     toggle_tc();
02171                     if( is_neg() == o_bit_at( x4 ) )
02172                         o_invert( x2 );
02173                     o_set( x, x3, SC_TC_, under );
02174                     o_extend( x, SC_TC_ );
02175                     toggle_tc();
02176                 }
02177                 else
02178                 {
02179                     if( under )
02180                         o_set_low( x, SC_TC_ );
02181                     else
02182                         o_set_high( x, x2, SC_TC_ );
02183                 }
02184                 break;
02185             }
02186             default:
02187                 ;
02188         }
02189 
02190         find_sw();
02191     }
02192 }

void sc_dt::scfx_rep::round ( int  wl  )  [private]

scfx_rep.cpp2851 行で定義されています。

02852 {
02853     // check for special cases
02854     
02855     if( is_nan() || is_inf() || is_zero() )
02856         return;
02857 
02858     // estimate effective wordlength and compare
02859 
02860     int wl_effective;
02861 
02862     wl_effective = ( m_msw - m_lsw + 1 ) * bits_in_word;
02863     if( wl_effective <= wl )
02864         return;
02865 
02866     // calculate effective wordlength and compare
02867 
02868     int msb = scfx_find_msb( m_mant[m_msw] );
02869     int lsb = scfx_find_lsb( m_mant[m_lsw] );
02870 
02871     wl_effective = ( m_msw * bits_in_word + msb ) -
02872                    ( m_lsw * bits_in_word + lsb ) + 1;
02873     if( wl_effective <= wl )
02874         return;
02875 
02876     // perform rounding
02877 
02878     int wi = m_msw - ( wl - 1 ) / bits_in_word;
02879     int bi =  msb - ( wl - 1 ) % bits_in_word;
02880     if( bi < 0 )
02881     {
02882         -- wi;
02883         bi += bits_in_word;
02884     }
02885 
02886     scfx_index x( wi, bi );
02887 
02888     if( q_bit( x ) && ! q_zero( x ) ||
02889         q_bit( x ) && q_zero( x ) && q_odd( x ) )
02890         q_incr( x );
02891     q_clear( x );
02892 
02893     find_sw();
02894 
02895     m_r_flag = true;
02896 }


フレンドと関連する関数

void multiply ( scfx_rep ,
const scfx_rep ,
const scfx_rep ,
int  = SC_DEFAULT_MAX_WL_ 
) [friend]

scfx_rep.cpp1517 行で定義されています。

01519 {
01520     //
01521     // check for special cases
01522     //
01523 
01524     if( lhs.is_nan() || rhs.is_nan()
01525     ||  lhs.is_inf() && rhs.is_zero()
01526     ||  lhs.is_zero() && rhs.is_inf() )
01527     {
01528         result.set_nan();
01529         return;
01530     }
01531 
01532     if( lhs.is_inf() || rhs.is_inf() )
01533     {
01534         result.set_inf( lhs.m_sign * rhs.m_sign );
01535         return;
01536     }
01537     
01538     if( lhs.is_zero() || rhs.is_zero() ) {
01539         result.set_zero( lhs.m_sign * rhs.m_sign );
01540         return;
01541     }
01542 
01543     //
01544     // do it
01545     //
01546 
01547     int len_lhs = lhs.m_msw - lhs.m_lsw + 1;
01548     int len_rhs = rhs.m_msw - rhs.m_lsw + 1;
01549 
01550     int new_size = sc_max( min_mant, len_lhs + len_rhs );
01551     int new_wp   = ( lhs.m_wp - lhs.m_lsw ) + ( rhs.m_wp - rhs.m_lsw );
01552     int new_sign = lhs.m_sign * rhs.m_sign;
01553 
01554     result.resize_to( new_size );
01555     result.m_mant.clear();
01556     result.m_wp    = new_wp;
01557     result.m_sign  = new_sign;
01558     result.m_state = scfx_rep::normal;
01559 
01560     half_word *s1 = lhs.m_mant.half_addr( lhs.m_lsw );
01561     half_word *s2 = rhs.m_mant.half_addr( rhs.m_lsw );
01562 
01563     half_word *t = result.m_mant.half_addr();
01564 
01565     len_lhs <<= 1;
01566     len_rhs <<= 1;
01567 
01568     int i1, i2;
01569 
01570     for( i1 = 0; i1 * half_word_incr < len_lhs; i1 += half_word_incr )
01571     {
01572         register word_short ls;
01573         ls.l = 0;
01574 
01575         half_word v1 = s1[i1];
01576 
01577         for( i2  = 0; i2 * half_word_incr < len_rhs; i2 += half_word_incr )
01578         {
01579             ls.l  += v1 * s2[i2];
01580             ls.s.l = ls.s.u + ( ( t[i2] += ls.s.l ) < ls.s.l );
01581             ls.s.u = 0;
01582         }
01583 
01584         t[i2] = ls.s.l;
01585         t += half_word_incr;
01586     }
01587 
01588     result.find_sw();
01589     result.round( max_wl );
01590 }

scfx_rep* neg_scfx_rep ( const scfx_rep a  )  [friend]

scfx_rep* mult_scfx_rep ( const scfx_rep a,
const scfx_rep b,
int  max_wl = SC_DEFAULT_MAX_WL_ 
) [friend]

scfx_rep* div_scfx_rep ( const scfx_rep ,
const scfx_rep ,
int  = SC_DEFAULT_DIV_WL_ 
) [friend]

scfx_rep.cpp1598 行で定義されています。

01599 {
01600     scfx_rep& result = *new scfx_rep;
01601 
01602     //
01603     // check for special cases
01604     //
01605 
01606     if( lhs.is_nan() || rhs.is_nan() || lhs.is_inf() && rhs.is_inf() ||
01607         lhs.is_zero() && rhs.is_zero() )
01608     {
01609         result.set_nan();
01610         return &result;
01611     }
01612 
01613     if( lhs.is_inf() || rhs.is_zero() )
01614     {
01615         result.set_inf( lhs.m_sign * rhs.m_sign );
01616         return &result;
01617     }
01618 
01619     if( lhs.is_zero() || rhs.is_inf() )
01620     {
01621         result.set_zero( lhs.m_sign * rhs.m_sign );
01622         return &result;
01623     }
01624 
01625     //
01626     // do it
01627     //
01628 
01629     // compute one bit more for rounding
01630     div_wl ++;
01631 
01632     result.resize_to( sc_max( n_word( div_wl ) + 1, min_mant ) );
01633     result.m_mant.clear();
01634     result.m_sign = lhs.m_sign * rhs.m_sign;
01635 
01636     int msb_lhs = scfx_find_msb( lhs.m_mant[lhs.m_msw] )
01637                 + ( lhs.m_msw - lhs.m_wp ) * bits_in_word;
01638     int msb_rhs = scfx_find_msb( rhs.m_mant[rhs.m_msw] )
01639                 + ( rhs.m_msw - rhs.m_wp ) * bits_in_word;
01640 
01641     int msb_res = msb_lhs - msb_rhs;
01642     int to_shift = -msb_res % bits_in_word;
01643     int result_index;
01644 
01645     int c = ( msb_res % bits_in_word >= 0 ) ? 1 : 0;
01646 
01647     result_index = (result.size() - c) * bits_in_word + msb_res % bits_in_word;
01648     result.m_wp   = (result.size() - c) - msb_res / bits_in_word;
01649 
01650     scfx_rep remainder = lhs;
01651 
01652     // align msb from remainder to msb from rhs
01653     remainder.lshift( to_shift );
01654 
01655     // make sure msw( remainder ) < size - 1
01656     if( remainder.m_msw == remainder.size() - 1 )
01657         remainder.resize_to( remainder.size() + 1, 1 );
01658 
01659     // make sure msw( remainder ) >= msw( rhs )!
01660     int msw_diff = rhs.m_msw - remainder.m_msw;
01661     if (msw_diff > 0)
01662         remainder.resize_to( remainder.size() + msw_diff, -1 );
01663 
01664     int counter;
01665 
01666     for( counter = div_wl; counter && ! remainder.is_zero(); counter -- )
01667     {
01668         if( compare_msw_ff( rhs, remainder ) <= 0 )
01669         {
01670             result.set_bin( result_index );
01671             sub_with_index( remainder.m_mant, remainder.m_msw, remainder.m_lsw,
01672                             rhs.m_mant, rhs.m_msw, rhs.m_lsw );
01673         }
01674         result_index --;
01675         remainder.shift_left( 1 );
01676         remainder.m_lsw = remainder.find_lsw();
01677     }
01678 
01679     // perform convergent rounding, if needed
01680     if( counter == 0 )
01681     {
01682         int index = result_index + 1 - result.m_wp * bits_in_word;
01683 
01684         scfx_index x = result.calc_indices( index );
01685         scfx_index x1 = result.calc_indices( index + 1 );
01686 
01687         if( result.o_bit_at( x ) && result.o_bit_at( x1 ) )
01688             result.q_incr( x );
01689 
01690         result.m_r_flag = true;
01691     }
01692 
01693     result.find_sw();
01694 
01695     return &result;
01696 }

scfx_rep* add_scfx_rep ( const scfx_rep ,
const scfx_rep ,
int  = SC_DEFAULT_MAX_WL_ 
) [friend]

scfx_rep.cpp1279 行で定義されています。

01280 {
01281     scfx_rep& result = *new scfx_rep;
01282 
01283     //
01284     // check for special cases
01285     //
01286 
01287     if( lhs.is_nan() || rhs.is_nan()
01288     ||  ( lhs.is_inf() && rhs.is_inf() && lhs.m_sign != rhs.m_sign ) )
01289     {
01290         result.set_nan();
01291         return &result;
01292     }
01293 
01294     if( lhs.is_inf() )
01295     {
01296         result.set_inf( lhs.m_sign );
01297         return &result;
01298     }
01299 
01300     if( rhs.is_inf() )
01301     {
01302         result.set_inf( rhs.m_sign );
01303         return &result;
01304     }
01305 
01306     //
01307     // align operands if needed
01308     //
01309 
01310     scfx_mant_ref lhs_mant;
01311     scfx_mant_ref rhs_mant;
01312 
01313     int len_mant = lhs.size();
01314     int new_wp = lhs.m_wp;
01315 
01316     align( lhs, rhs, new_wp, len_mant, lhs_mant, rhs_mant );
01317 
01318     //
01319     // size the result mantissa
01320     //
01321 
01322     result.resize_to( len_mant );
01323     result.m_wp = new_wp;
01324 
01325     //
01326     // do it
01327     //
01328 
01329     if( lhs.m_sign == rhs.m_sign )
01330     {
01331         add_mants( len_mant, result.m_mant, lhs_mant, rhs_mant );
01332         result.m_sign = lhs.m_sign;
01333     }
01334     else
01335     {
01336         int cmp = compare_abs( lhs, rhs );
01337 
01338         if( cmp == 1 )
01339         {
01340             sub_mants( len_mant, result.m_mant, lhs_mant, rhs_mant );
01341             result.m_sign = lhs.m_sign;
01342         }
01343         else if ( cmp == -1 )
01344         {
01345             sub_mants( len_mant, result.m_mant, rhs_mant, lhs_mant );
01346             result.m_sign = rhs.m_sign;
01347         }
01348         else
01349         {
01350             result.m_mant.clear();
01351             result.m_sign = 1;
01352         }
01353     }
01354 
01355     result.find_sw();
01356     result.round( max_wl );
01357 
01358     return &result;
01359 }

scfx_rep* sub_scfx_rep ( const scfx_rep ,
const scfx_rep ,
int  = SC_DEFAULT_MAX_WL_ 
) [friend]

scfx_rep.cpp1408 行で定義されています。

01409 {
01410     scfx_rep& result = *new scfx_rep;
01411 
01412     //
01413     // check for special cases
01414     //
01415 
01416     if( lhs.is_nan() || rhs.is_nan()
01417     ||  ( lhs.is_inf() && rhs.is_inf() && lhs.m_sign == rhs.m_sign ) )
01418     {
01419         result.set_nan();
01420         return &result;
01421     }
01422 
01423     if( lhs.is_inf() )
01424     {
01425         result.set_inf( lhs.m_sign );
01426         return &result;
01427     }
01428 
01429     if( rhs.is_inf() )
01430     {
01431         result.set_inf( -1 * rhs.m_sign );
01432         return &result;
01433     }
01434 
01435     //
01436     // align operands if needed
01437     //
01438 
01439     scfx_mant_ref lhs_mant;
01440     scfx_mant_ref rhs_mant;
01441 
01442     int len_mant = lhs.size();
01443     int new_wp = lhs.m_wp;
01444 
01445     align( lhs, rhs, new_wp, len_mant, lhs_mant, rhs_mant );
01446 
01447     //
01448     // size the result mantissa
01449     //
01450 
01451     result.resize_to( len_mant );
01452     result.m_wp = new_wp;
01453 
01454     //
01455     // do it
01456     //
01457 
01458     if( lhs.m_sign != rhs.m_sign )
01459     {
01460         add_mants( len_mant, result.m_mant, lhs_mant, rhs_mant );
01461         result.m_sign = lhs.m_sign;
01462     }
01463     else
01464     {
01465         int cmp = compare_abs( lhs, rhs );
01466 
01467         if( cmp == 1 )
01468         {
01469             sub_mants( len_mant, result.m_mant, lhs_mant, rhs_mant );
01470             result.m_sign = lhs.m_sign;
01471         }
01472         else if ( cmp == -1 )
01473         {
01474             sub_mants( len_mant, result.m_mant, rhs_mant, lhs_mant );
01475             result.m_sign = -rhs.m_sign;
01476         } else {
01477             result.m_mant.clear();
01478             result.m_sign = 1;
01479         }
01480     }
01481 
01482     result.find_sw();
01483     result.round( max_wl );
01484 
01485     return &result;
01486 }

scfx_rep* lsh_scfx_rep ( const scfx_rep a,
int  b 
) [friend]

scfx_rep* rsh_scfx_rep ( const scfx_rep a,
int  b 
) [friend]

int cmp_scfx_rep ( const scfx_rep ,
const scfx_rep  
) [friend]

scfx_rep.cpp1850 行で定義されています。

01851 {
01852     // handle special cases
01853 
01854     if( a.is_nan() || b.is_nan() )
01855     {
01856 #if 0
01857         if( a.is_nan() && b.is_nan() )
01858         {
01859             return 0;
01860         }
01861 #endif
01862         return 2;
01863     }
01864 
01865     if( a.is_inf() || b.is_inf() )
01866     {
01867         if( a.is_inf() )
01868         {
01869             if( ! a.is_neg() )
01870             {
01871                 if( b.is_inf() && ! b.is_neg() )
01872                 {
01873                     return 0;
01874                 }
01875                 else
01876                 {
01877                     return 1;
01878                 }
01879             }
01880             else
01881             {
01882                 if( b.is_inf() && b.is_neg() )
01883                 {
01884                     return 0;
01885                 }
01886                 else
01887                 {
01888                     return -1;
01889                 }
01890             }
01891         }
01892         if( b.is_inf() )
01893         {
01894             if( ! b.is_neg() )
01895             {
01896                 return -1;
01897             }
01898             else
01899             {
01900                 return 1;
01901             }
01902         }
01903     }
01904   
01905     if( a.is_zero() && b.is_zero() )
01906     {
01907         return 0;
01908     }
01909 
01910     // compare sign
01911 
01912     if( a.m_sign != b.m_sign )
01913     {
01914         return a.m_sign;
01915     }
01916 
01917     return ( a.m_sign * compare_abs( a, b ) );
01918 }

scfx_rep* quantization_scfx_rep ( const scfx_rep a,
const scfx_params params,
bool &  q_flag 
) [friend]

scfx_rep.h446 行で定義されています。

00449 {
00450     scfx_rep& c = *new scfx_rep( a );
00451     c.quantization( params, q_flag );
00452     return &c;
00453 }

scfx_rep* overflow_scfx_rep ( const scfx_rep a,
const scfx_params params,
bool &  o_flag 
) [friend]

scfx_rep.h457 行で定義されています。

00460 {
00461     scfx_rep& c = *new scfx_rep( a );
00462     c.overflow( params, o_flag );
00463     return &c;
00464 }

void align ( const scfx_rep lhs,
const scfx_rep rhs,
int &  new_wp,
int &  len_mant,
scfx_mant_ref lhs_mant,
scfx_mant_ref rhs_mant 
) [friend]

scfx_rep.cpp2233 行で定義されています。

02235 {
02236     bool need_lhs = true;
02237     bool need_rhs = true;
02238 
02239     if( lhs.m_wp != rhs.m_wp || lhs.size() != rhs.size() )
02240     {
02241         int lower_bound_lhs = lhs.m_lsw - lhs.m_wp;
02242         int upper_bound_lhs = lhs.m_msw - lhs.m_wp;
02243         int lower_bound_rhs = rhs.m_lsw - rhs.m_wp;
02244         int upper_bound_rhs = rhs.m_msw - rhs.m_wp;
02245 
02246         int lower_bound = sc_min( lower_bound_lhs, lower_bound_rhs );
02247         int upper_bound = sc_max( upper_bound_lhs, upper_bound_rhs );
02248 
02249         new_wp   = -lower_bound;
02250         len_mant = sc_max( min_mant, upper_bound - lower_bound + 1 );
02251 
02252         if( new_wp != lhs.m_wp || len_mant != lhs.size() )
02253         {
02254             lhs_mant = lhs.resize( len_mant, new_wp );
02255             need_lhs = false;
02256         }
02257 
02258         if( new_wp != rhs.m_wp || len_mant != rhs.size() )
02259         {
02260             rhs_mant = rhs.resize( len_mant, new_wp );
02261             need_rhs = false;
02262         }
02263     }
02264 
02265     if( need_lhs )
02266     {
02267         lhs_mant = lhs.m_mant;
02268     }
02269 
02270     if( need_rhs )
02271     {
02272         rhs_mant = rhs.m_mant;
02273     }
02274 }

int compare_msw ( const scfx_rep ,
const scfx_rep  
) [friend]

int compare_msw_ff ( const scfx_rep lhs,
const scfx_rep rhs 
) [friend]

scfx_rep.cpp2282 行で定義されています。

02283 {
02284     // special case: rhs.m_mant[rhs.m_msw + 1] == 1
02285     if( rhs.m_msw < rhs.size() - 1 && rhs.m_mant[rhs.m_msw + 1 ] != 0 )
02286     {
02287         return -1;
02288     }
02289 
02290     int lhs_size = lhs.m_msw - lhs.m_lsw + 1;
02291     int rhs_size = rhs.m_msw - rhs.m_lsw + 1;
02292 
02293     int size = sc_min( lhs_size, rhs_size );
02294 
02295     int lhs_index = lhs.m_msw;
02296     int rhs_index = rhs.m_msw;
02297 
02298     int i;
02299 
02300     for( i = 0;
02301          i < size && lhs.m_mant[lhs_index] == rhs.m_mant[rhs_index];
02302          i ++ )
02303     {
02304         lhs_index --;
02305         rhs_index --;
02306     }
02307 
02308     if( i == size )
02309     {
02310         if( lhs_size == rhs_size )
02311         {
02312             return 0;
02313         }
02314 
02315         if( lhs_size < rhs_size )
02316         {
02317             return -1;
02318         }
02319         else
02320         {
02321             return 1;
02322         }
02323   }
02324 
02325   if( lhs.m_mant[lhs_index] < rhs.m_mant[rhs_index] )
02326   {
02327       return -1;
02328   } else {
02329       return 1;
02330   }
02331 }

void print_dec ( scfx_string s,
const scfx_rep num,
int  w_prefix,
sc_fmt  fmt 
) [friend]

scfx_rep.cpp888 行で定義されています。

00889 {
00890     if( num.is_neg() )
00891         s += '-';
00892 
00893     if( w_prefix == 1 ) {
00894         scfx_print_prefix( s, SC_DEC );
00895     }
00896 
00897     if( num.is_zero() )
00898     {
00899         s += '0';
00900         return;
00901     }
00902 
00903     // split 'num' into its integer and fractional part
00904 
00905     scfx_rep int_part  = num;
00906     scfx_rep frac_part = num;
00907 
00908     int i;
00909     
00910     for( i = int_part.m_lsw; i <= int_part.m_msw && i < int_part.m_wp; i ++ )
00911         int_part.m_mant[i] = 0;
00912     int_part.find_sw();
00913     if( int_part.m_wp < int_part.m_lsw )
00914         int_part.resize_to( int_part.size() - int_part.m_wp, -1 );
00915     
00916     for( i = frac_part.m_msw;
00917          i >= frac_part.m_lsw && i >= frac_part.m_wp;
00918          i -- )
00919         frac_part.m_mant[i] = 0;
00920     frac_part.find_sw();
00921     if( frac_part.m_msw == frac_part.size() - 1 )
00922         frac_part.resize_to( frac_part.size() + 1, 1 );
00923 
00924     // print integer part
00925 
00926     int int_digits = 0;
00927     int int_zeros  = 0;
00928     
00929     if( ! int_part.is_zero() )
00930     {
00931         double int_wl = ( int_part.m_msw - int_part.m_wp ) * bits_in_word
00932                       + scfx_find_msb( int_part.m_mant[int_part.m_msw] ) + 1;
00933         int_digits = (int) ceil( int_wl * log10( 2. ) );
00934 
00935         int len = s.length();
00936         s.append( int_digits );
00937 
00938         bool zero_digits = ( frac_part.is_zero() && fmt != SC_F );
00939 
00940         for( i = int_digits + len - 1; i >= len; i-- )
00941         {
00942             unsigned int remainder = int_part.divide_by_ten();
00943             s[i] = static_cast<char>( '0' + remainder );
00944             
00945             if( zero_digits )
00946             {
00947                 if( remainder == 0 )
00948                     int_zeros ++;
00949                 else
00950                     zero_digits = false;
00951             }
00952         }
00953 
00954         // discard trailing zeros from int_part
00955         s.discard( int_zeros );
00956 
00957         if( s[len] == '0' )
00958         {
00959             // int_digits was overestimated by one
00960             s.remove( len );
00961             -- int_digits;
00962         }
00963     }
00964 
00965     // print fractional part
00966 
00967     int frac_digits = 0;
00968     int frac_zeros  = 0;
00969 
00970     if( ! frac_part.is_zero() )
00971     {
00972         s += '.';
00973 
00974         bool zero_digits = ( int_digits == 0 && fmt != SC_F );
00975 
00976         double frac_wl = ( frac_part.m_wp - frac_part.m_msw ) * bits_in_word
00977                        - scfx_find_msb( frac_part.m_mant[frac_part.m_msw] )
00978                        - 1;
00979         frac_zeros = (int) floor( frac_wl * log10( 2. ) );
00980 
00981         scfx_rep temp;
00982         sc_dt::multiply( temp, frac_part, pow10_fx( frac_zeros ) );
00983         frac_part = temp;
00984         if( frac_part.m_msw == frac_part.size() - 1 )
00985             frac_part.resize_to( frac_part.size() + 1, 1 );
00986         
00987         frac_digits = frac_zeros;
00988         if( ! zero_digits )
00989         {
00990             for( i = 0; i < frac_zeros; i ++ )
00991                 s += '0';
00992             frac_zeros = 0;
00993         }
00994 
00995         while( ! frac_part.is_zero() )
00996         {
00997             frac_part.multiply_by_ten();
00998             int n = frac_part.m_mant[frac_part.m_msw + 1];
00999         
01000             if( zero_digits )
01001             {
01002                 if( n == 0 )
01003                     frac_zeros ++;
01004                 else
01005                     zero_digits = false;
01006             }
01007         
01008             if( ! zero_digits )
01009                 s += static_cast<char>( '0' + n );
01010 
01011             frac_part.m_mant[frac_part.m_msw + 1] = 0;
01012             frac_digits ++;
01013         }
01014     }
01015 
01016     // print exponent
01017     
01018     if( fmt != SC_F )
01019     {
01020         if( frac_digits == 0 )
01021             scfx_print_exp( s, int_zeros );
01022         else if( int_digits == 0 )
01023             scfx_print_exp( s, - frac_zeros );
01024     }
01025 }

void print_other ( scfx_string s,
const scfx_rep a,
sc_numrep  numrep,
int  w_prefix,
sc_fmt  fmt,
const scfx_params params 
) [friend]

scfx_rep.cpp1028 行で定義されています。

01030 {
01031     scfx_rep b = a;
01032 
01033     sc_numrep numrep2 = numrep;
01034 
01035     bool numrep_is_sm = ( numrep == SC_BIN_SM ||
01036                           numrep == SC_OCT_SM ||
01037                           numrep == SC_HEX_SM );
01038 
01039     if( numrep_is_sm )
01040     {
01041         if( b.is_neg() )
01042         {
01043             s += '-';
01044             b = *neg_scfx_rep( a );
01045         }
01046         switch( numrep )
01047         {
01048             case SC_BIN_SM:
01049                 numrep2 = SC_BIN_US;
01050                 break;
01051             case SC_OCT_SM:
01052                 numrep2 = SC_OCT_US;
01053                 break;
01054             case SC_HEX_SM:
01055                 numrep2 = SC_HEX_US;
01056                 break;
01057             default:
01058                 ;
01059         }
01060     }
01061     
01062     if( w_prefix != 0 ) {
01063         scfx_print_prefix( s, numrep );
01064     }
01065 
01066     numrep = numrep2;
01067 
01068     int msb, lsb;
01069 
01070     if( params != 0 )
01071     {
01072         msb = params->iwl() - 1;
01073         lsb = params->iwl() - params->wl();
01074 
01075         if( params->enc() == SC_TC_ &&
01076             ( numrep == SC_BIN_US ||
01077               numrep == SC_OCT_US ||
01078               numrep == SC_HEX_US ) &&
01079             ! numrep_is_sm &&
01080             params->wl() > 1 )
01081             -- msb;
01082         else if( params->enc() == SC_US_ &&
01083             ( numrep == SC_BIN ||
01084               numrep == SC_OCT ||
01085               numrep == SC_HEX ||
01086               numrep == SC_CSD ) )
01087             ++ msb;
01088     }
01089     else
01090     {
01091         if( b.is_zero() )
01092         {
01093             msb = 0;
01094             lsb = 0;
01095         }
01096         else
01097         {
01098             msb = ( b.m_msw - b.m_wp ) * bits_in_word
01099                 + scfx_find_msb( b.m_mant[ b.m_msw ] ) + 1;
01100             while( b.get_bit( msb ) == b.get_bit( msb - 1 ) )
01101                 -- msb;
01102 
01103             if( numrep == SC_BIN_US ||
01104                 numrep == SC_OCT_US ||
01105                 numrep == SC_HEX_US )
01106                 -- msb;
01107 
01108             lsb = ( b.m_lsw - b.m_wp ) * bits_in_word
01109                 + scfx_find_lsb( b.m_mant[ b.m_lsw ] );
01110         }
01111     }
01112 
01113     int step;
01114 
01115     switch( numrep )
01116     {
01117         case SC_BIN:
01118         case SC_BIN_US:
01119         case SC_CSD:
01120             step = 1;
01121            break;
01122         case SC_OCT:
01123         case SC_OCT_US:
01124             step = 3;
01125             break;
01126         case SC_HEX:
01127         case SC_HEX_US:
01128             step = 4;
01129             break;
01130         default:
01131             step = 0;
01132     }
01133 
01134     msb = (int) ceil( double( msb + 1 ) / step ) * step - 1;
01135 
01136     lsb = (int) floor( double( lsb ) / step ) * step;
01137 
01138     if( msb < 0 )
01139     {
01140         s += '.';
01141         if( fmt == SC_F )
01142         {
01143             int sign = ( b.is_neg() ) ? ( 1 << step ) - 1 : 0;
01144             for( int i = ( msb + 1 ) / step; i < 0; i ++ )
01145             {
01146                 if( sign < 10 )
01147                     s += static_cast<char>( sign + '0' );
01148                 else
01149                     s += static_cast<char>( sign + 'a' - 10 );
01150             }
01151         }
01152     }
01153 
01154     int i = msb;
01155     while( i >= lsb )
01156     {
01157         int value = 0;
01158         for( int j = step - 1; j >= 0; -- j )
01159         {
01160             value += static_cast<int>( b.get_bit( i ) ) << j;
01161             -- i;
01162         }
01163         if( value < 10 )
01164             s += static_cast<char>( value + '0' );
01165         else
01166             s += static_cast<char>( value + 'a' - 10 );
01167         if( i == -1 )
01168             s += '.';
01169     }
01170 
01171     if( lsb > 0 && fmt == SC_F )
01172     {
01173         for( int i = lsb / step; i > 0; i -- )
01174             s += '0';
01175     }
01176 
01177     if( s[s.length() - 1] == '.' )
01178         s.discard( 1 );
01179 
01180     if( fmt != SC_F )
01181     {
01182         if( msb < 0 )
01183             scfx_print_exp( s, ( msb + 1 ) / step );
01184         else if( lsb > 0 )
01185             scfx_print_exp( s, lsb / step );
01186     }
01187 
01188     if( numrep == SC_CSD )
01189         scfx_tc2csd( s, w_prefix );
01190 }

int compare_abs ( const scfx_rep a,
const scfx_rep b 
) [friend]

scfx_rep.cpp1773 行で定義されています。

01774 {
01775     // check for zero
01776 
01777     word a_word = a.m_mant[a.m_msw];
01778     word b_word = b.m_mant[b.m_msw];
01779   
01780     if( a_word == 0 || b_word == 0 )
01781     {
01782         if( a_word != 0 )
01783             return 1;
01784         if( b_word != 0 )
01785             return -1;
01786         return 0;
01787     }
01788 
01789     // compare msw index
01790 
01791     int a_msw = a.m_msw - a.m_wp;
01792     int b_msw = b.m_msw - b.m_wp;
01793 
01794     if( a_msw > b_msw )
01795         return 1;
01796 
01797     if( a_msw < b_msw )
01798         return -1;
01799 
01800     // compare content
01801 
01802     int a_i = a.m_msw;
01803     int b_i = b.m_msw;
01804 
01805     while( a_i >= a.m_lsw && b_i >= b.m_lsw )
01806     {
01807         a_word = a.m_mant[a_i];
01808         b_word = b.m_mant[b_i];
01809         if( a_word > b_word )
01810             return 1;
01811         if( a_word < b_word )
01812             return -1;
01813         -- a_i;
01814         -- b_i;
01815     }
01816 
01817     bool a_zero = true;
01818     while( a_i >= a.m_lsw )
01819     {
01820         a_zero = a_zero && ( a.m_mant[a_i] == 0 );
01821         -- a_i;
01822     }
01823   
01824     bool b_zero = true;
01825     while( b_i >= b.m_lsw )
01826     {
01827         b_zero = b_zero && ( b.m_mant[b_i] == 0 );
01828         -- b_i;
01829     }
01830 
01831     // assertion: a_zero || b_zero == true
01832 
01833     if( ! a_zero && b_zero )
01834         return 1;
01835 
01836     if( a_zero && ! b_zero )
01837         return -1;
01838 
01839     return 0;
01840 }


変数

scfx_rep.h280 行で定義されています。

int sc_dt::scfx_rep::m_wp [private]

scfx_rep.h281 行で定義されています。

int sc_dt::scfx_rep::m_sign [private]

scfx_rep.h282 行で定義されています。

scfx_rep.h283 行で定義されています。

int sc_dt::scfx_rep::m_msw [private]

scfx_rep.h284 行で定義されています。

int sc_dt::scfx_rep::m_lsw [private]

scfx_rep.h285 行で定義されています。

bool sc_dt::scfx_rep::m_r_flag [private]

scfx_rep.h286 行で定義されています。


このクラスの説明は次のファイルから生成されました:

SystemCに対してFri Jun 6 20:12:49 2008に生成されました。  doxygen 1.5.6