sc_uint_base.h

Go to the documentation of this file.
00001 /*****************************************************************************
00002 
00003   The following code is derived, directly or indirectly, from the SystemC
00004   source code Copyright (c) 1996-2006 by all Contributors.
00005   All Rights reserved.
00006 
00007   The contents of this file are subject to the restrictions and limitations
00008   set forth in the SystemC Open Source License Version 2.4 (the "License");
00009   You may not use this file except in compliance with such restrictions and
00010   limitations. You may obtain instructions on how to receive a copy of the
00011   License at http://www.systemc.org/. Software distributed by Contributors
00012   under the License is distributed on an "AS IS" basis, WITHOUT WARRANTY OF
00013   ANY KIND, either express or implied. See the License for the specific
00014   language governing rights and limitations under the License.
00015 
00016  *****************************************************************************/
00017 
00018 /*****************************************************************************
00019 
00020   sc_uint_base.h -- A sc_uint is an unsigned integer whose length is less than
00021                the machine's native integer length. We provide two
00022                implementations (i) sc_uint with length between 1 - 64, and (ii)
00023                sc_uint with length between 1 - 32. Implementation (i) is the
00024                default implementation, while implementation (ii) can be used
00025                only if compiled with -D_32BIT_. Unlike arbitrary precision,
00026                arithmetic and bitwise operations are performed using the native
00027                types (hence capped at 32/64 bits). The sc_uint integer is
00028                useful when the user does not need arbitrary precision and the
00029                performance is superior to sc_bigint/sc_biguint.
00030 
00031   Original Author: Amit Rao, Synopsys, Inc.
00032 
00033  *****************************************************************************/
00034 
00035 /*****************************************************************************
00036 
00037   MODIFICATION LOG - modifiers, enter your name, affiliation, date and
00038   changes you are making here.
00039 
00040       Name, Affiliation, Date: Ali Dasdan, Synopsys, Inc.
00041   Description of Modification: - Resolved ambiguity with sc_(un)signed.
00042                                - Merged the code for 64- and 32-bit versions
00043                                  via the constants in sc_nbdefs.h.
00044                                - Eliminated redundant file inclusions.
00045 
00046       Name, Affiliation, Date:
00047   Description of Modification:
00048 
00049  *****************************************************************************/
00050 
00051 // $Log: sc_uint_base.h,v $
00052 // Revision 1.1.1.1  2006/12/15 20:31:36  acg
00053 // SystemC 2.2
00054 //
00055 // Revision 1.3  2006/01/13 18:49:32  acg
00056 // Added $Log command so that CVS check in comments are reproduced in the
00057 // source.
00058 //
00059 
00060 #ifndef SC_UINT_BASE_H
00061 #define SC_UINT_BASE_H
00062 
00063 
00064 #include "sysc/kernel/sc_object.h"
00065 #include "sysc/datatypes/misc/sc_value_base.h"
00066 #include "sysc/datatypes/int/sc_int_ids.h"
00067 #include "sysc/datatypes/int/sc_length_param.h"
00068 #include "sysc/datatypes/int/sc_nbdefs.h"
00069 #include "sysc/datatypes/fx/scfx_ieee.h"
00070 #include "sysc/utils/sc_iostream.h"
00071 #include "sysc/utils/sc_temporary.h"
00072 
00073 
00074 namespace sc_dt
00075 {
00076 
00077 class sc_concatref;
00078 
00079 // classes defined in this module
00080 class sc_uint_bitref_r;
00081 class sc_uint_bitref;
00082 class sc_uint_subref_r;
00083 class sc_uint_subref;
00084 class sc_uint_base;
00085 
00086 // forward class declarations
00087 class sc_bv_base;
00088 class sc_lv_base;
00089 class sc_int_subref_r;
00090 class sc_signed_subref_r;
00091 class sc_unsigned_subref_r;
00092 class sc_signed;
00093 class sc_unsigned;
00094 class sc_fxval;
00095 class sc_fxval_fast;
00096 class sc_fxnum;
00097 class sc_fxnum_fast;
00098 
00099 
00100 extern const uint_type mask_int[SC_INTWIDTH][SC_INTWIDTH];
00101 
00102 // friend operator declarations
00103     inline bool operator == ( const sc_uint_base& a, const sc_uint_base& b );
00104     inline bool operator != ( const sc_uint_base& a, const sc_uint_base& b );
00105     inline bool operator <  ( const sc_uint_base& a, const sc_uint_base& b );
00106     inline bool operator <= ( const sc_uint_base& a, const sc_uint_base& b );
00107     inline bool operator >  ( const sc_uint_base& a, const sc_uint_base& b );
00108     inline bool operator >= ( const sc_uint_base& a, const sc_uint_base& b );
00109 
00110 
00111 
00112 // ----------------------------------------------------------------------------
00113 //  CLASS : sc_uint_bitref_r
00114 //
00115 //  Proxy class for sc_uint bit selection (r-value only).
00116 // ----------------------------------------------------------------------------
00117 
00118 class sc_uint_bitref_r : public sc_value_base
00119 {
00120     friend class sc_uint_base;
00121     friend class sc_uint_signal;
00122 
00123 
00124     // constructors
00125 
00126 public:
00127     sc_uint_bitref_r( const sc_uint_bitref_r& init ) :
00128      m_index(init.m_index), m_obj_p(init.m_obj_p)
00129      {}
00130 
00131 protected:
00132     sc_uint_bitref_r()
00133         {}
00134 
00135     // initializer for sc_core::sc_vpool:
00136 
00137     void initialize( const sc_uint_base* obj_p, int index_ )
00138     {
00139         m_obj_p = (sc_uint_base*)obj_p;
00140         m_index = index_;
00141     }
00142 
00143 public:
00144 
00145     // destructor
00146 
00147     virtual ~sc_uint_bitref_r()
00148     {}
00149 
00150     // concatenation support
00151 
00152     virtual int concat_length(bool* xz_present_p) const
00153     { if ( xz_present_p ) *xz_present_p = false; return 1; }
00154     virtual bool concat_get_ctrl( sc_digit* dst_p, int low_i ) const
00155         {
00156             int  bit_mask = 1 << (low_i % BITS_PER_DIGIT);
00157             int  word_i = low_i / BITS_PER_DIGIT;
00158 
00159         dst_p[word_i] &= ~bit_mask;
00160         return false;
00161         }
00162     virtual bool concat_get_data( sc_digit* dst_p, int low_i ) const
00163         {
00164             int  bit_mask = 1 << (low_i % BITS_PER_DIGIT);
00165         bool result;             // True is non-zero.
00166             int  word_i = low_i / BITS_PER_DIGIT;
00167 
00168             if ( operator uint64() )
00169         {
00170                 dst_p[word_i] |= bit_mask;
00171         result = true;
00172         }
00173             else
00174         {
00175                 dst_p[word_i] &= ~bit_mask;
00176         result = false;
00177         }
00178         return result;
00179         }
00180     virtual uint64 concat_get_uint64() const
00181     { return operator uint64(); }
00182 
00183     // capacity
00184 
00185     int length() const
00186     { return 1; }
00187 
00188 #ifdef SC_DT_DEPRECATED
00189     int bitwidth() const
00190     { return length(); }
00191 #endif
00192 
00193 
00194     // implicit conversion to uint64
00195 
00196     operator uint64 () const;
00197     bool operator ! () const;
00198     bool operator ~ () const;
00199 
00200 
00201     // explicit conversions
00202 
00203     uint64 value() const
00204     { return operator uint64 (); }
00205 
00206     bool to_bool() const
00207     { return operator uint64 (); }
00208 
00209 
00210     // other methods
00211 
00212     void print( ::std::ostream& os = ::std::cout ) const
00213     { os << to_bool(); }
00214 
00215 protected:
00216 
00217     int           m_index;
00218     sc_uint_base* m_obj_p;
00219 
00220 private:
00221 
00222     // disabled
00223     sc_uint_bitref_r& operator = ( const sc_uint_bitref_r& );
00224 };
00225 
00226 
00227 
00228 inline
00229 ::std::ostream&
00230 operator << ( ::std::ostream&, const sc_uint_bitref_r& );
00231 
00232 
00233 // ----------------------------------------------------------------------------
00234 //  CLASS : sc_uint_bitref
00235 //
00236 //  Proxy class for sc_uint bit selection (r-value and l-value).
00237 // ----------------------------------------------------------------------------
00238 
00239 class sc_uint_bitref
00240     : public sc_uint_bitref_r
00241 {
00242     friend class sc_uint_base;
00243     friend class sc_core::sc_vpool<sc_uint_bitref>;
00244 
00245 
00246     // constructors
00247 
00248 protected:
00249     sc_uint_bitref()
00250         {}
00251 public:
00252     sc_uint_bitref( const sc_uint_bitref& init ) : sc_uint_bitref_r(init)
00253         {}
00254 
00255 public:
00256 
00257     // assignment operators
00258 
00259     sc_uint_bitref& operator = ( const sc_uint_bitref_r& b );
00260     sc_uint_bitref& operator = ( const sc_uint_bitref& b );
00261     sc_uint_bitref& operator = ( bool b );
00262 
00263     sc_uint_bitref& operator &= ( bool b );
00264     sc_uint_bitref& operator |= ( bool b );
00265     sc_uint_bitref& operator ^= ( bool b );
00266 
00267     // concatenation methods
00268 
00269     virtual void concat_set(int64 src, int low_i);
00270     virtual void concat_set(const sc_signed& src, int low_i);
00271     virtual void concat_set(const sc_unsigned& src, int low_i);
00272     virtual void concat_set(uint64 src, int low_i);
00273 
00274     // other methods
00275 
00276     void scan( ::std::istream& is = ::std::cin );
00277 
00278 protected:
00279     static sc_core::sc_vpool<sc_uint_bitref> m_pool;
00280 
00281 };
00282 
00283 
00284 
00285 inline
00286 ::std::istream&
00287 operator >> ( ::std::istream&, sc_uint_bitref& );
00288 
00289 
00290 // ----------------------------------------------------------------------------
00291 //  CLASS : sc_uint_subref_r
00292 //
00293 //  Proxy class for sc_uint part selection (r-value only).
00294 // ----------------------------------------------------------------------------
00295 
00296 class sc_uint_subref_r : public sc_value_base
00297 {
00298     friend class sc_uint_base;
00299     friend class sc_uint_subref;
00300 
00301 
00302     // constructors
00303 
00304 public:
00305     sc_uint_subref_r( const sc_uint_subref_r& init ) :
00306         m_left(init.m_left), m_obj_p(init.m_obj_p), m_right(init.m_right)
00307     {}
00308 
00309 protected:
00310     sc_uint_subref_r()
00311     {}
00312 
00313     // initializer for sc_core::sc_vpool:
00314 
00315     void initialize( const sc_uint_base* obj_p, int left_i, int right_i )
00316     {
00317         m_obj_p = (sc_uint_base*)obj_p;
00318         m_left = left_i;
00319         m_right = right_i;
00320     }
00321 
00322 public:
00323 
00324     // destructor
00325 
00326     virtual ~sc_uint_subref_r()
00327     {}
00328 
00329     // capacity
00330 
00331     int length() const
00332     { return ( m_left - m_right + 1 ); }
00333 
00334 #ifdef SC_DT_DEPRECATED
00335     int bitwidth() const
00336     { return length(); }
00337 #endif
00338 
00339     // concatenation support
00340 
00341     virtual int concat_length(bool* xz_present_p) const
00342     { if ( xz_present_p ) *xz_present_p = false; return length(); }
00343     virtual bool concat_get_ctrl( sc_digit* dst_p, int low_i ) const;
00344     virtual bool concat_get_data( sc_digit* dst_p, int low_i ) const;
00345     virtual uint64 concat_get_uint64() const
00346     { return (uint64)operator uint_type(); }
00347 
00348 
00349     // reduce methods
00350 
00351     bool and_reduce() const;
00352 
00353     bool nand_reduce() const
00354     { return ( ! and_reduce() ); }
00355 
00356     bool or_reduce() const;
00357 
00358     bool nor_reduce() const
00359     { return ( ! or_reduce() ); }
00360 
00361     bool xor_reduce() const;
00362 
00363     bool xnor_reduce() const
00364     { return ( ! xor_reduce() ); }
00365 
00366 
00367     // implicit conversion to uint_type
00368 
00369     operator uint_type() const;
00370 
00371 
00372     // explicit conversions
00373 
00374     uint_type value() const
00375     { return operator uint_type(); }
00376 
00377 
00378     int           to_int() const;
00379     unsigned int  to_uint() const;
00380     long          to_long() const;
00381     unsigned long to_ulong() const;
00382     int64         to_int64() const;
00383     uint64        to_uint64() const;
00384     double        to_double() const;
00385 
00386 
00387     // explicit conversion to character string
00388 
00389     const std::string to_string( sc_numrep numrep = SC_DEC ) const;
00390     const std::string to_string( sc_numrep numrep, bool w_prefix ) const;
00391 
00392 
00393     // other methods
00394 
00395     void print( ::std::ostream& os = ::std::cout ) const
00396     { os << to_string(sc_io_base(os,SC_DEC),sc_io_show_base(os)); }
00397 
00398 protected:
00399 
00400     int           m_left;
00401     sc_uint_base* m_obj_p;
00402     int           m_right;
00403 
00404 private:
00405 
00406     // disabled
00407     sc_uint_subref_r& operator = ( const sc_uint_subref_r& );
00408 };
00409 
00410 
00411 
00412 inline
00413 ::std::ostream&
00414 operator << ( ::std::ostream&, const sc_uint_subref_r& );
00415 
00416 
00417 // ----------------------------------------------------------------------------
00418 //  CLASS : sc_uint_subref
00419 //
00420 //  Proxy class for sc_uint part selection (r-value and l-value).
00421 // ----------------------------------------------------------------------------
00422 
00423 class sc_uint_subref
00424     : public sc_uint_subref_r
00425 {
00426     friend class sc_uint_base;
00427     friend class sc_core::sc_vpool<sc_uint_subref>;
00428 
00429 
00430     // constructors
00431 
00432 protected:
00433     sc_uint_subref()
00434         {}
00435 
00436 public:
00437     sc_uint_subref( const sc_uint_subref& init ) : sc_uint_subref_r(init)
00438         {}
00439 
00440 public:
00441 
00442     // assignment operators
00443 
00444     sc_uint_subref& operator = ( uint_type v );
00445 
00446     sc_uint_subref& operator = ( const sc_uint_base& a );
00447 
00448     sc_uint_subref& operator = ( const sc_uint_subref_r& a )
00449     { return operator = ( a.operator uint_type() ); }
00450 
00451     sc_uint_subref& operator = ( const sc_uint_subref& a )
00452     { return operator = ( a.operator uint_type() ); }
00453 
00454     template<class T>
00455     sc_uint_subref& operator = ( const sc_generic_base<T>& a )
00456         { return operator = ( a->to_uint64() ); }
00457 
00458     sc_uint_subref& operator = ( const char* a );
00459 
00460     sc_uint_subref& operator = ( unsigned long a )
00461     { return operator = ( (uint_type) a ); }
00462 
00463     sc_uint_subref& operator = ( long a )
00464     { return operator = ( (uint_type) a ); }
00465 
00466     sc_uint_subref& operator = ( unsigned int a )
00467     { return operator = ( (uint_type) a ); }
00468 
00469     sc_uint_subref& operator = ( int a )
00470     { return operator = ( (uint_type) a ); }
00471 
00472     sc_uint_subref& operator = ( int64 a )
00473     { return operator = ( (uint_type) a ); }
00474 
00475     sc_uint_subref& operator = ( double a )
00476     { return operator = ( (uint_type) a ); }
00477 
00478     sc_uint_subref& operator = ( const sc_signed& );
00479     sc_uint_subref& operator = ( const sc_unsigned& );
00480     sc_uint_subref& operator = ( const sc_bv_base& );
00481     sc_uint_subref& operator = ( const sc_lv_base& );
00482 
00483     // concatenation methods
00484 
00485     virtual void concat_set(int64 src, int low_i);
00486     virtual void concat_set(const sc_signed& src, int low_i);
00487     virtual void concat_set(const sc_unsigned& src, int low_i);
00488     virtual void concat_set(uint64 src, int low_i);
00489 
00490     // other methods
00491 
00492     void scan( ::std::istream& is = ::std::cin );
00493 
00494 protected:
00495     static sc_core::sc_vpool<sc_uint_subref> m_pool;
00496 
00497 };
00498 
00499 
00500 
00501 inline
00502 ::std::istream&
00503 operator >> ( ::std::istream&, sc_uint_subref& );
00504 
00505 
00506 // ----------------------------------------------------------------------------
00507 //  CLASS : sc_uint_base
00508 //
00509 //  Base class for sc_uint.
00510 // ----------------------------------------------------------------------------
00511 
00512 class sc_uint_base : public sc_value_base
00513 {
00514     friend class sc_uint_bitref_r;
00515     friend class sc_uint_bitref;
00516     friend class sc_uint_subref_r;
00517     friend class sc_uint_subref;
00518 
00519 
00520     // support methods
00521 
00522     void invalid_length() const;
00523     void invalid_index( int i ) const;
00524     void invalid_range( int l, int r ) const;
00525 
00526     void check_length() const
00527     { if( m_len <= 0 || m_len > SC_INTWIDTH ) { invalid_length(); } }
00528 
00529     void check_index( int i ) const
00530     { if( i < 0 || i >= m_len ) { invalid_index( i ); } }
00531 
00532     void check_range( int l, int r ) const
00533     { if( r < 0 || l >= m_len || l < r ) { invalid_range( l, r ); } }
00534 
00535     void check_value() const;
00536 
00537     void extend_sign()
00538     {
00539 #ifdef DEBUG_SYSTEMC
00540         check_value();
00541 #endif
00542         m_val &= ( ~UINT_ZERO >> m_ulen );
00543     }
00544 
00545 public:
00546 
00547     // constructors
00548 
00549     explicit sc_uint_base( int w = sc_length_param().len() )
00550     : m_val( 0 ), m_len( w ), m_ulen( SC_INTWIDTH - m_len )
00551     { check_length(); }
00552 
00553     sc_uint_base( uint_type v, int w )
00554     : m_val( v ), m_len( w ), m_ulen( SC_INTWIDTH - m_len )
00555     { check_length(); extend_sign(); }
00556 
00557     sc_uint_base( const sc_uint_base& a )
00558     : m_val( a.m_val ), m_len( a.m_len ), m_ulen( a.m_ulen )
00559     {}
00560 
00561     explicit sc_uint_base( const sc_uint_subref_r& a )
00562         : m_val( a ), m_len( a.length() ), m_ulen( SC_INTWIDTH - m_len )
00563         { extend_sign(); }
00564 
00565     template<class T>
00566     explicit sc_uint_base( const sc_generic_base<T>& a )
00567     : m_val( a->to_uint64() ), m_len( a->length() ),
00568       m_ulen( SC_INTWIDTH - m_len )
00569     { check_length(); extend_sign(); }
00570 
00571     explicit sc_uint_base( const sc_bv_base& v );
00572     explicit sc_uint_base( const sc_lv_base& v );
00573     explicit sc_uint_base( const sc_int_subref_r& v );
00574     explicit sc_uint_base( const sc_signed_subref_r& v );
00575     explicit sc_uint_base( const sc_unsigned_subref_r& v );
00576     explicit sc_uint_base( const sc_signed& a );
00577     explicit sc_uint_base( const sc_unsigned& a );
00578 
00579 
00580     // destructor
00581 
00582     virtual ~sc_uint_base()
00583     {}
00584 
00585 
00586     // assignment operators
00587 
00588     sc_uint_base& operator = ( uint_type v )
00589     { m_val = v; extend_sign(); return *this; }
00590 
00591     sc_uint_base& operator = ( const sc_uint_base& a )
00592     { m_val = a.m_val; extend_sign(); return *this; }
00593 
00594     sc_uint_base& operator = ( const sc_uint_subref_r& a )
00595         { m_val = a; extend_sign(); return *this; }
00596 
00597     template<class T>
00598     sc_uint_base& operator = ( const sc_generic_base<T>& a )
00599         { m_val = a->to_uint64(); extend_sign(); return *this; }
00600 
00601     sc_uint_base& operator = ( const sc_signed& a );
00602     sc_uint_base& operator = ( const sc_unsigned& a );
00603 
00604 #ifdef SC_INCLUDE_FX
00605     sc_uint_base& operator = ( const sc_fxval& a );
00606     sc_uint_base& operator = ( const sc_fxval_fast& a );
00607     sc_uint_base& operator = ( const sc_fxnum& a );
00608     sc_uint_base& operator = ( const sc_fxnum_fast& a );
00609 #endif
00610 
00611     sc_uint_base& operator = ( const sc_bv_base& a );
00612     sc_uint_base& operator = ( const sc_lv_base& a );
00613 
00614     sc_uint_base& operator = ( const char* a );
00615 
00616     sc_uint_base& operator = ( unsigned long a )
00617     { m_val = a; extend_sign(); return *this; }
00618 
00619     sc_uint_base& operator = ( long a )
00620     { m_val = a; extend_sign(); return *this; }
00621 
00622     sc_uint_base& operator = ( unsigned int a )
00623     { m_val = a; extend_sign(); return *this; }
00624 
00625     sc_uint_base& operator = ( int a )
00626     { m_val = a; extend_sign(); return *this; }
00627 
00628     sc_uint_base& operator = ( int64 a )
00629     { m_val = a; extend_sign(); return *this; }
00630 
00631     sc_uint_base& operator = ( double a )
00632     { m_val = (uint_type) a; extend_sign(); return *this; }
00633 
00634 
00635     // arithmetic assignment operators
00636 
00637     sc_uint_base& operator += ( uint_type v )
00638     { m_val += v; extend_sign(); return *this; }
00639 
00640     sc_uint_base& operator -= ( uint_type v )
00641     { m_val -= v; extend_sign(); return *this; }
00642 
00643     sc_uint_base& operator *= ( uint_type v )
00644     { m_val *= v; extend_sign(); return *this; }
00645 
00646     sc_uint_base& operator /= ( uint_type v )
00647     { m_val /= v; extend_sign(); return *this; }
00648 
00649     sc_uint_base& operator %= ( uint_type v )
00650     { m_val %= v; extend_sign(); return *this; }
00651 
00652 
00653     // bitwise assignment operators
00654 
00655     sc_uint_base& operator &= ( uint_type v )
00656     { m_val &= v; extend_sign(); return *this; }
00657 
00658     sc_uint_base& operator |= ( uint_type v )
00659     { m_val |= v; extend_sign(); return *this; }
00660 
00661     sc_uint_base& operator ^= ( uint_type v )
00662     { m_val ^= v; extend_sign(); return *this; }
00663 
00664 
00665     sc_uint_base& operator <<= ( uint_type v )
00666     { m_val <<= v; extend_sign(); return *this; }
00667 
00668     sc_uint_base& operator >>= ( uint_type v )
00669     { m_val >>= v; /* no sign extension needed */ return *this; }
00670 
00671 
00672     // prefix and postfix increment and decrement operators
00673 
00674     sc_uint_base& operator ++ () // prefix
00675     { ++ m_val; extend_sign(); return *this; }
00676 
00677     const sc_uint_base operator ++ ( int ) // postfix
00678     { sc_uint_base tmp( *this ); ++ m_val; extend_sign(); return tmp; }
00679 
00680     sc_uint_base& operator -- () // prefix
00681     { -- m_val; extend_sign(); return *this; }
00682 
00683     const sc_uint_base operator -- ( int ) // postfix
00684     { sc_uint_base tmp( *this ); -- m_val; extend_sign(); return tmp; }
00685 
00686 
00687     // relational operators
00688 
00689     friend bool operator == ( const sc_uint_base& a, const sc_uint_base& b )
00690     { return a.m_val == b.m_val; }
00691 
00692     friend bool operator != ( const sc_uint_base& a, const sc_uint_base& b )
00693     { return a.m_val != b.m_val; }
00694 
00695     friend bool operator <  ( const sc_uint_base& a, const sc_uint_base& b )
00696     { return a.m_val < b.m_val; }
00697 
00698     friend bool operator <= ( const sc_uint_base& a, const sc_uint_base& b )
00699     { return a.m_val <= b.m_val; }
00700 
00701     friend bool operator >  ( const sc_uint_base& a, const sc_uint_base& b )
00702     { return a.m_val > b.m_val; }
00703 
00704     friend bool operator >= ( const sc_uint_base& a, const sc_uint_base& b )
00705     { return a.m_val >= b.m_val; }
00706 
00707 
00708     // bit selection
00709 
00710     sc_uint_bitref&         operator [] ( int i );
00711     const sc_uint_bitref_r& operator [] ( int i ) const;
00712 
00713     sc_uint_bitref&         bit( int i );
00714     const sc_uint_bitref_r& bit( int i ) const;
00715 
00716 
00717     // part selection
00718 
00719     sc_uint_subref&         operator () ( int left, int right );
00720     const sc_uint_subref_r& operator () ( int left, int right ) const;
00721 
00722     sc_uint_subref&         range( int left, int right );
00723     const sc_uint_subref_r& range( int left, int right ) const;
00724 
00725 
00726     // bit access, without bounds checking or sign extension
00727 
00728     bool test( int i ) const
00729     { return ( 0 != (m_val & (UINT_ONE << i)) ); }
00730 
00731     void set( int i )
00732     { m_val |= (UINT_ONE << i); }
00733 
00734     void set( int i, bool v )
00735     { v ? m_val |= (UINT_ONE << i) : m_val &= ~(UINT_ONE << i); }
00736 
00737 
00738     // capacity
00739 
00740     int length() const
00741     { return m_len; }
00742 
00743 #ifdef SC_DT_DEPRECATED
00744     int bitwidth() const
00745     { return length(); }
00746 #endif
00747 
00748     // concatenation support
00749 
00750     virtual int concat_length(bool* xz_present_p) const
00751     { if ( xz_present_p ) *xz_present_p = false; return length(); }
00752     virtual bool concat_get_ctrl( sc_digit* dst_p, int low_i ) const;
00753     virtual bool concat_get_data( sc_digit* dst_p, int low_i ) const;
00754     virtual uint64 concat_get_uint64() const
00755         { return m_val; }
00756     virtual void concat_set(int64 src, int low_i);
00757     virtual void concat_set(const sc_signed& src, int low_i);
00758     virtual void concat_set(const sc_unsigned& src, int low_i);
00759     virtual void concat_set(uint64 src, int low_i);
00760 
00761 
00762     // reduce methods
00763 
00764     bool and_reduce() const;
00765 
00766     bool nand_reduce() const
00767     { return ( ! and_reduce() ); }
00768 
00769     bool or_reduce() const;
00770 
00771     bool nor_reduce() const
00772     { return ( ! or_reduce() ); }
00773 
00774     bool xor_reduce() const;
00775 
00776     bool xnor_reduce() const
00777     { return ( ! xor_reduce() ); }
00778 
00779 
00780     // implicit conversion to uint_type
00781 
00782     operator uint_type() const
00783     { return m_val; }
00784 
00785 
00786     // explicit conversions
00787 
00788     uint_type value() const
00789     { return operator uint_type(); }
00790 
00791 
00792     int to_int() const
00793     { return (int) m_val; }
00794 
00795     unsigned int to_uint() const
00796     { return (unsigned int) m_val; }
00797 
00798     long to_long() const
00799     { return (long) m_val; }
00800 
00801     unsigned long to_ulong() const
00802     { return (unsigned long) m_val; }
00803 
00804     int64 to_int64() const
00805     { return (int64) m_val; }
00806 
00807     uint64 to_uint64() const
00808     { return (uint64) m_val; }
00809 
00810     double to_double() const
00811         { return uint64_to_double( m_val ); }
00812 
00813 
00814 #ifndef _32BIT_
00815     long long_low() const
00816     { return (long) (m_val & UINT64_32ONES); }
00817 
00818     long long_high() const
00819     { return (long) ((m_val >> 32) & UINT64_32ONES); }
00820 #endif
00821 
00822     // explicit conversion to character string
00823 
00824     const std::string to_string( sc_numrep numrep = SC_DEC ) const;
00825     const std::string to_string( sc_numrep numrep, bool w_prefix ) const;
00826 
00827 
00828     // other methods
00829 
00830     void print( ::std::ostream& os = ::std::cout ) const
00831     { os << to_string(sc_io_base(os,SC_DEC),sc_io_show_base(os)); }
00832 
00833     void scan( ::std::istream& is = ::std::cin );
00834 
00835 protected:
00836 
00837     uint_type m_val;   // value
00838     int       m_len;   // length
00839     int       m_ulen;  // unused length
00840 };
00841 
00842 
00843 
00844 inline
00845 ::std::ostream&
00846 operator << ( ::std::ostream&, const sc_uint_base& );
00847 
00848 inline
00849 ::std::istream&
00850 operator >> ( ::std::istream&, sc_uint_base& );
00851 
00852 
00853 
00854 // ----------------------------------------------------------------------------
00855 //  CLASS : sc_uint_bitref_r
00856 //
00857 //  Proxy class for sc_uint bit selection (r-value only).
00858 // ----------------------------------------------------------------------------
00859 
00860 // implicit conversion to bool
00861 
00862 inline
00863 sc_uint_bitref_r::operator uint64 () const
00864 {
00865     return m_obj_p->test( m_index );
00866 }
00867 
00868 inline
00869 bool
00870 sc_uint_bitref_r::operator ! () const
00871 {
00872     return ! m_obj_p->test( m_index );
00873 }
00874 
00875 inline
00876 bool
00877 sc_uint_bitref_r::operator ~ () const
00878 {
00879     return ! m_obj_p->test( m_index );
00880 }
00881 
00882 
00883 
00884 inline
00885 ::std::ostream&
00886 operator << ( ::std::ostream& os, const sc_uint_bitref_r& a )
00887 {
00888     a.print( os );
00889     return os;
00890 }
00891 
00892 
00893 // ----------------------------------------------------------------------------
00894 //  CLASS : sc_uint_bitref
00895 //
00896 //  Proxy class for sc_uint bit selection (r-value and l-value).
00897 // ----------------------------------------------------------------------------
00898 
00899 // assignment operators
00900 
00901 inline
00902 sc_uint_bitref&
00903 sc_uint_bitref::operator = ( const sc_uint_bitref_r& b )
00904 {
00905     m_obj_p->set( m_index, b.to_bool() );
00906     return *this;
00907 }
00908 
00909 inline
00910 sc_uint_bitref&
00911 sc_uint_bitref::operator = ( const sc_uint_bitref& b )
00912 {
00913     m_obj_p->set( m_index, b.to_bool() );
00914     return *this;
00915 }
00916 
00917 inline
00918 sc_uint_bitref&
00919 sc_uint_bitref::operator = ( bool b )
00920 {
00921     m_obj_p->set( m_index, b );
00922     return *this;
00923 }
00924 
00925 
00926 inline
00927 sc_uint_bitref&
00928 sc_uint_bitref::operator &= ( bool b )
00929 {
00930     if( ! b ) {
00931     m_obj_p->set( m_index, b );
00932     }
00933     return *this;
00934 }
00935 
00936 inline
00937 sc_uint_bitref&
00938 sc_uint_bitref::operator |= ( bool b )
00939 {
00940     if( b ) {
00941     m_obj_p->set( m_index, b );
00942     }
00943     return *this;
00944 }
00945 
00946 inline
00947 sc_uint_bitref&
00948 sc_uint_bitref::operator ^= ( bool b )
00949 {
00950     if( b ) {
00951     m_obj_p->m_val ^= (UINT_ONE << m_index);
00952     }
00953     return *this;
00954 }
00955 
00956 
00957 
00958 inline
00959 ::std::istream&
00960 operator >> ( ::std::istream& is, sc_uint_bitref& a )
00961 {
00962     a.scan( is );
00963     return is;
00964 }
00965 
00966 
00967 // ----------------------------------------------------------------------------
00968 //  CLASS : sc_uint_subref_r
00969 //
00970 //  Proxy class for sc_uint part selection (r-value only).
00971 // ----------------------------------------------------------------------------
00972 
00973 // implicit conversion to uint_type
00974 
00975 inline
00976 sc_uint_subref_r::operator uint_type() const
00977 {
00978     uint_type val = m_obj_p->m_val;
00979     int uleft = SC_INTWIDTH - (m_left + 1);
00980     return ( (val & (~UINT_ZERO >> uleft)) >> m_right );
00981 }
00982 
00983 
00984 // reduce methods
00985 
00986 inline
00987 bool
00988 sc_uint_subref_r::and_reduce() const
00989 {
00990     sc_uint_base a( *this );
00991     return a.and_reduce();
00992 }
00993 
00994 inline
00995 bool
00996 sc_uint_subref_r::or_reduce() const
00997 {
00998     sc_uint_base a( *this );
00999     return a.or_reduce();
01000 }
01001 
01002 inline
01003 bool
01004 sc_uint_subref_r::xor_reduce() const
01005 {
01006     sc_uint_base a( *this );
01007     return a.xor_reduce();
01008 }
01009 
01010 
01011 // explicit conversions
01012 
01013 inline
01014 int
01015 sc_uint_subref_r::to_int() const
01016 {
01017     sc_uint_base a( *this );
01018     return a.to_int();
01019 }
01020 
01021 inline
01022 unsigned int
01023 sc_uint_subref_r::to_uint() const
01024 {
01025     sc_uint_base a( *this );
01026     return a.to_uint();
01027 }
01028 
01029 inline
01030 long
01031 sc_uint_subref_r::to_long() const
01032 {
01033     sc_uint_base a( *this );
01034     return a.to_long();
01035 }
01036 
01037 inline
01038 unsigned long
01039 sc_uint_subref_r::to_ulong() const
01040 {
01041     sc_uint_base a( *this );
01042     return a.to_ulong();
01043 }
01044 
01045 inline
01046 int64
01047 sc_uint_subref_r::to_int64() const
01048 {
01049     sc_uint_base a( *this );
01050     return a.to_int64();
01051 }
01052 
01053 inline
01054 uint64
01055 sc_uint_subref_r::to_uint64() const
01056 {
01057     sc_uint_base a( *this );
01058     return a.to_uint64();
01059 }
01060 
01061 inline
01062 double
01063 sc_uint_subref_r::to_double() const
01064 {
01065     sc_uint_base a( *this );
01066     return a.to_double();
01067 }
01068 
01069 
01070 // explicit conversion to character string
01071 
01072 inline
01073 const std::string
01074 sc_uint_subref_r::to_string( sc_numrep numrep ) const
01075 {
01076     sc_uint_base a( *this );
01077     return a.to_string( numrep );
01078 }
01079 
01080 inline
01081 const std::string
01082 sc_uint_subref_r::to_string( sc_numrep numrep, bool w_prefix ) const
01083 {
01084     sc_uint_base a( *this );
01085     return a.to_string( numrep, w_prefix );
01086 }
01087 
01088 
01089 // functional notation for the reduce methods
01090 
01091 inline
01092 bool
01093 and_reduce( const sc_uint_subref_r& a )
01094 {
01095     return a.and_reduce();
01096 }
01097 
01098 inline
01099 bool
01100 nand_reduce( const sc_uint_subref_r& a )
01101 {
01102     return a.nand_reduce();
01103 }
01104 
01105 inline
01106 bool
01107 or_reduce( const sc_uint_subref_r& a )
01108 {
01109     return a.or_reduce();
01110 }
01111 
01112 inline
01113 bool
01114 nor_reduce( const sc_uint_subref_r& a )
01115 {
01116     return a.nor_reduce();
01117 }
01118 
01119 inline
01120 bool
01121 xor_reduce( const sc_uint_subref_r& a )
01122 {
01123     return a.xor_reduce();
01124 }
01125 
01126 inline
01127 bool
01128 xnor_reduce( const sc_uint_subref_r& a )
01129 {
01130     return a.xnor_reduce();
01131 }
01132 
01133 
01134 
01135 inline
01136 ::std::ostream&
01137 operator << ( ::std::ostream& os, const sc_uint_subref_r& a )
01138 {
01139     a.print( os );
01140     return os;
01141 }
01142 
01143 
01144 // ----------------------------------------------------------------------------
01145 //  CLASS : sc_uint_subref
01146 //
01147 //  Proxy class for sc_uint part selection (r-value and l-value).
01148 // ----------------------------------------------------------------------------
01149 
01150 // assignment operators
01151 
01152 inline
01153 sc_uint_subref&
01154 sc_uint_subref::operator = ( const sc_uint_base& a )
01155 {
01156     return operator = ( a.operator uint_type() );
01157 }
01158 
01159 inline
01160 sc_uint_subref&
01161 sc_uint_subref::operator = ( const char* a )
01162 {
01163     sc_uint_base aa( length() );
01164     return ( *this = aa = a );
01165 }
01166 
01167 
01168 
01169 inline
01170 ::std::istream&
01171 operator >> ( ::std::istream& is, sc_uint_subref& a )
01172 {
01173     a.scan( is );
01174     return is;
01175 }
01176 
01177 
01178 // ----------------------------------------------------------------------------
01179 //  CLASS : sc_uint_base
01180 //
01181 //  Base class for sc_uint.
01182 // ----------------------------------------------------------------------------
01183 
01184 // bit selection
01185 
01186 inline
01187 sc_uint_bitref&
01188 sc_uint_base::operator [] ( int i )
01189 {
01190     check_index( i );
01191     sc_uint_bitref* result_p = sc_uint_bitref::m_pool.allocate();
01192     result_p->initialize(this, i);
01193     return *result_p;
01194 }
01195 
01196 inline
01197 const sc_uint_bitref_r&
01198 sc_uint_base::operator [] ( int i ) const
01199 {
01200     check_index( i );
01201     sc_uint_bitref* result_p = sc_uint_bitref::m_pool.allocate();
01202     result_p->initialize(this, i);
01203     return *result_p;
01204 }
01205 
01206 
01207 inline
01208 sc_uint_bitref&
01209 sc_uint_base::bit( int i )
01210 {
01211     check_index( i );
01212     sc_uint_bitref* result_p = sc_uint_bitref::m_pool.allocate();
01213     result_p->initialize(this, i);
01214     return *result_p;
01215 }
01216 
01217 inline
01218 const sc_uint_bitref_r&
01219 sc_uint_base::bit( int i ) const
01220 {
01221     check_index( i );
01222     sc_uint_bitref* result_p = sc_uint_bitref::m_pool.allocate();
01223     result_p->initialize(this, i);
01224     return *result_p;
01225 }
01226 
01227 
01228 // part selection
01229 
01230 inline
01231 sc_uint_subref&
01232 sc_uint_base::operator () ( int left, int right )
01233 {
01234     check_range( left, right );
01235     sc_uint_subref* result_p = sc_uint_subref::m_pool.allocate();
01236     result_p->initialize(this, left, right);
01237     return *result_p;
01238 }
01239 
01240 inline
01241 const sc_uint_subref_r&
01242 sc_uint_base::operator () ( int left, int right ) const
01243 {
01244     check_range( left, right );
01245     sc_uint_subref* result_p = sc_uint_subref::m_pool.allocate();
01246     result_p->initialize(this, left, right);
01247     return *result_p;
01248 }
01249 
01250 
01251 inline
01252 sc_uint_subref&
01253 sc_uint_base::range( int left, int right )
01254 {
01255     check_range( left, right );
01256     sc_uint_subref* result_p = sc_uint_subref::m_pool.allocate();
01257     result_p->initialize(this, left, right);
01258     return *result_p;
01259 }
01260 
01261 inline
01262 const sc_uint_subref_r&
01263 sc_uint_base::range( int left, int right ) const
01264 {
01265     check_range( left, right );
01266     sc_uint_subref* result_p = sc_uint_subref::m_pool.allocate();
01267     result_p->initialize(this, left, right);
01268     return *result_p;
01269 }
01270 
01271 
01272 // functional notation for the reduce methods
01273 
01274 inline
01275 bool
01276 and_reduce( const sc_uint_base& a )
01277 {
01278     return a.and_reduce();
01279 }
01280 
01281 inline
01282 bool
01283 nand_reduce( const sc_uint_base& a )
01284 {
01285     return a.nand_reduce();
01286 }
01287 
01288 inline
01289 bool
01290 or_reduce( const sc_uint_base& a )
01291 {
01292     return a.or_reduce();
01293 }
01294 
01295 inline
01296 bool
01297 nor_reduce( const sc_uint_base& a )
01298 {
01299     return a.nor_reduce();
01300 }
01301 
01302 inline
01303 bool
01304 xor_reduce( const sc_uint_base& a )
01305 {
01306     return a.xor_reduce();
01307 }
01308 
01309 inline
01310 bool
01311 xnor_reduce( const sc_uint_base& a )
01312 {
01313     return a.xnor_reduce();
01314 }
01315 
01316 
01317 
01318 inline
01319 ::std::ostream&
01320 operator << ( ::std::ostream& os, const sc_uint_base& a )
01321 {
01322     a.print( os );
01323     return os;
01324 }
01325 
01326 inline
01327 ::std::istream&
01328 operator >> ( ::std::istream& is, sc_uint_base& a )
01329 {
01330     a.scan( is );
01331     return is;
01332 }
01333 
01334 } // namespace sc_dt
01335 
01336 
01337 #endif
01338 
01339 // Taf!

Generated on Wed Jan 21 15:32:08 2009 for SystemC by  doxygen 1.5.5