systemc: Improve scheduler cleanup.
authorGabe Black <gabeblack@google.com>
Tue, 21 Aug 2018 22:29:15 +0000 (15:29 -0700)
committerGabe Black <gabeblack@google.com>
Tue, 25 Sep 2018 23:53:16 +0000 (23:53 +0000)
Make the scheduler clear itself out when it's destructed to ensure that
nobody will try to use it after it's gone away. Also make sure there
are no pending events which might refer to it as well, either systemc
events or gem5 events.

Change-Id: I12dadc06bd9db7016a8dc0c1827b3e630b0d23d5
Reviewed-on: https://gem5-review.googlesource.com/12222
Reviewed-by: Gabe Black <gabeblack@google.com>
Maintainer: Gabe Black <gabeblack@google.com>

src/systemc/core/SConscript
src/systemc/core/channel.cc
src/systemc/core/process.hh
src/systemc/core/sched_event.cc [new file with mode: 0644]
src/systemc/core/sched_event.hh
src/systemc/core/scheduler.cc
src/systemc/core/scheduler.hh

index 76327c860fb8f7dc9d7b8f66c917a0cf97750cd9..4814e6afa9209b52370a9f8b9cd41afbcbe3f721 100644 (file)
@@ -39,6 +39,7 @@ if env['USE_SYSTEMC']:
     Source('process_types.cc')
     Source('python.cc')
     Source('scheduler.cc')
+    Source('sched_event.cc')
 
     Source('sc_attr.cc')
     Source('sc_event.cc')
index 49d9f6cb78c8eb2caf35f7d70e7f155b1a01f854..04f158bead71efd81dacd44abc2f8fd4fa8ba07f 100644 (file)
@@ -41,6 +41,7 @@ Channel::Channel(sc_core::sc_prim_channel *_sc_chan) : _sc_chan(_sc_chan)
 
 Channel::~Channel()
 {
+    popListNode();
     allChannels.erase(this);
 }
 
index 25d3e4eb0d6dfb09741dd2d1d021cdae2cc11c81..267a7ed3d9fd7fab40eda273fd923bf0bc2b5cf1 100644 (file)
@@ -330,6 +330,7 @@ class Process : public ::sc_core::sc_object, public ListNode
 
     virtual ~Process()
     {
+        popListNode();
         delete func;
         for (auto s: staticSensitivities)
             delete s;
diff --git a/src/systemc/core/sched_event.cc b/src/systemc/core/sched_event.cc
new file mode 100644 (file)
index 0000000..576c23b
--- /dev/null
@@ -0,0 +1,43 @@
+/*
+ * Copyright 2018 Google, Inc.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met: redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer;
+ * redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution;
+ * neither the name of the copyright holders nor the names of its
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+ * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+ * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ *
+ * Authors: Gabe Black
+ */
+
+#include "systemc/core/sched_event.hh"
+
+#include "systemc/core/scheduler.hh"
+
+namespace sc_gem5
+{
+
+ScEvent::~ScEvent()
+{
+    if (scheduled())
+        scheduler.deschedule(this);
+}
+
+} // namespace sc_gem5
index 63b76ef0a645be5ee00f06c58b7e45d456572a03..9aefb744049dfaa930e9c7b7294c9c0649c546c3 100644 (file)
@@ -59,6 +59,8 @@ class ScEvent
         work(work), _when(MaxTick), _scheduled(false)
     {}
 
+    ~ScEvent();
+
     bool scheduled() { return _scheduled; }
 
     void when(Tick w) { _when = w; }
index cdebd99866f608cfe2b333f9e64b5e1b8da350bd..6762086a0f94f19b4bdbf5ac3ec972bb57411b73 100644 (file)
@@ -50,6 +50,48 @@ Scheduler::Scheduler() :
     runOnce(false)
 {}
 
+Scheduler::~Scheduler()
+{
+    // Clear out everything that belongs to us to make sure nobody tries to
+    // clear themselves out after the scheduler goes away.
+
+    // Delta notifications.
+    for (auto &e: deltas)
+        e->deschedule();
+
+    // Timed notifications.
+    for (auto &ts: timeSlots) {
+        for (auto &e: ts.second->events)
+            e->deschedule();
+        delete ts.second;
+        ts.second = nullptr;
+    }
+
+    // gem5 events.
+    if (readyEvent.scheduled())
+        eq->deschedule(&readyEvent);
+    if (pauseEvent.scheduled())
+        eq->deschedule(&pauseEvent);
+    if (stopEvent.scheduled())
+        eq->deschedule(&stopEvent);
+    if (starvationEvent.scheduled())
+        eq->deschedule(&starvationEvent);
+    if (maxTickEvent.scheduled())
+        eq->deschedule(&maxTickEvent);
+
+    Process *p;
+    while ((p = toFinalize.getNext()))
+        p->popListNode();
+    while ((p = initList.getNext()))
+        p->popListNode();
+    while ((p = readyList.getNext()))
+        p->popListNode();
+
+    Channel *c;
+    while ((c = updateList.getNext()))
+        c->popListNode();
+}
+
 void
 Scheduler::initPhase()
 {
index c22bdf87025b7c33f822b48421502087e96815d8..24b7fd2ff4ad1f74501c179cd19228ed7f571436 100644 (file)
@@ -159,6 +159,7 @@ class Scheduler
     typedef std::map<Tick, TimeSlot *> TimeSlots;
 
     Scheduler();
+    ~Scheduler();
 
     const std::string name() const { return "systemc_scheduler"; }