sc_module.cc revision 13189:057566bc8fd6
1/* 2 * Copyright 2018 Google, Inc. 3 * 4 * Redistribution and use in source and binary forms, with or without 5 * modification, are permitted provided that the following conditions are 6 * met: redistributions of source code must retain the above copyright 7 * notice, this list of conditions and the following disclaimer; 8 * redistributions in binary form must reproduce the above copyright 9 * notice, this list of conditions and the following disclaimer in the 10 * documentation and/or other materials provided with the distribution; 11 * neither the name of the copyright holders nor the names of its 12 * contributors may be used to endorse or promote products derived from 13 * this software without specific prior written permission. 14 * 15 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 16 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 17 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 18 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 19 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 20 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 21 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 22 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 23 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 24 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 25 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 26 * 27 * Authors: Gabe Black 28 */ 29 30#include <memory> 31#include <string> 32#include <vector> 33 34#include "base/logging.hh" 35#include "systemc/core/kernel.hh" 36#include "systemc/core/module.hh" 37#include "systemc/core/process_types.hh" 38#include "systemc/ext/channel/sc_signal_in_if.hh" 39#include "systemc/ext/core/sc_module.hh" 40#include "systemc/ext/core/sc_module_name.hh" 41#include "systemc/ext/dt/bit/sc_logic.hh" 42#include "systemc/ext/utils/sc_report_handler.hh" 43 44namespace sc_gem5 45{ 46 47Process * 48newMethodProcess(const char *name, ProcessFuncWrapper *func) 49{ 50 Method *p = new Method(name, func); 51 if (::sc_core::sc_is_running()) { 52 std::string name = p->name(); 53 delete p; 54 SC_REPORT_ERROR("(E541) call to SC_METHOD in sc_module while " 55 "simulation running", name.c_str()); 56 return nullptr; 57 } 58 scheduler.reg(p); 59 return p; 60} 61 62Process * 63newThreadProcess(const char *name, ProcessFuncWrapper *func) 64{ 65 Thread *p = new Thread(name, func); 66 if (::sc_core::sc_is_running()) { 67 std::string name = p->name(); 68 delete p; 69 SC_REPORT_ERROR("(E542) call to SC_THREAD in sc_module while " 70 "simulation running", name.c_str()); 71 return nullptr; 72 } 73 scheduler.reg(p); 74 return p; 75} 76 77Process * 78newCThreadProcess(const char *name, ProcessFuncWrapper *func) 79{ 80 CThread *p = new CThread(name, func); 81 if (::sc_core::sc_is_running()) { 82 std::string name = p->name(); 83 delete p; 84 SC_REPORT_ERROR("(E543) call to SC_CTHREAD in sc_module while " 85 "simulation running", name.c_str()); 86 return nullptr; 87 } 88 scheduler.reg(p); 89 p->dontInitialize(); 90 return p; 91} 92 93UniqueNameGen nameGen; 94 95} // namespace sc_gem5 96 97namespace sc_core 98{ 99 100sc_bind_proxy::sc_bind_proxy(sc_interface &_interface) : 101 _interface(&_interface), _port(nullptr) 102{} 103 104sc_bind_proxy::sc_bind_proxy(sc_port_base &_port) : 105 _interface(nullptr), _port(&_port) 106{} 107 108const sc_bind_proxy SC_BIND_PROXY_NUL(*(sc_port_base *)nullptr); 109 110sc_module::~sc_module() { delete _gem5_module; } 111 112const sc_bind_proxy SC_BIND_PROXY_NIL(*(sc_port_base *)nullptr); 113 114void 115sc_module::operator () (const sc_bind_proxy &p001, 116 const sc_bind_proxy &p002, 117 const sc_bind_proxy &p003, 118 const sc_bind_proxy &p004, 119 const sc_bind_proxy &p005, 120 const sc_bind_proxy &p006, 121 const sc_bind_proxy &p007, 122 const sc_bind_proxy &p008, 123 const sc_bind_proxy &p009, 124 const sc_bind_proxy &p010, 125 const sc_bind_proxy &p011, 126 const sc_bind_proxy &p012, 127 const sc_bind_proxy &p013, 128 const sc_bind_proxy &p014, 129 const sc_bind_proxy &p015, 130 const sc_bind_proxy &p016, 131 const sc_bind_proxy &p017, 132 const sc_bind_proxy &p018, 133 const sc_bind_proxy &p019, 134 const sc_bind_proxy &p020, 135 const sc_bind_proxy &p021, 136 const sc_bind_proxy &p022, 137 const sc_bind_proxy &p023, 138 const sc_bind_proxy &p024, 139 const sc_bind_proxy &p025, 140 const sc_bind_proxy &p026, 141 const sc_bind_proxy &p027, 142 const sc_bind_proxy &p028, 143 const sc_bind_proxy &p029, 144 const sc_bind_proxy &p030, 145 const sc_bind_proxy &p031, 146 const sc_bind_proxy &p032, 147 const sc_bind_proxy &p033, 148 const sc_bind_proxy &p034, 149 const sc_bind_proxy &p035, 150 const sc_bind_proxy &p036, 151 const sc_bind_proxy &p037, 152 const sc_bind_proxy &p038, 153 const sc_bind_proxy &p039, 154 const sc_bind_proxy &p040, 155 const sc_bind_proxy &p041, 156 const sc_bind_proxy &p042, 157 const sc_bind_proxy &p043, 158 const sc_bind_proxy &p044, 159 const sc_bind_proxy &p045, 160 const sc_bind_proxy &p046, 161 const sc_bind_proxy &p047, 162 const sc_bind_proxy &p048, 163 const sc_bind_proxy &p049, 164 const sc_bind_proxy &p050, 165 const sc_bind_proxy &p051, 166 const sc_bind_proxy &p052, 167 const sc_bind_proxy &p053, 168 const sc_bind_proxy &p054, 169 const sc_bind_proxy &p055, 170 const sc_bind_proxy &p056, 171 const sc_bind_proxy &p057, 172 const sc_bind_proxy &p058, 173 const sc_bind_proxy &p059, 174 const sc_bind_proxy &p060, 175 const sc_bind_proxy &p061, 176 const sc_bind_proxy &p062, 177 const sc_bind_proxy &p063, 178 const sc_bind_proxy &p064) 179{ 180 std::vector<const ::sc_core::sc_bind_proxy *> proxies; 181 auto insert = [&proxies](const ::sc_core::sc_bind_proxy &p) -> bool { 182 if (!p.port() && !p.interface()) 183 return false; 184 proxies.push_back(&p); 185 return true; 186 }; 187 insert(p001) && insert(p002) && insert(p003) && insert(p004) && 188 insert(p005) && insert(p006) && insert(p007) && insert(p008) && 189 insert(p009) && insert(p010) && insert(p011) && insert(p012) && 190 insert(p013) && insert(p014) && insert(p015) && insert(p016) && 191 insert(p017) && insert(p018) && insert(p019) && insert(p020) && 192 insert(p021) && insert(p022) && insert(p023) && insert(p024) && 193 insert(p025) && insert(p026) && insert(p027) && insert(p028) && 194 insert(p029) && insert(p030) && insert(p031) && insert(p032) && 195 insert(p033) && insert(p034) && insert(p035) && insert(p036) && 196 insert(p037) && insert(p038) && insert(p039) && insert(p040) && 197 insert(p041) && insert(p042) && insert(p043) && insert(p044) && 198 insert(p045) && insert(p046) && insert(p047) && insert(p048) && 199 insert(p049) && insert(p050) && insert(p051) && insert(p052) && 200 insert(p053) && insert(p054) && insert(p055) && insert(p056) && 201 insert(p057) && insert(p058) && insert(p059) && insert(p060) && 202 insert(p061) && insert(p062) && insert(p063) && insert(p064); 203 _gem5_module->bindPorts(proxies); 204} 205 206const std::vector<sc_object *> & 207sc_module::get_child_objects() const 208{ 209 return _gem5_module->obj()->get_child_objects(); 210} 211 212const std::vector<sc_event *> & 213sc_module::get_child_events() const 214{ 215 return _gem5_module->obj()->get_child_events(); 216} 217 218sc_module::sc_module() : 219 sc_object(sc_gem5::newModuleChecked()->name()), 220 _gem5_module(sc_gem5::currentModule()) 221{} 222 223sc_module::sc_module(const sc_module_name &) : sc_module() {} 224sc_module::sc_module(const char *_name) : sc_module(sc_module_name(_name)) {} 225sc_module::sc_module(const std::string &_name) : 226 sc_module(sc_module_name(_name.c_str())) 227{} 228 229void 230sc_module::reset_signal_is(const sc_in<bool> &, bool) 231{ 232 warn("%s not implemented.\n", __PRETTY_FUNCTION__); 233} 234 235void 236sc_module::reset_signal_is(const sc_inout<bool> &, bool) 237{ 238 warn("%s not implemented.\n", __PRETTY_FUNCTION__); 239} 240 241void 242sc_module::reset_signal_is(const sc_out<bool> &, bool) 243{ 244 warn("%s not implemented.\n", __PRETTY_FUNCTION__); 245} 246 247void 248sc_module::reset_signal_is(const sc_signal_in_if<bool> &, bool) 249{ 250 warn("%s not implemented.\n", __PRETTY_FUNCTION__); 251} 252 253 254void 255sc_module::async_reset_signal_is(const sc_in<bool> &, bool) 256{ 257 warn("%s not implemented.\n", __PRETTY_FUNCTION__); 258} 259 260void 261sc_module::async_reset_signal_is(const sc_inout<bool> &, bool) 262{ 263 warn("%s not implemented.\n", __PRETTY_FUNCTION__); 264} 265 266void 267sc_module::async_reset_signal_is(const sc_out<bool> &, bool) 268{ 269 warn("%s not implemented.\n", __PRETTY_FUNCTION__); 270} 271 272void 273sc_module::async_reset_signal_is(const sc_signal_in_if<bool> &, bool) 274{ 275 warn("%s not implemented.\n", __PRETTY_FUNCTION__); 276} 277 278 279void 280sc_module::dont_initialize() 281{ 282 ::sc_gem5::Process::newest()->dontInitialize(); 283} 284 285void 286sc_module::set_stack_size(size_t size) 287{ 288 ::sc_gem5::Process::newest()->setStackSize(size); 289} 290 291 292void sc_module::next_trigger() { ::sc_core::next_trigger(); } 293 294void 295sc_module::next_trigger(const sc_event &e) 296{ 297 ::sc_core::next_trigger(e); 298} 299 300void 301sc_module::next_trigger(const sc_event_or_list &eol) 302{ 303 ::sc_core::next_trigger(eol); 304} 305 306void 307sc_module::next_trigger(const sc_event_and_list &eal) 308{ 309 ::sc_core::next_trigger(eal); 310} 311 312void 313sc_module::next_trigger(const sc_time &t) 314{ 315 ::sc_core::next_trigger(t); 316} 317 318void 319sc_module::next_trigger(double d, sc_time_unit u) 320{ 321 ::sc_core::next_trigger(d, u); 322} 323 324void 325sc_module::next_trigger(const sc_time &t, const sc_event &e) 326{ 327 ::sc_core::next_trigger(t, e); 328} 329 330void 331sc_module::next_trigger(double d, sc_time_unit u, const sc_event &e) 332{ 333 ::sc_core::next_trigger(d, u, e); 334} 335 336void 337sc_module::next_trigger(const sc_time &t, const sc_event_or_list &eol) 338{ 339 ::sc_core::next_trigger(t, eol); 340} 341 342void 343sc_module::next_trigger(double d, sc_time_unit u, const sc_event_or_list &eol) 344{ 345 ::sc_core::next_trigger(d, u, eol); 346} 347 348void 349sc_module::next_trigger(const sc_time &t, const sc_event_and_list &eal) 350{ 351 ::sc_core::next_trigger(t, eal); 352} 353 354void 355sc_module::next_trigger(double d, sc_time_unit u, const sc_event_and_list &eal) 356{ 357 ::sc_core::next_trigger(d, u, eal); 358} 359 360 361bool 362sc_module::timed_out() 363{ 364 return ::sc_core::timed_out(); 365} 366 367 368void 369sc_module::wait() 370{ 371 ::sc_core::wait(); 372} 373 374void 375sc_module::wait(int i) 376{ 377 ::sc_core::wait(i); 378} 379 380void 381sc_module::wait(const sc_event &e) 382{ 383 ::sc_core::wait(e); 384} 385 386void 387sc_module::wait(const sc_event_or_list &eol) 388{ 389 ::sc_core::wait(eol); 390} 391 392void 393sc_module::wait(const sc_event_and_list &eal) 394{ 395 ::sc_core::wait(eal); 396} 397 398void 399sc_module::wait(const sc_time &t) 400{ 401 ::sc_core::wait(t); 402} 403 404void 405sc_module::wait(double d, sc_time_unit u) 406{ 407 ::sc_core::wait(d, u); 408} 409 410void 411sc_module::wait(const sc_time &t, const sc_event &e) 412{ 413 ::sc_core::wait(t, e); 414} 415 416void 417sc_module::wait(double d, sc_time_unit u, const sc_event &e) 418{ 419 ::sc_core::wait(d, u, e); 420} 421 422void 423sc_module::wait(const sc_time &t, const sc_event_or_list &eol) 424{ 425 ::sc_core::wait(t, eol); 426} 427 428void 429sc_module::wait(double d, sc_time_unit u, const sc_event_or_list &eol) 430{ 431 ::sc_core::wait(d, u, eol); 432} 433 434void 435sc_module::wait(const sc_time &t, const sc_event_and_list &eal) 436{ 437 ::sc_core::wait(t, eal); 438} 439 440void 441sc_module::wait(double d, sc_time_unit u, const sc_event_and_list &eal) 442{ 443 ::sc_core::wait(d, u, eal); 444} 445 446 447void 448sc_module::halt() 449{ 450 ::sc_core::halt(); 451} 452 453void 454sc_module::at_posedge(const sc_signal_in_if<bool> &s) 455{ 456 ::sc_core::at_posedge(s); 457} 458 459void 460sc_module::at_posedge(const sc_signal_in_if<sc_dt::sc_logic> &s) 461{ 462 ::sc_core::at_posedge(s); 463} 464 465void 466sc_module::at_negedge(const sc_signal_in_if<bool> &s) 467{ 468 ::sc_core::at_negedge(s); 469} 470 471void 472sc_module::at_negedge(const sc_signal_in_if<sc_dt::sc_logic> &s) 473{ 474 ::sc_core::at_negedge(s); 475} 476 477 478void 479next_trigger() 480{ 481 sc_gem5::Process *p = sc_gem5::scheduler.current(); 482 p->setDynamic(nullptr); 483} 484 485void 486next_trigger(const sc_event &e) 487{ 488 sc_gem5::Process *p = sc_gem5::scheduler.current(); 489 p->setDynamic(new ::sc_gem5::SensitivityEvent(p, &e)); 490} 491 492void 493next_trigger(const sc_event_or_list &eol) 494{ 495 sc_gem5::Process *p = sc_gem5::scheduler.current(); 496 p->setDynamic(new ::sc_gem5::SensitivityEventOrList(p, &eol)); 497} 498 499void 500next_trigger(const sc_event_and_list &eal) 501{ 502 sc_gem5::Process *p = sc_gem5::scheduler.current(); 503 p->setDynamic(new ::sc_gem5::SensitivityEventAndList(p, &eal)); 504} 505 506void 507next_trigger(const sc_time &t) 508{ 509 sc_gem5::Process *p = sc_gem5::scheduler.current(); 510 p->setDynamic(new ::sc_gem5::SensitivityTimeout(p, t)); 511} 512 513void 514next_trigger(double d, sc_time_unit u) 515{ 516 next_trigger(sc_time(d, u)); 517} 518 519void 520next_trigger(const sc_time &t, const sc_event &e) 521{ 522 sc_gem5::Process *p = sc_gem5::scheduler.current(); 523 p->setDynamic(new ::sc_gem5::SensitivityTimeoutAndEvent(p, t, &e)); 524} 525 526void 527next_trigger(double d, sc_time_unit u, const sc_event &e) 528{ 529 next_trigger(sc_time(d, u), e); 530} 531 532void 533next_trigger(const sc_time &t, const sc_event_or_list &eol) 534{ 535 sc_gem5::Process *p = sc_gem5::scheduler.current(); 536 p->setDynamic( 537 new ::sc_gem5::SensitivityTimeoutAndEventOrList(p, t, &eol)); 538} 539 540void 541next_trigger(double d, sc_time_unit u, const sc_event_or_list &eol) 542{ 543 next_trigger(sc_time(d, u), eol); 544} 545 546void 547next_trigger(const sc_time &t, const sc_event_and_list &eal) 548{ 549 sc_gem5::Process *p = sc_gem5::scheduler.current(); 550 p->setDynamic( 551 new ::sc_gem5::SensitivityTimeoutAndEventAndList(p, t, &eal)); 552} 553 554void 555next_trigger(double d, sc_time_unit u, const sc_event_and_list &eal) 556{ 557 next_trigger(sc_time(d, u), eal); 558} 559 560bool 561timed_out() 562{ 563 ::sc_gem5::Process *p = sc_gem5::scheduler.current(); 564 if (!p) 565 return false; 566 else 567 return p->timedOut(); 568} 569 570 571void 572wait() 573{ 574 sc_gem5::Process *p = sc_gem5::scheduler.current(); 575 p->setDynamic(nullptr); 576 sc_gem5::scheduler.yield(); 577} 578 579void 580wait(int n) 581{ 582 if (n <= 0) { 583 std::string msg = csprintf("n = %d", n); 584 SC_REPORT_ERROR("(E525) wait(n) is only valid for n > 0", msg.c_str()); 585 } 586 for (int i = 0; i < n; i++) 587 wait(); 588} 589 590void 591wait(const sc_event &e) 592{ 593 sc_gem5::Process *p = sc_gem5::scheduler.current(); 594 p->setDynamic(new ::sc_gem5::SensitivityEvent(p, &e)); 595 sc_gem5::scheduler.yield(); 596} 597 598void 599wait(const sc_event_or_list &eol) 600{ 601 sc_gem5::Process *p = sc_gem5::scheduler.current(); 602 p->setDynamic(new ::sc_gem5::SensitivityEventOrList(p, &eol)); 603 sc_gem5::scheduler.yield(); 604} 605 606void 607wait(const sc_event_and_list &eal) 608{ 609 sc_gem5::Process *p = sc_gem5::scheduler.current(); 610 p->setDynamic(new ::sc_gem5::SensitivityEventAndList(p, &eal)); 611 sc_gem5::scheduler.yield(); 612} 613 614void 615wait(const sc_time &t) 616{ 617 sc_gem5::Process *p = sc_gem5::scheduler.current(); 618 p->setDynamic(new ::sc_gem5::SensitivityTimeout(p, t)); 619 sc_gem5::scheduler.yield(); 620} 621 622void 623wait(double d, sc_time_unit u) 624{ 625 wait(sc_time(d, u)); 626} 627 628void 629wait(const sc_time &t, const sc_event &e) 630{ 631 sc_gem5::Process *p = sc_gem5::scheduler.current(); 632 p->setDynamic(new ::sc_gem5::SensitivityTimeoutAndEvent(p, t, &e)); 633 sc_gem5::scheduler.yield(); 634} 635 636void 637wait(double d, sc_time_unit u, const sc_event &e) 638{ 639 wait(sc_time(d, u), e); 640} 641 642void 643wait(const sc_time &t, const sc_event_or_list &eol) 644{ 645 sc_gem5::Process *p = sc_gem5::scheduler.current(); 646 p->setDynamic( 647 new ::sc_gem5::SensitivityTimeoutAndEventOrList(p, t, &eol)); 648 sc_gem5::scheduler.yield(); 649} 650 651void 652wait(double d, sc_time_unit u, const sc_event_or_list &eol) 653{ 654 wait(sc_time(d, u), eol); 655} 656 657void 658wait(const sc_time &t, const sc_event_and_list &eal) 659{ 660 sc_gem5::Process *p = sc_gem5::scheduler.current(); 661 p->setDynamic( 662 new ::sc_gem5::SensitivityTimeoutAndEventAndList(p, t, &eal)); 663 sc_gem5::scheduler.yield(); 664} 665 666void 667wait(double d, sc_time_unit u, const sc_event_and_list &eal) 668{ 669 wait(sc_time(d, u), eal); 670} 671 672void 673halt() 674{ 675 ::sc_core::wait(); 676 throw ::sc_gem5::ScHalt(); 677} 678 679void 680at_posedge(const sc_signal_in_if<bool> &s) 681{ 682 while (s.read()) 683 wait(); 684 while (!s.read()) 685 wait(); 686} 687 688void 689at_posedge(const sc_signal_in_if<sc_dt::sc_logic> &s) 690{ 691 while (s.read() == sc_dt::Log_1) 692 wait(); 693 while (s.read() == sc_dt::Log_0) 694 wait(); 695} 696 697void 698at_negedge(const sc_signal_in_if<bool> &s) 699{ 700 while (!s.read()) 701 wait(); 702 while (s.read()) 703 wait(); 704} 705 706void 707at_negedge(const sc_signal_in_if<sc_dt::sc_logic> &s) 708{ 709 while (s.read() == sc_dt::Log_0) 710 wait(); 711 while (s.read() == sc_dt::Log_1) 712 wait(); 713} 714 715const char * 716sc_gen_unique_name(const char *seed) 717{ 718 ::sc_gem5::Module *mod = ::sc_gem5::currentModule(); 719 return mod ? mod->uniqueName(seed) : 720 ::sc_gem5::nameGen.gen(seed); 721} 722 723bool 724sc_hierarchical_name_exists(const char *name) 725{ 726 warn("%s not implemented.\n", __PRETTY_FUNCTION__); 727 return false; 728} 729 730bool 731sc_start_of_simulation_invoked() 732{ 733 return ::sc_gem5::kernel->startOfSimulationComplete(); 734} 735 736bool 737sc_end_of_simulation_invoked() 738{ 739 return ::sc_gem5::kernel->endOfSimulationComplete(); 740} 741 742sc_module * 743sc_module_sc_new(sc_module *mod) 744{ 745 static std::vector<std::unique_ptr<sc_module> > modules; 746 modules.emplace_back(mod); 747 return mod; 748} 749 750} // namespace sc_core 751