scx_signal_uint.h revision 12922
1/***************************************************************************** 2 3 Licensed to Accellera Systems Initiative Inc. (Accellera) under one or 4 more contributor license agreements. See the NOTICE file distributed 5 with this work for additional information regarding copyright ownership. 6 Accellera licenses this file to you under the Apache License, Version 2.0 7 (the "License"); you may not use this file except in compliance with the 8 License. You may obtain a copy of the License at 9 10 http://www.apache.org/licenses/LICENSE-2.0 11 12 Unless required by applicable law or agreed to in writing, software 13 distributed under the License is distributed on an "AS IS" BASIS, 14 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or 15 implied. See the License for the specific language governing 16 permissions and limitations under the License. 17 18 *****************************************************************************/ 19 20/***************************************************************************** 21 22 sc_signal_uint.cpp -- The sc_signal<sc_dt::sc_uint<W> > implementations. 23 24 Original Author: Andy Goodrich, Forte Design Systems, 2002-10-22 25 26 *****************************************************************************/ 27 28/***************************************************************************** 29 30 MODIFICATION LOG - modifiers, enter your name, affiliation, date and 31 changes you are making here. 32 33 Name, Affiliation, Date: 34 Description of Modification: 35 36 *****************************************************************************/ 37 38/* 39$Log: scx_signal_uint.h,v $ 40Revision 1.1 2011/08/15 17:31:11 acg 41 Andy Goodrich: moved specialized signals from examples to this tree. 42 43Revision 1.2 2011/08/15 16:43:24 acg 44 Torsten Maehne: changes to remove unused argument warnings. 45 46Revision 1.1.1.1 2006/12/15 20:20:03 acg 47SystemC 2.3 48 49Revision 1.2 2005/12/26 20:11:14 acg 50Fixed up copyright. 51 52Revision 1.1.1.1 2005/12/19 23:16:42 acg 53First check in of SystemC 2.1 into its own archive. 54 55Revision 1.16 2005/09/15 23:01:52 acg 56Added std:: prefix to appropriate methods and types to get around 57issues with the Edison Front End. 58 59Revision 1.15 2005/05/03 19:52:26 acg 60Get proper header locations on includes. 61 62Revision 1.14 2005/05/03 19:50:20 acg 63Name space version. 64 65Revision 1.11 2005/04/11 19:05:36 acg 66Change to sc_clock for Microsoft VCC 6.0. Changes for namespaces 67 68Revision 1.10 2005/04/03 22:52:52 acg 69Namespace changes. 70 71Revision 1.9 2005/03/21 22:31:32 acg 72Changes to sc_core namespace. 73 74Revision 1.8 2004/09/27 21:01:59 acg 75Andy Goodrich - Forte Design Systems, Inc. 76 - This is specialized signal support that allows better use of signals 77 and ports whose target value is a SystemC native type. 78 79*/ 80 81 82 83#include <systemc> 84#include <typeinfo> 85 86/***************************************************************************** 87 88 sc_signal_uint.h -- The sc_signal<sc_uint<W> > definitions. 89 90 Original Author: Andy Goodrich, Forte Design Systems, 2002-10-22 91 92 *****************************************************************************/ 93 94/***************************************************************************** 95 96 MODIFICATION LOG - modifiers, enter your name, affiliation, date and 97 changes you are making here. 98 99 Name, Affiliation, Date: 100 Description of Modification: 101 102 *****************************************************************************/ 103 104/* 105$Log: scx_signal_uint.h,v $ 106Revision 1.1 2011/08/15 17:31:11 acg 107 Andy Goodrich: moved specialized signals from examples to this tree. 108 109Revision 1.3 2011/08/15 16:43:24 acg 110 Torsten Maehne: changes to remove unused argument warnings. 111 112Revision 1.2 2011/06/28 21:23:02 acg 113 Andy Goodrich: merging of SCV tree. 114 115Revision 1.1.1.1 2006/12/15 20:20:03 acg 116SystemC 2.3 117 118Revision 1.4 2006/04/05 23:47:02 acg 119 Andy Goodrich: changed sc_get_current_process_base calls into 120 sc_get_current_process_b calls. 121 122Revision 1.3 2006/03/21 01:31:48 acg 123 Andy Goodrich: changed over to sc_get_current_process_b() from 124 sc_get_current_process_base() since the function's name changed. 125 126Revision 1.2 2005/12/26 20:11:14 acg 127Fixed up copyright. 128 129Revision 1.1.1.1 2005/12/19 23:16:42 acg 130First check in of SystemC 2.1 into its own archive. 131 132Revision 1.27 2005/09/15 23:01:52 acg 133Added std:: prefix to appropriate methods and types to get around 134issues with the Edison Front End. 135 136Revision 1.26 2005/07/30 03:44:11 acg 137Changes from 2.1. 138 139Revision 1.25 2005/06/10 22:40:55 acg 140Changes from 2.1 for operator << and other iostream stuff. 141 142Revision 1.24 2005/05/09 17:17:12 acg 143Changes from 2.1. 144 145Revision 1.23 2005/05/08 19:04:06 acg 146Fix bug in concat_set(int64,off). Other changes from 2.1 examples usage. 147 148Revision 1.22 2005/05/03 19:50:20 acg 149Name space version. 150 151Revision 1.20 2005/03/21 22:31:32 acg 152Changes to sc_core namespace. 153 154Revision 1.18 2004/11/09 00:11:27 acg 155Added support for sc_generic_base<T> in place of sc_concatref. sc_concatref 156now is derived from sc_generic_base<sc_concatref>. 157 158Revision 1.17 2004/09/27 21:01:59 acg 159Andy Goodrich - Forte Design Systems, Inc. 160 - This is specialized signal support that allows better use of signals 161 and ports whose target value is a SystemC native type. 162 163*/ 164 165 166#if !defined(SC_SIGNAL_UINT_H) 167#define SC_SIGNAL_UINT_H 168 169#if ( !defined(_MSC_VER) || _MSC_VER > 1200 ) 170# define SC_TEMPLATE template<int W> 171#else 172# define SC_TEMPLATE template<> template<int W> 173#endif 174 175// FORWARD REFERENCES AND USINGS: 176 177namespace sc_core { 178 179class sc_uint_sigref; 180 181//============================================================================== 182// CLASS sc_uint_part_if 183// 184// This class provides generic access to part selections for signals whose 185// data type is sc_dt::sc_uint<W>. This class serves as the base class for the 186// sc_dt::sc_uint<W> specialization of the sc_signal_in_if<T> class. The methods 187// in this class may be over-ridden individually, those that are not overridden 188// will produce an error message when called. The methods are used by the 189// sc_uint_sigref class. 190// 191// Notes: 192// (1) Descriptions of the methods and operators in this class appear with 193// their implementations in sc_signal<sc_dt::sc_uint<W> >. 194//============================================================================== 195class sc_uint_part_if : virtual public sc_interface { 196 protected: 197 // constructor: 198 sc_uint_part_if() {} 199 200 public: 201 // perform a part read. 202 virtual sc_dt::sc_uint_base* part_read_target(); 203 virtual sc_dt::uint64 read_part( int left, int right ) const; 204 205 // perform a part write. 206 virtual sc_uint_sigref& select_part( int left, int right ); 207 virtual void write_part( sc_dt::uint64 v, int left, int right ); 208 209 private: 210 sc_uint_part_if( const sc_uint_part_if& ); 211 sc_uint_part_if& operator = ( const sc_uint_part_if& ); 212}; 213 214 215//============================================================================== 216// CLASS sc_signal_in_if<sc_dt::sc_uint<W> > 217// 218// This is the class specializations for the sc_signal_in_if<T> class to 219// provide additional features for sc_signal instances whose template is 220// sc_dt::sc_uint<W>, including part access. 221// 222// Notes: 223// (1) Descriptions of the methods and operators in this class appear with 224// their implementations in sc_signal<sc_dt::sc_uint<W> >. 225//============================================================================== 226template< int W > 227class sc_signal_in_if<sc_dt::sc_uint<W> > : public sc_uint_part_if { 228 friend class sc_uint_sigref; 229 public: 230 typedef sc_signal_in_if<sc_dt::sc_uint<W> > this_type; 231 232 // get the value changed event 233 virtual const sc_event& value_changed_event() const = 0; 234 235 236 // read the current value 237 virtual const sc_dt::sc_uint<W>& read() const = 0; 238 239 // get a reference to the current value (for tracing) 240 virtual const sc_dt::sc_uint<W>& get_data_ref() const = 0; 241 242 243 // was there a value changed event? 244 virtual bool event() const = 0; 245 246 protected: 247 // constructor 248 sc_signal_in_if() 249 {} 250 251 private: // disabled 252 sc_signal_in_if( const this_type& ); 253 this_type& operator = ( const this_type& ); 254}; 255 256//============================================================================= 257// CLASS : sc_uint_sigref 258// 259// Proxy class for sc_signal_uint bit and part selection. 260//============================================================================= 261class sc_uint_sigref : public sc_dt::sc_uint_subref_r 262{ 263 public: 264 sc_uint_sigref() : sc_dt::sc_uint_subref_r() {} 265 virtual ~sc_uint_sigref() {} 266 virtual void concat_set(sc_dt::int64 src, int low_i); 267 virtual void concat_set(const sc_dt::sc_signed& src, int low_i); 268 virtual void concat_set(const sc_dt::sc_unsigned& src, int low_i); 269 virtual void concat_set(const sc_dt::sc_lv_base& src, int low_i); 270 virtual void concat_set(sc_dt::uint64 src, int low_i); 271 272 public: 273 inline void initialize( sc_uint_part_if* if_p, int left_, int right_ ); 274 275 public: 276 inline void operator = ( sc_dt::uint64 v ); 277 inline void operator = ( const char* v ); 278 inline void operator = ( unsigned long v ); 279 inline void operator = ( long v ); 280 inline void operator = ( unsigned int v ); 281 inline void operator = ( int v ); 282 inline void operator = ( sc_dt::int64 v ); 283 inline void operator = ( double v ); 284 inline void operator = ( const sc_uint_sigref& v ); 285 template<typename T> 286 inline void operator = ( const sc_dt::sc_generic_base<T>& v ); 287 inline void operator = ( const sc_dt::sc_signed& v ); 288 inline void operator = ( const sc_dt::sc_unsigned& v ); 289 inline void operator = ( const sc_dt::sc_bv_base& v ); 290 inline void operator = ( const sc_dt::sc_lv_base& v ); 291 292 public: 293 static sc_vpool<sc_uint_sigref> m_pool; // Pool of objects to use. 294 295 protected: 296 sc_uint_part_if* m_if_p; // Target for selection. 297 298 private: 299 300 // disabled 301 sc_uint_sigref( const sc_uint_sigref& a ); 302}; 303 304 305//============================================================================== 306// CLASS sc_signal<sc_dt::sc_uint<W> > 307// 308// This class implements a signal whose value acts like an sc_dt::sc_uint<W> data 309// value. This class is a specialization of the generic sc_signal class to 310// implement tailored support for the sc_dt::sc_uint<W> class. 311// 312// Notes: 313// (1) Descriptions of the methods and operators in this class appear with 314// their implementations. 315//============================================================================== 316SC_TEMPLATE 317class sc_signal<sc_dt::sc_uint<W> > : 318 public sc_signal_inout_if<sc_dt::sc_uint<W> >, 319 public sc_prim_channel, 320 public sc_dt::sc_uint<W> 321{ 322 public: // typedefs 323 typedef sc_signal<sc_dt::sc_uint<W> > this_type; 324 325 public: // constructors and destructor: 326 inline sc_signal(); 327 explicit inline sc_signal(const char* name_); 328 virtual inline ~sc_signal(); 329 330 public: // base methods: 331 inline bool base_event() const; 332 inline const sc_dt::sc_uint<W>& base_read() const; 333 inline const sc_event& base_value_changed_event() const; 334 inline void base_write( sc_dt::uint64 value ); 335 336 public: // sc_prim_channel virtual methods: 337 virtual inline const char* kind() const; 338 virtual inline void update(); 339 340 public: // sc_interface virtual methods: 341 virtual inline const sc_event& default_event() const; 342 virtual inline void register_port( 343 sc_port_base& port_, const char* if_typename_ ); 344 345 public: // sc_uint_channel virtual methods: 346 virtual sc_dt::sc_uint_base* part_read_target(); 347 virtual inline sc_dt::uint64 read_part(int left, int right) const; 348 virtual inline sc_uint_sigref& select_part(int left, int right); 349 virtual inline void write_part(sc_dt::uint64 v, int left, int right); 350 351 public: // interface virtual methods: 352 virtual inline bool event() const; 353 virtual inline const sc_dt::sc_uint<W>& get_data_ref() const; 354 // virtual inline sc_signal<sc_dt::sc_uint<W> >& get_signal() ; 355 virtual inline const sc_dt::sc_uint<W>& read() const; 356 virtual inline const sc_event& value_changed_event() const; 357 virtual inline void write( const sc_in<sc_dt::sc_uint<W> >& value ); 358 virtual inline void write( const sc_inout<sc_dt::sc_uint<W> >& value ); 359 virtual inline void write( const sc_dt::sc_uint<W>& value ); 360 361 public: // part selections: 362 inline sc_uint_sigref& operator () ( int left, int right ); 363 inline sc_uint_sigref& operator [] ( int bit ); 364 365 public: // operators: 366 inline void operator = ( const this_type& new_val ); 367 inline void operator = ( const char* new_val ); 368 inline void operator = ( sc_dt::uint64 new_val ); 369 inline void operator = ( sc_dt::int64 new_val ); 370 inline void operator = ( int new_val ); 371 inline void operator = ( long new_val ) ; 372 inline void operator = ( short new_val ) ; 373 inline void operator = ( unsigned int new_val ) ; 374 inline void operator = ( unsigned long new_val ); 375 inline void operator = ( unsigned short new_val ); 376 template<typename T> 377 inline void operator = ( const sc_dt::sc_generic_base<T>& new_val ); 378 inline void operator = ( const sc_dt::sc_signed& new_val ); 379 inline void operator = ( const sc_dt::sc_unsigned& new_val ); 380 inline void operator = ( const sc_dt::sc_bv_base& new_val ); 381 inline void operator = ( const sc_dt::sc_lv_base& new_val ); 382 383 public: // concatenation methods (we inherit length and gets from sc_dt::sc_uint<W>): 384 virtual inline void concat_set(sc_dt::int64 src, int low_i); 385 virtual inline void concat_set(const sc_dt::sc_lv_base& src, int low_i); 386 virtual inline void concat_set(const sc_dt::sc_signed& src, int low_i); 387 virtual inline void concat_set(const sc_dt::sc_unsigned& src, int low_i); 388 virtual inline void concat_set(sc_dt::uint64 src, int low_i); 389 390 protected: // debugging methods: 391 // #### void check_port(); 392 void check_writer(); 393 394 private: // Disabled operations that sc_dt::sc_uint<W> supports: 395 sc_signal<sc_dt::sc_uint<W> >& operator ++ (); // prefix 396 const sc_signal<sc_dt::sc_uint<W> >& operator ++ (int); // postfix 397 sc_signal<sc_dt::sc_uint<W> >& operator -- (); // prefix 398 const sc_signal<sc_dt::sc_uint<W> >& operator -- (int); // postfix 399 sc_signal<sc_dt::sc_uint<W> >& operator += (sc_dt::uint_type); 400 sc_signal<sc_dt::sc_uint<W> >& operator -= (sc_dt::uint_type); 401 sc_signal<sc_dt::sc_uint<W> >& operator *= (sc_dt::uint_type); 402 sc_signal<sc_dt::sc_uint<W> >& operator /= (sc_dt::uint_type); 403 sc_signal<sc_dt::sc_uint<W> >& operator %= (sc_dt::uint_type); 404 sc_signal<sc_dt::sc_uint<W> >& operator &= (sc_dt::uint_type); 405 sc_signal<sc_dt::sc_uint<W> >& operator |= (sc_dt::uint_type); 406 sc_signal<sc_dt::sc_uint<W> >& operator ^= (sc_dt::uint_type); 407 408 protected: 409 mutable sc_event* m_changed_event_p; // Value changed event this object. 410 sc_dt::uint64 m_event_delta; // Delta cycle of last event. 411 sc_dt::uint64 m_new_val; // New value for this object instance. 412 sc_port_base* m_output_p; // Single write port verify field. 413 sc_process_b* m_writer_p; // Single writer verify field. 414}; 415 416 417SC_TEMPLATE // Return true if a changed event happened in the last delta cycle. 418inline bool sc_signal<sc_dt::sc_uint<W> >::base_event() const 419{ 420 return simcontext()->delta_count() == m_event_delta + 1; 421} 422 423 424SC_TEMPLATE // Return this object's sc_dt::sc_uint<W> object instance. 425inline const sc_dt::sc_uint<W>& sc_signal<sc_dt::sc_uint<W> >::base_read() const 426{ 427 return *this; 428} 429 430 431SC_TEMPLATE // Return the value changed event, allocating it if necessary. 432inline const sc_event& sc_signal<sc_dt::sc_uint<W> >::base_value_changed_event() const 433{ 434 if ( !m_changed_event_p ) m_changed_event_p = new sc_event; 435 return *m_changed_event_p; 436} 437 438 439SC_TEMPLATE // Write an sc_dt::uint64 value to this object instance. 440inline void sc_signal<sc_dt::sc_uint<W> >::base_write( sc_dt::uint64 value ) 441{ 442# if defined(DEBUG_SYSTEMC) 443 check_writer(); 444# endif 445 m_new_val = value; 446 request_update(); 447} 448 449//------------------------------------------------------------------------------ 450//"sc_signal<sc_dt::sc_uint<W> >::check_writer" 451// 452// This method checks to see if there is more than one writer for this 453// object instance by keeping track of the process performing the write. 454//------------------------------------------------------------------------------ 455SC_TEMPLATE 456inline void sc_signal<sc_dt::sc_uint<W> >::check_writer() 457{ 458 sc_process_b* writer_p = sc_get_current_process_b(); 459 if( m_writer_p == 0 ) 460 { 461 m_writer_p = writer_p; 462 } 463 else if( m_writer_p != writer_p ) 464 { 465 sc_signal_invalid_writer( name(), kind(), 466 m_writer_p->name(), writer_p->name() ); 467 } 468} 469 470 471//------------------------------------------------------------------------------ 472//"sc_signal<sc_dt::sc_uint<W> >::concat_set" 473// 474// These virtual methods allow value assignments to this object instance 475// from various sources. The position within the supplied source of the 476// low order bit for this object instance's value is low_i. 477// src = source value. 478// low_i = bit within src to serve as low order bit of this object 479// instance's value. 480//------------------------------------------------------------------------------ 481SC_TEMPLATE 482inline void sc_signal<sc_dt::sc_uint<W> >::concat_set( 483 sc_dt::int64 src, int low_i) 484{ 485 if ( low_i < 64 ) 486 { 487 base_write(src >> low_i); 488 } 489 else 490 { 491 base_write( (src < 0 ) ? src >> 63 : 0 ); 492 } 493} 494 495SC_TEMPLATE 496inline void sc_signal<sc_dt::sc_uint<W> >::concat_set( 497 const sc_dt::sc_lv_base& src, int low_i) 498{ 499 sc_dt::sc_unsigned tmp(src.length()); 500 tmp = src >> low_i; 501 base_write( tmp.to_uint64() ); 502} 503 504SC_TEMPLATE 505inline void sc_signal<sc_dt::sc_uint<W> >::concat_set( 506 const sc_dt::sc_signed& src, int low_i) 507{ 508 base_write( (src >> low_i).to_uint64()); 509} 510 511SC_TEMPLATE 512inline void sc_signal<sc_dt::sc_uint<W> >::concat_set( 513 const sc_dt::sc_unsigned& src, int low_i) 514{ 515 base_write( (src >> low_i).to_uint64()); 516} 517 518SC_TEMPLATE 519inline void sc_signal<sc_dt::sc_uint<W> >::concat_set( 520 sc_dt::uint64 src, int low_i) 521{ 522 base_write( ( low_i < 64 ) ? src >> low_i : 0 ); 523} 524 525 526 527SC_TEMPLATE // Return the default event for this object instance. 528inline const sc_event& sc_signal<sc_dt::sc_uint<W> >::default_event() const 529 { return base_value_changed_event(); } 530 531 532SC_TEMPLATE // Return true if a changed event happened in the last delta cycle. 533inline bool sc_signal<sc_dt::sc_uint<W> >::event() const 534 { return base_event(); } 535 536 537SC_TEMPLATE // Return a reference to the value of this object instance. 538inline const sc_dt::sc_uint<W>& 539sc_signal<sc_dt::sc_uint<W> >::get_data_ref() const 540 { return *this; } 541 542 543#if 0 544SC_TEMPLATE // Return a pointer to this object instance. 545inline sc_signal<sc_dt::sc_uint<W> >& sc_signal<sc_dt::sc_uint<W> >::get_signal() 546 { return *this; } 547#endif // 0 548 549 550SC_TEMPLATE // Return a kind value of "sc_signal". 551inline const char* sc_signal<sc_dt::sc_uint<W> >::kind() const 552{ 553 return "sc_signal"; 554} 555 556 557//------------------------------------------------------------------------------ 558//"sc_signal_uint::operator () 559// 560// This operator returns a part selection of this object instance. 561// left = left-hand bit of the selection. 562// right = right-hand bit of the selection. 563//------------------------------------------------------------------------------ 564SC_TEMPLATE 565inline sc_uint_sigref& sc_signal<sc_dt::sc_uint<W> >::operator () 566 (int left, int right) 567{ 568 sc_uint_sigref* result_p; // Value to return. 569 570 result_p = sc_uint_sigref::m_pool.allocate(); 571 result_p->initialize(this, left, right); 572 return *result_p; 573} 574 575 576//------------------------------------------------------------------------------ 577//"sc_signal_uint::operator []" 578// 579// This operator returns a bit selection of this object instance. 580// i = bit to be selected. 581//------------------------------------------------------------------------------ 582SC_TEMPLATE 583inline sc_uint_sigref& sc_signal<sc_dt::sc_uint<W> >::operator [] ( int bit ) 584{ 585 return operator () (bit,bit); 586} 587 588SC_TEMPLATE 589inline void sc_signal<sc_dt::sc_uint<W> >::operator = ( 590 const this_type& new_val ) 591 { base_write( (sc_dt::uint64)new_val ); } 592 593SC_TEMPLATE 594inline void sc_signal<sc_dt::sc_uint<W> >::operator = ( sc_dt::uint64 new_val ) 595 { base_write(new_val); } 596 597 598SC_TEMPLATE 599inline void sc_signal<sc_dt::sc_uint<W> >::operator = ( const char* new_val ) 600 { m_new_val = sc_dt::sc_uint<64>(new_val); request_update(); } 601 602 603SC_TEMPLATE 604inline void sc_signal<sc_dt::sc_uint<W> >::operator = ( sc_dt::int64 new_val ) 605 { base_write((sc_dt::uint64)new_val); } 606 607 608SC_TEMPLATE 609inline void sc_signal<sc_dt::sc_uint<W> >::operator = ( int new_val ) 610 { base_write((sc_dt::uint64)new_val); } 611 612 613SC_TEMPLATE 614inline void sc_signal<sc_dt::sc_uint<W> >::operator = ( long new_val ) 615 { base_write((sc_dt::uint64)new_val); } 616 617 618SC_TEMPLATE 619inline void sc_signal<sc_dt::sc_uint<W> >::operator = ( short new_val ) 620 { base_write((sc_dt::uint64)new_val); } 621 622 623SC_TEMPLATE 624inline void sc_signal<sc_dt::sc_uint<W> >::operator = ( unsigned int new_val ) 625 { base_write((sc_dt::uint64)new_val); } 626 627 628SC_TEMPLATE 629inline void sc_signal<sc_dt::sc_uint<W> >::operator = ( unsigned long new_val ) 630 { base_write((sc_dt::uint64)new_val); } 631 632 633SC_TEMPLATE 634inline void sc_signal<sc_dt::sc_uint<W> >::operator = ( unsigned short new_val ) 635 { base_write((sc_dt::uint64)new_val); } 636 637 638SC_TEMPLATE 639template<typename T> 640inline void sc_signal<sc_dt::sc_uint<W> >::operator = ( 641 const sc_dt::sc_generic_base<T>& new_val ) 642 { base_write(new_val->to_uint64()); } 643 644 645SC_TEMPLATE 646inline void sc_signal<sc_dt::sc_uint<W> >::operator = ( 647 const sc_dt::sc_signed& new_val ) 648 { base_write(new_val.to_uint64()); } 649 650 651SC_TEMPLATE 652inline void sc_signal<sc_dt::sc_uint<W> >::operator = ( 653 const sc_dt::sc_unsigned& new_val ) 654 { base_write(new_val.to_uint64()); } 655 656SC_TEMPLATE 657inline void sc_signal<sc_dt::sc_uint<W> >::operator = ( 658 const sc_dt::sc_bv_base& new_val ) 659 { base_write( (sc_dt::sc_uint<W>)new_val ); } 660 661SC_TEMPLATE 662inline void sc_signal<sc_dt::sc_uint<W> >::operator = ( 663 const sc_dt::sc_lv_base& new_val ) 664 { base_write( (sc_dt::sc_uint<W>)new_val ); } 665 666 667SC_TEMPLATE 668inline sc_dt::sc_uint_base* sc_signal<sc_dt::sc_uint<W> >::part_read_target() 669 { return this; } 670 671 672SC_TEMPLATE 673inline const sc_dt::sc_uint<W>& sc_signal<sc_dt::sc_uint<W> >::read() const 674 { return *this; } 675 676 677SC_TEMPLATE // Read a portion of a value. 678inline sc_dt::uint64 sc_signal<sc_dt::sc_uint<W> >::read_part( int left, int right ) const 679{ 680 // This pointer required for HP aCC. 681 return (this->m_val & ~sc_dt::mask_int[left][right]) >> right; 682} 683 684SC_TEMPLATE 685inline void sc_signal<sc_dt::sc_uint<W> >::register_port( 686 sc_port_base& port_, const char* if_typename_ ) 687{ 688# ifdef DEBUG_SYSTEMC 689 std::string nm( if_typename_ ); 690 if( nm == typeid( sc_signal_inout_if<sc_dt::sc_uint<W> > ).name() ) 691 { 692 if( m_output_p != 0 ) 693 { 694 sc_signal_invalid_writer( name(), kind(), 695 m_output_p->name(), port_.name() ); 696 } 697 m_output_p = &port_; 698 } 699# else 700 if ( &port_ && if_typename_ ) {} // Silence unused args warning. 701# endif 702} 703 704 705SC_TEMPLATE // Autogenerated name object instance constructor. 706inline sc_signal<sc_dt::sc_uint<W> >::sc_signal() : 707 sc_prim_channel(sc_gen_unique_name( "signal" )), 708 m_changed_event_p(0), 709 m_output_p(0), 710 m_writer_p(0) 711{ } 712 713 714SC_TEMPLATE // Explicitly named object instance constructor. 715inline sc_signal<sc_dt::sc_uint<W> >::sc_signal(const char* name_) : 716 sc_prim_channel(name_), 717 m_changed_event_p(0), 718 m_output_p(0), 719 m_writer_p(0) 720{ } 721 722 723SC_TEMPLATE // Object instance destructor. 724inline sc_signal<sc_dt::sc_uint<W> >::~sc_signal() 725{ 726 if ( m_changed_event_p ) delete m_changed_event_p; 727} 728 729 730SC_TEMPLATE // Update the current value from new value. 731inline void sc_signal<sc_dt::sc_uint<W> >::update() 732{ 733 if ( m_changed_event_p ) 734 { 735 // This pointer required for HP aCC. 736 sc_dt::uint64 old_val = this->m_val; 737 sc_dt::sc_uint_base::operator = (m_new_val); 738 if ( old_val != this->m_val ) 739 { 740 m_changed_event_p->notify_delayed(); 741 m_event_delta = simcontext()->delta_count(); 742 } 743 } 744 else 745 { 746 sc_dt::sc_uint_base::operator = (m_new_val); 747 } 748} 749 750 751SC_TEMPLATE // Return the value changed event. 752inline const sc_event& sc_signal<sc_dt::sc_uint<W> >::value_changed_event() const 753 { return base_value_changed_event(); } 754 755 756SC_TEMPLATE // Write a sc_in<sc_dt::sc_uint<W> > value to this object instance. 757inline void sc_signal<sc_dt::sc_uint<W> >::write( const sc_in<sc_dt::sc_uint<W> >& value ) 758 { base_write( value.operator sc_dt::uint64 () ); } 759 760 761SC_TEMPLATE // Write a sc_inout<sc_dt::sc_uint<W> > value to this object instance. 762inline void sc_signal<sc_dt::sc_uint<W> >::write( const sc_inout<sc_dt::sc_uint<W> >& value ) 763 { base_write( value.operator sc_dt::uint64 () ); } 764 765 766SC_TEMPLATE // Write a sc_dt::sc_uint<W> value to this object instance. 767inline void sc_signal<sc_dt::sc_uint<W> >::write( 768 const sc_dt::sc_uint<W>& value ) 769 { base_write( value); } 770 771 772SC_TEMPLATE // Select a portion of a value. 773inline sc_uint_sigref& sc_signal<sc_dt::sc_uint<W> >::select_part(int left, int right) 774{ 775 sc_uint_sigref* result_p = sc_uint_sigref::m_pool.allocate(); 776 result_p->initialize(this, left, right); 777 return *result_p; 778} 779 780 781SC_TEMPLATE // Write a portion of a value. If this is the first write in 782 // a delta cycle we copy the existing value before setting the bits. 783inline void sc_signal<sc_dt::sc_uint<W> >::write_part( sc_dt::uint64 v, int left, int right ) 784{ 785 sc_dt::uint64 new_v; // New value. 786 sc_dt::uint64 keep; // Keep mask value. 787 788 keep = sc_dt::mask_int[left][right]; 789 new_v = (m_new_val & keep) | ((v << right) & ~keep); 790 m_new_val = new_v; 791 request_update(); 792} 793 794 795//============================================================================== 796// CLASS sc_in<sc_dt::sc_uint<W> > 797// 798// This class implements an input port whose target acts like an sc_dt::sc_uint<W> data 799// value. This class is a specialization of the generic sc_in class to 800// implement tailored support for the sc_dt::sc_uint<W> class. 801//============================================================================== 802SC_TEMPLATE 803class sc_in<sc_dt::sc_uint<W> > : 804 public sc_port<sc_signal_in_if<sc_dt::sc_uint<W> >, 1, 805 SC_ONE_OR_MORE_BOUND>, 806 public sc_dt::sc_value_base 807{ 808 public: 809 810 // typedefs 811 812 typedef sc_dt::sc_uint<W> data_type; 813 typedef sc_signal_in_if<sc_dt::sc_uint<W> > if_type; 814 typedef sc_port<if_type,1,SC_ONE_OR_MORE_BOUND> base_type; 815 typedef sc_in<sc_dt::sc_uint<W> > this_type; 816 817 typedef if_type in_if_type; 818 typedef base_type in_port_type; 819 typedef sc_signal_inout_if<sc_dt::sc_uint<W> > inout_if_type; 820 typedef sc_inout<sc_dt::sc_uint<W> > inout_port_type; 821 822 public: 823 824 // bind methods and operators: 825 826 void bind( const in_if_type& interface_ ) 827 { sc_port_base::bind( const_cast<in_if_type&>( interface_) );} 828 void operator () ( const in_if_type& interface_ ) 829 { sc_port_base::bind( const_cast<in_if_type&>( interface_) );} 830 void bind( in_port_type& parent_ ) 831 { sc_port_base::bind(parent_);} 832 void operator () ( in_port_type& parent_ ) 833 { sc_port_base::bind(parent_);} 834 void bind( inout_port_type& parent_ ) 835 { sc_port_base::bind(parent_);} 836 void operator () ( inout_port_type& parent_ ) 837 { sc_port_base::bind(parent_);} 838 839 protected: 840 // called by pbind (for internal use only) 841 virtual inline int vbind( sc_interface& interface_ ) 842 { 843 return sc_port_b<if_type>::vbind( interface_ ); 844 } 845 virtual inline int vbind( sc_port_base& parent_ ) 846 { 847 in_port_type* in_parent = dynamic_cast<in_port_type*>( &parent_ ); 848 if( in_parent != 0 ) { 849 sc_port_base::bind( *in_parent ); 850 return 0; 851 } 852 inout_port_type* inout_parent = dynamic_cast<inout_port_type*>( &parent_ ); 853 if( inout_parent != 0 ) { 854 sc_port_base::bind( *inout_parent ); 855 return 0; 856 } 857 // type mismatch 858 return 2; 859 } 860 861 862 // constructors 863 864 public: 865 sc_in() 866 : base_type(), m_traces( 0 ) 867 {} 868 869 explicit sc_in( const char* name_ ) 870 : base_type( name_ ), m_traces( 0 ) 871 {} 872 873 explicit sc_in( const in_if_type& interface_ ) 874 : base_type( const_cast<in_if_type&>( interface_ ) ), m_traces( 0 ) 875 {} 876 877 sc_in( const char* name_, const in_if_type& interface_ ) 878 : base_type( name_, const_cast<in_if_type&>( interface_ ) ), m_traces( 0 ) 879 {} 880 881 explicit sc_in( in_port_type& parent_ ) 882 : base_type( parent_ ), m_traces( 0 ) 883 {} 884 885 sc_in( const char* name_, in_port_type& parent_ ) 886 : base_type( name_, parent_ ), m_traces( 0 ) 887 {} 888 889 explicit sc_in( inout_port_type& parent_ ) 890 : base_type(), m_traces( 0 ) 891 { sc_port_base::bind( parent_ ); } 892 893 sc_in( const char* name_, inout_port_type& parent_ ) 894 : base_type( name_ ), m_traces( 0 ) 895 { sc_port_base::bind( parent_ ); } 896 897 sc_in( this_type& parent_ ) 898 : base_type( parent_ ), m_traces( 0 ) 899 {} 900 901 sc_in( const char* name_, this_type& parent_ ) 902 : base_type( name_, parent_ ), m_traces( 0 ) 903 {} 904 905 906 // destructor 907 908 virtual inline ~sc_in() 909 { 910 remove_traces(); 911 } 912 913 // bit and part selection 914 915 sc_dt::sc_uint_bitref_r operator [] ( int i ) const 916 { return (*this)->read()[i]; } 917 sc_dt::sc_uint_bitref_r bit( int i ) const 918 { return (*this)->read()[i]; } 919 sc_dt::sc_uint_subref_r operator () ( int left, int right ) const 920 { return (*this)->read()(left,right); } 921 sc_dt::sc_uint_subref_r range( int left, int right ) const 922 { return (*this)->read()(left,right); } 923 924 925 // interface access shortcut methods 926 927 // get the default event 928 929 const sc_event& default_event() const 930 { return (*this)->value_changed_event(); } 931 932 933 // get the value changed event 934 935 const sc_event& value_changed_event() const 936 { return (*this)->value_changed_event(); } 937 938 939 // read the current value 940 941 const sc_dt::sc_uint<W>& read() const 942 { return (*this)->read(); } 943 944 operator sc_dt::uint64 () const 945 { return (sc_dt::uint64)(*this)->read(); } 946 947 // was there a value changed event? 948 949 bool event() const 950 { return (*this)->event(); } 951 952 953 // (other) event finder method(s) 954 955 sc_event_finder& value_changed() const 956 { 957 return *new sc_event_finder_t<in_if_type>( 958 *this, &in_if_type::value_changed_event ); 959 } 960 961 962 963 // reduction methods: 964 965 inline bool and_reduce() const 966 { return (*this)->read().and_reduce(); } 967 inline bool nand_reduce() const 968 { return (*this)->read().nand_reduce(); } 969 inline bool nor_reduce() const 970 { return (*this)->read().nor_reduce(); } 971 inline bool or_reduce() const 972 { return (*this)->read().or_reduce(); } 973 inline bool xnor_reduce() const 974 { return (*this)->read().xnor_reduce(); } 975 inline bool xor_reduce() const 976 { return (*this)->read().xor_reduce(); } 977 978 979 // called when elaboration is done 980 /* WHEN DEFINING THIS METHOD IN A DERIVED CLASS, */ 981 /* MAKE SURE THAT THIS METHOD IS CALLED AS WELL. */ 982 983 virtual inline void end_of_elaboration() 984 { 985 if( m_traces != 0 ) { 986 for( unsigned int i = 0; i < m_traces->size(); ++ i ) { 987 sc_trace_params* p = (*m_traces)[i]; 988 sc_trace( p->tf, read(), p->name ); 989 } 990 remove_traces(); 991 } 992 } 993 994 virtual inline const char* kind() const 995 { return "sc_in"; } 996 997 998 // called by sc_trace 999 void add_trace( sc_trace_file* tf_, const std::string& name_ ) const 1000 { 1001 if( tf_ != 0 ) { 1002 if( m_traces == 0 ) { 1003 m_traces = new sc_trace_params_vec; 1004 } 1005 m_traces->push_back( new sc_trace_params( tf_, name_ ) ); 1006 } 1007 } 1008 1009 1010 // concatenation methods 1011 1012 virtual inline int concat_length(bool* xz_present_p) const 1013 { return (*this)->read().concat_length( xz_present_p ); } 1014 virtual inline sc_dt::uint64 concat_get_uint64() const 1015 { return (*this)->read().concat_get_uint64(); } 1016 virtual inline bool concat_get_ctrl( 1017 sc_dt::sc_digit* dst_p, int low_i ) const 1018 { return (*this)->read().concat_get_ctrl(dst_p, low_i); } 1019 virtual inline bool concat_get_data( 1020 sc_dt::sc_digit* dst_p, int low_i ) const 1021 { return (*this)->read().concat_get_data(dst_p, low_i); } 1022 1023 protected: 1024 void remove_traces() const 1025 { 1026 if( m_traces != 0 ) { 1027 for( int i = m_traces->size() - 1; i >= 0; -- i ) { 1028 delete (*m_traces)[i]; 1029 } 1030 delete m_traces; 1031 m_traces = 0; 1032 } 1033 } 1034 1035 mutable sc_trace_params_vec* m_traces; 1036 1037 1038 private: 1039 1040 // disabled 1041 sc_in( const sc_in<sc_dt::sc_uint<W> >& ); 1042 sc_in<sc_dt::sc_uint<W> >& operator = ( const sc_in<sc_dt::sc_uint<W> >& ); 1043 1044#ifdef __GNUC__ 1045 // Needed to circumvent a problem in the g++-2.95.2 compiler: 1046 // This unused variable forces the compiler to instantiate 1047 // an object of T template so an implicit conversion from 1048 // read() to a C++ intrinsic data type will work. 1049 static data_type dummy; 1050#endif 1051 1052}; 1053 1054 1055 1056SC_TEMPLATE 1057inline std::ostream& operator << ( 1058 std::ostream& os, const sc_in<sc_dt::sc_uint<W> >& a ) 1059{ 1060 a.read().print( os ); 1061 return os; 1062} 1063 1064 1065//============================================================================== 1066// CLASS sc_inout<sc_dt::sc_uint<W> > 1067// 1068// This class implements an input/output port whose target acts like an 1069// sc_dt::sc_uint<W> data value. It is derived from the sc_uint_in. This class is a 1070// specialization of the generic sc_inout class to implement tailored support 1071// for the sc_dt::sc_uint<W> class. 1072//============================================================================== 1073SC_TEMPLATE 1074class sc_inout<sc_dt::sc_uint<W> > : 1075 public sc_port<sc_signal_inout_if<sc_dt::sc_uint<W> >, 1, 1076 SC_ONE_OR_MORE_BOUND>, 1077 public sc_dt::sc_value_base 1078{ 1079 public: 1080 1081 // typedefs 1082 1083 typedef sc_dt::sc_uint<W> data_type; 1084 typedef sc_signal_inout_if<sc_dt::sc_uint<W> > if_type; 1085 typedef sc_port<if_type,1,SC_ONE_OR_MORE_BOUND> base_type; 1086 typedef sc_inout<sc_dt::sc_uint<W> > this_type; 1087 1088 typedef if_type inout_if_type; 1089 typedef base_type inout_port_type; 1090 1091 public: 1092 1093 // bind methods and operators: 1094 1095 void bind( const inout_if_type& interface_ ) 1096 { sc_port_base::bind( const_cast<inout_if_type&>( interface_) ); } 1097 void operator () ( const inout_if_type& interface_ ) 1098 { sc_port_base::bind( const_cast<inout_if_type&>( interface_) ); } 1099 void bind( inout_port_type& parent_ ) 1100 { sc_port_base::bind(parent_); } 1101 void operator () ( inout_port_type& parent_ ) 1102 { sc_port_base::bind(parent_); } 1103 1104 protected: 1105 // called by pbind (for internal use only) 1106 virtual inline int vbind( sc_interface& interface_ ) 1107 { 1108 return sc_port_b<if_type>::vbind( interface_ ); 1109 } 1110 virtual inline int vbind( sc_port_base& parent_ ) 1111 { 1112 inout_port_type* inout_parent = dynamic_cast<inout_port_type*>( &parent_ ); 1113 if( inout_parent != 0 ) { 1114 sc_port_base::bind( *inout_parent ); 1115 return 0; 1116 } 1117 // type mismatch 1118 return 2; 1119 } 1120 1121 1122 // constructors 1123 1124 public: 1125 sc_inout() 1126 : base_type(), m_init_val_p(0), m_traces( 0 ) 1127 {} 1128 1129 explicit sc_inout( const char* name_ ) 1130 : base_type( name_ ), m_init_val_p(0), m_traces( 0 ) 1131 {} 1132 1133 explicit sc_inout( inout_if_type& interface_ ) 1134 : base_type( interface_ ), m_init_val_p(0), m_traces( 0 ) 1135 {} 1136 1137 sc_inout( const char* name_, inout_if_type& interface_ ) 1138 : base_type( name_, interface_ ), m_init_val_p(0), m_traces( 0 ) 1139 {} 1140 1141 explicit sc_inout( inout_port_type& parent_ ) 1142 : base_type( parent_ ), m_init_val_p(0), m_traces( 0 ) 1143 {} 1144 1145 sc_inout( const char* name_, inout_port_type& parent_ ) 1146 : base_type( name_, parent_ ), m_init_val_p(0), m_traces( 0 ) 1147 {} 1148 1149 sc_inout( this_type& parent_ ) 1150 : base_type( parent_ ), m_init_val_p(0), m_traces( 0 ) 1151 {} 1152 1153 sc_inout( const char* name_, this_type& parent_ ) 1154 : base_type( name_, parent_ ), m_init_val_p(0), m_traces( 0 ) 1155 {} 1156 1157 1158 // destructor 1159 1160 virtual inline ~sc_inout() 1161 { 1162 remove_traces(); 1163 } 1164 1165 // bit and part selection 1166 1167 sc_dt::sc_uint_bitref_r operator [] ( int i ) const 1168 { return (*this)->read()[i]; } 1169 sc_dt::sc_uint_bitref_r bit( int i ) const 1170 { return (*this)->read()[i]; } 1171 sc_uint_sigref& operator [] ( int i ) 1172 { return (*this)->select_part(i,i); } 1173 sc_uint_sigref& bit( int i ) 1174 { return (*this)->select_part(i,i); } 1175 sc_dt::sc_uint_subref_r operator () ( int left, int right ) const 1176 { return (*this)->read()(left,right); } 1177 sc_dt::sc_uint_subref_r range( int left, int right ) const 1178 { return (*this)->read()(left,right); } 1179 sc_uint_sigref& operator () ( int left, int right ) 1180 { return (*this)->select_part(left,right); } 1181 sc_uint_sigref& range( int left, int right ) 1182 { return (*this)->select_part(left,right); } 1183 1184 1185 // interface access shortcut methods 1186 1187 // get the default event 1188 1189 const sc_event& default_event() const 1190 { return (*this)->value_changed_event(); } 1191 1192 1193 // get the value changed event 1194 1195 const sc_event& value_changed_event() const 1196 { return (*this)->value_changed_event(); } 1197 1198 1199 // read the current value 1200 1201 const sc_dt::sc_uint<W>& read() const 1202 { return (*this)->read(); } 1203 1204 operator sc_dt::uint64 () const 1205 { return (sc_dt::uint64)(*this)->read(); } 1206 1207 // was there a value changed event? 1208 1209 bool event() const 1210 { return (*this)->event(); } 1211 1212 1213 // (other) event finder method(s) 1214 1215 sc_event_finder& value_changed() const 1216 { 1217 return *new sc_event_finder_t<inout_if_type>( 1218 *this, &inout_if_type::value_changed_event ); 1219 } 1220 1221 1222 1223 // reduction methods: 1224 1225 inline bool and_reduce() const 1226 { return (*this)->read().and_reduce(); } 1227 inline bool nand_reduce() const 1228 { return (*this)->read().nand_reduce(); } 1229 inline bool nor_reduce() const 1230 { return (*this)->read().nor_reduce(); } 1231 inline bool or_reduce() const 1232 { return (*this)->read().or_reduce(); } 1233 inline bool xnor_reduce() const 1234 { return (*this)->read().xnor_reduce(); } 1235 inline bool xor_reduce() const 1236 { return (*this)->read().xor_reduce(); } 1237 1238 1239 // called when elaboration is done 1240 /* WHEN DEFINING THIS METHOD IN A DERIVED CLASS, */ 1241 /* MAKE SURE THAT THIS METHOD IS CALLED AS WELL. */ 1242 1243 virtual inline void end_of_elaboration() 1244 { 1245 if( m_init_val_p != 0 ) { 1246 (*this)->write( (sc_dt::uint64) *m_init_val_p ); 1247 delete m_init_val_p; 1248 m_init_val_p = 0; 1249 } 1250 if( m_traces != 0 ) { 1251 for( unsigned int i = 0; i < m_traces->size(); ++ i ) { 1252 sc_trace_params* p = (*m_traces)[i]; 1253 sc_trace( p->tf, read(), p->name ); 1254 } 1255 remove_traces(); 1256 } 1257 } 1258 1259 virtual inline const char* kind() const 1260 { return "sc_inout"; } 1261 1262 // value initialization 1263 1264 inline void initialize( const sc_dt::sc_uint<W>& value_ ) 1265 { 1266 inout_if_type* iface = this->get_interface(0); 1267 if( iface != 0 ) { 1268 iface->write( value_ ); 1269 } else { 1270 if( m_init_val_p == 0 ) { 1271 m_init_val_p = new sc_dt::uint64; 1272 } 1273 *m_init_val_p = value_; 1274 } 1275 } 1276 1277 1278 // called by sc_trace 1279 void add_trace( sc_trace_file* tf_, const std::string& name_ ) const 1280 { 1281 if( tf_ != 0 ) { 1282 if( m_traces == 0 ) { 1283 m_traces = new sc_trace_params_vec; 1284 } 1285 m_traces->push_back( new sc_trace_params( tf_, name_ ) ); 1286 } 1287 } 1288 1289 1290 // concatenation methods 1291 1292 virtual inline int concat_length(bool* xz_present_p) const 1293 { return (*this)->read().concat_length( xz_present_p ); } 1294 virtual inline sc_dt::uint64 concat_get_uint64() const 1295 { return (*this)->read().concat_get_uint64(); } 1296 virtual inline bool concat_get_ctrl( 1297 sc_dt::sc_digit* dst_p, int low_i ) const 1298 { return (*this)->read().concat_get_ctrl(dst_p, low_i); } 1299 virtual inline bool concat_get_data( 1300 sc_dt::sc_digit* dst_p, int low_i ) const 1301 { return (*this)->read().concat_get_data(dst_p, low_i); } 1302 virtual inline void concat_set(sc_dt::int64 src, int low_i) 1303 { *this = (src >> ((low_i < 64) ? low_i : 63)); } 1304#if 0 1305 virtual inline void concat_set(const sc_dt::sc_lv_base& src, int low_i) 1306 { if (low_i < 64) *this = src >> low_i; else *this = 0; } 1307#endif // 0 #### 1308 virtual inline void concat_set(const sc_dt::sc_signed& src, int low_i) 1309 { *this = (src >> low_i); } 1310 virtual inline void concat_set(const sc_dt::sc_unsigned& src, int low_i) 1311 { *this = (src >> low_i); } 1312 virtual inline void concat_set(sc_dt::uint64 src, int low_i) 1313 { *this = (low_i < 64) ? src >> low_i : (sc_dt::uint64)0; } 1314 1315 // assignment operators: 1316 1317 public: 1318 inline void operator = ( const this_type& new_val ) 1319 { (*this)->write( (sc_dt::uint64)new_val ); } 1320 inline void operator = ( const char* new_val ) 1321 { (*this)->write( this_type(new_val) ); } 1322 inline void operator = ( sc_dt::uint64 new_val ) 1323 { (*this)->write(new_val); } 1324 inline void operator = ( sc_dt::int64 new_val ) 1325 { (*this)->write((sc_dt::uint64)new_val); } 1326 inline void operator = ( int new_val ) 1327 { (*this)->write((sc_dt::uint64)new_val); } 1328 inline void operator = ( long new_val ) 1329 { (*this)->write((sc_dt::uint64)new_val); } 1330 inline void operator = ( short new_val ) 1331 { (*this)->write((sc_dt::uint64)new_val); } 1332 inline void operator = ( unsigned int new_val ) 1333 { (*this)->write((sc_dt::uint64)new_val); } 1334 inline void operator = ( unsigned long new_val ) 1335 { (*this)->write((sc_dt::uint64)new_val); } 1336 inline void operator = ( unsigned short new_val ) 1337 { (*this)->write((sc_dt::uint64)new_val); } 1338 template<typename T> 1339 inline void operator = ( const sc_dt::sc_generic_base<T>& new_val ) 1340 { (*this)->write(new_val->to_uint64()); } 1341 inline void operator = ( const sc_dt::sc_signed& new_val ) 1342 { (*this)->write(new_val.to_uint64()); } 1343 inline void operator = ( const sc_dt::sc_unsigned& new_val ) 1344 { (*this)->write(new_val.to_uint64()); } 1345 inline void operator = ( const sc_dt::sc_bv_base& new_val ) 1346 { (*this)->write((sc_dt::sc_uint<W>)new_val); } 1347 inline void operator = ( const sc_dt::sc_lv_base& new_val ) 1348 { (*this)->write((sc_dt::sc_uint<W>)new_val); } 1349 1350 inline void write( const sc_in<sc_dt::sc_uint<W> >& new_val ) 1351 { (*this)->write( (sc_dt::uint64)new_val ); } 1352 inline void write( const sc_inout<sc_dt::sc_uint<W> >& new_val ) 1353 { (*this)->write( (sc_dt::uint64)new_val); } 1354 inline void write( const sc_dt::sc_uint<W>& new_val ) 1355 { (*this)->write( (sc_dt::uint64)new_val); } 1356 1357 protected: 1358 void remove_traces() const 1359 { 1360 if( m_traces != 0 ) { 1361 for( int i = m_traces->size() - 1; i >= 0; -- i ) { 1362 delete (*m_traces)[i]; 1363 } 1364 delete m_traces; 1365 m_traces = 0; 1366 } 1367 } 1368 1369 sc_dt::uint64* m_init_val_p; 1370 mutable sc_trace_params_vec* m_traces; 1371 1372 1373 private: 1374 1375 // disabled 1376 sc_inout( const sc_inout<sc_dt::sc_uint<W> >& ); 1377 1378#ifdef __GNUC__ 1379 // Needed to circumvent a problem in the g++-2.95.2 compiler: 1380 // This unused variable forces the compiler to instantiate 1381 // an object of T template so an implicit conversion from 1382 // read() to a C++ intrinsic data type will work. 1383 static data_type dummy; 1384#endif 1385 1386}; 1387 1388 1389 1390SC_TEMPLATE 1391inline std::ostream& operator << ( 1392 std::ostream& os, const sc_inout<sc_dt::sc_uint<W> >& a ) 1393{ 1394 a.read().print( os ); 1395 return os; 1396} 1397 1398 1399//============================================================================== 1400// CLASS sc_out<sc_dt::sc_uint<W> > 1401// 1402// This class implements an output port whose target acts like an 1403// sc_dt::sc_uint<W> data value. This class is a derivation of sc_inout, since 1404// output ports are really no different from input/output ports. 1405//============================================================================== 1406SC_TEMPLATE 1407class sc_out<sc_dt::sc_uint<W> > : public sc_inout<sc_dt::sc_uint<W> > 1408{ 1409 public: 1410 1411 // typedefs 1412 1413 typedef sc_dt::sc_uint<W> data_type; 1414 1415 typedef sc_out<data_type> this_type; 1416 typedef sc_inout<data_type> base_type; 1417 1418 typedef typename base_type::inout_if_type inout_if_type; 1419 typedef typename base_type::inout_port_type inout_port_type; 1420 1421 // constructors 1422 1423 sc_out() 1424 : base_type() 1425 {} 1426 1427 explicit sc_out( const char* name_ ) 1428 : base_type( name_ ) 1429 {} 1430 1431 explicit sc_out( inout_if_type& interface_ ) 1432 : base_type( interface_ ) 1433 {} 1434 1435 sc_out( const char* name_, inout_if_type& interface_ ) 1436 : base_type( name_, interface_ ) 1437 {} 1438 1439 explicit sc_out( inout_port_type& parent_ ) 1440 : base_type( parent_ ) 1441 {} 1442 1443 sc_out( const char* name_, inout_port_type& parent_ ) 1444 : base_type( name_, parent_ ) 1445 {} 1446 1447 sc_out( this_type& parent_ ) 1448 : base_type( parent_ ) 1449 {} 1450 1451 sc_out( const char* name_, this_type& parent_ ) 1452 : base_type( name_, parent_ ) 1453 {} 1454 1455 1456 // destructor (does nothing) 1457 1458 virtual inline ~sc_out() 1459 {} 1460 1461 1462 // assignment operators: 1463 1464 public: 1465 inline void operator = ( const this_type& new_val ) 1466 { (*this)->write( (sc_dt::uint64)new_val ); } 1467 inline void operator = ( const char* new_val ) 1468 { (*this)->write( this_type(new_val) ); } 1469 inline void operator = ( sc_dt::uint64 new_val ) 1470 { (*this)->write(new_val); } 1471 inline void operator = ( sc_dt::int64 new_val ) 1472 { (*this)->write((sc_dt::uint64)new_val); } 1473 inline void operator = ( int new_val ) 1474 { (*this)->write((sc_dt::uint64)new_val); } 1475 inline void operator = ( long new_val ) 1476 { (*this)->write((sc_dt::uint64)new_val); } 1477 inline void operator = ( short new_val ) 1478 { (*this)->write((sc_dt::uint64)new_val); } 1479 inline void operator = ( unsigned int new_val ) 1480 { (*this)->write((sc_dt::uint64)new_val); } 1481 inline void operator = ( unsigned long new_val ) 1482 { (*this)->write((sc_dt::uint64)new_val); } 1483 inline void operator = ( unsigned short new_val ) 1484 { (*this)->write((sc_dt::uint64)new_val); } 1485 template<typename T> 1486 inline void operator = ( const sc_dt::sc_generic_base<T>& new_val ) 1487 { (*this)->write(new_val->to_uint64()); } 1488 inline void operator = ( const sc_dt::sc_signed& new_val ) 1489 { (*this)->write(new_val); } 1490 inline void operator = ( const sc_dt::sc_unsigned& new_val ) 1491 { (*this)->write(new_val); } 1492 inline void operator = ( const sc_dt::sc_bv_base& new_val ) 1493 { (*this)->write((sc_dt::sc_uint<W>)new_val); } 1494 inline void operator = ( const sc_dt::sc_lv_base& new_val ) 1495 { (*this)->write((sc_dt::sc_uint<W>)new_val); } 1496 1497 private: 1498 1499 // disabled 1500 sc_out( const this_type& ); 1501}; 1502 1503 1504 1505//------------------------------------------------------------------------------ 1506//"sc_uint_sigref::initialize" 1507// 1508// This method initializes an object instance from the supplied arguments. 1509// if_p -> interface for signal to perform writes for this object. 1510// left = left-most bit in selection. 1511// right = right-most bit in selection. 1512//------------------------------------------------------------------------------ 1513inline 1514void sc_uint_sigref::initialize(sc_uint_part_if* if_p, int left, int right) 1515{ 1516 m_left = left; 1517 m_right = right; 1518 m_if_p = if_p; 1519 m_obj_p = if_p->part_read_target(); 1520} 1521 1522 1523//------------------------------------------------------------------------------ 1524//"sc_uint_sigref::operator =" 1525// 1526// These operators assign a value to the bits associated with this object 1527// instance within this object instance's target signal. 1528//------------------------------------------------------------------------------ 1529inline void sc_uint_sigref::operator = ( sc_dt::uint64 v ) 1530{ 1531 m_if_p->write_part( v, m_left, m_right ); 1532} 1533 1534inline void sc_uint_sigref::operator = ( const char* /*v*/ ) 1535{ 1536} 1537 1538inline void sc_uint_sigref:: operator = ( sc_dt::int64 v ) 1539{ 1540 *this = (sc_dt::uint64)v; 1541} 1542 1543inline void sc_uint_sigref:: operator = ( int v ) 1544{ 1545 *this = (sc_dt::uint64)v; 1546} 1547 1548inline void sc_uint_sigref:: operator = ( long v ) 1549{ 1550 *this = (sc_dt::uint64)v; 1551} 1552 1553inline void sc_uint_sigref:: operator = ( unsigned int v ) 1554{ 1555 *this = (sc_dt::uint64)v; 1556} 1557 1558inline void sc_uint_sigref:: operator = ( unsigned long v ) 1559{ 1560 *this = (sc_dt::uint64)v; 1561} 1562 1563void sc_uint_sigref::operator = ( const sc_uint_sigref& v ) 1564{ 1565 *this = (sc_dt::uint64)v; 1566} 1567 1568template<typename T> 1569inline void sc_uint_sigref:: operator = ( const sc_dt::sc_generic_base<T>& v ) 1570{ 1571 *this = v->to_uint64(); 1572} 1573 1574inline void sc_uint_sigref:: operator = ( const sc_dt::sc_signed& v ) 1575{ 1576 *this = v.to_uint64(); 1577} 1578 1579inline void sc_uint_sigref:: operator = ( const sc_dt::sc_unsigned& v ) 1580{ 1581 *this = v.to_uint64(); 1582} 1583 1584#undef SC_TEMPLATE 1585} // namespace sc_core 1586#endif // !defined(SC_SIGNAL_UINT_H) 1587 1588namespace sc_core { 1589 1590//------------------------------------------------------------------------------ 1591// POOL OF TEMPORARY INSTANCES OF sc_uint_sigref 1592// 1593// This allows use to pass const references for part and bit selections 1594// on sc_signal<sc_dt::sc_uint<W> > object instances. 1595//------------------------------------------------------------------------------ 1596sc_vpool<sc_uint_sigref> sc_uint_sigref::m_pool(8); 1597 1598 1599//------------------------------------------------------------------------------ 1600//"sc_uint_part_if::default methods" 1601// 1602// These versions just produce errors if they are not overloaded but used. 1603//------------------------------------------------------------------------------ 1604 1605sc_dt::sc_uint_base* sc_uint_part_if::part_read_target() 1606{ 1607 SC_REPORT_ERROR( "attempted specalized signal operation on " 1608 "non-specialized signal", "int" ); 1609 return 0; 1610} 1611sc_dt::uint64 sc_uint_part_if::read_part( int /*left*/, int /*right*/ ) const 1612{ 1613 SC_REPORT_ERROR( "attempted specalized signal operation on " 1614 "non-specialized signal", "int" ); 1615 return 0; 1616} 1617sc_uint_sigref& sc_uint_part_if::select_part( int /*left*/, int /*right*/ ) 1618{ 1619 SC_REPORT_ERROR( "attempted specalized signal operation on " 1620 "non-specialized signal", "int" ); 1621 return *(sc_uint_sigref*)0; 1622} 1623void sc_uint_part_if::write_part( sc_dt::uint64 v, int /*left*/, int /*right*/ ) 1624{ 1625 SC_REPORT_ERROR( "attempted specalized signal operation on " 1626 "non-specialized signal", "int" ); 1627} 1628 1629//------------------------------------------------------------------------------ 1630//"sc_uint_sigref::concate_set" 1631// 1632// These methods assign this object instance's value from the supplied 1633// value starting at the supplied bit within that value. 1634// src = value to use to set this object instance's value. 1635// low_i = bit in src that is to be the low order bit of the value to set. 1636// #### OPTIMIZE 1637//------------------------------------------------------------------------------ 1638void sc_uint_sigref::concat_set(sc_dt::int64 src, int low_i) 1639{ 1640 *this = (low_i < 64) ? src >> low_i : src >> 63; 1641} 1642 1643 1644void sc_uint_sigref::concat_set(const sc_dt::sc_signed& src, int low_i) 1645{ 1646 if ( low_i < src.length() ) 1647 *this = src >> low_i; 1648 else 1649 *this = (src < 0) ? (sc_dt::uint64)-1 : 0; 1650} 1651 1652 1653void sc_uint_sigref::concat_set(const sc_dt::sc_lv_base& src, int low_i) 1654{ 1655 if ( low_i < src.length() ) 1656 *this = (src >> low_i).to_uint64(); 1657 else 1658 *this = 0; 1659} 1660 1661 1662void sc_uint_sigref::concat_set(const sc_dt::sc_unsigned& src, int low_i) 1663{ 1664 if ( low_i < src.length() ) 1665 *this = src >> low_i; 1666 else 1667 *this = 0; 1668} 1669 1670 1671void sc_uint_sigref::concat_set(sc_dt::uint64 src, int low_i) 1672{ 1673 *this = (low_i < 64) ? src >> low_i : 0; 1674} 1675 1676} // namespace sc_core 1677