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// method_with_reset.cpp -- test for
21//
22//  Original Author: John Aynsley, Doulos, Inc.
23//
24// MODIFICATION LOG - modifiers, enter your name, affiliation, date and
25//
26// $Log: method_with_reset.cpp,v $
27// Revision 1.2  2011/05/08 19:18:46  acg
28//  Andy Goodrich: remove extraneous + prefixes from git diff.
29//
30
31// Method processes with sync and async resets, reset_event, sc_event_or_list
32
33#define SC_INCLUDE_DYNAMIC_PROCESSES
34
35#include <systemc>
36
37using namespace sc_core;
38using std::cout;
39using std::endl;
40
41struct Top: sc_module
42{
43  Top(sc_module_name _name)
44  : clk("clk")
45  , count(0)
46  {
47    SC_THREAD(ctrl);
48
49    SC_METHOD(method_sync_reset);
50      sensitive << clk.posedge_event();
51      reset_signal_is(reset, true);
52      dont_initialize();
53      m1 = sc_get_current_process_handle();
54
55    SC_METHOD(method_async_reset);
56      sensitive << clk.posedge_event();
57      async_reset_signal_is(reset, true);
58      dont_initialize();
59      m2 = sc_get_current_process_handle();
60
61    f0 = f1 = f2 = f3 = f4 = f5 = f6 = f7 = f8 = f9 = 0;
62    f10 = f11 = f12 = f13 = f14 = f15 = f16 = f17 = f18 = f19 = 0;
63    f20 = f21 = f22 = f23 = f24 = f25 = f26 = f27 = f28 = f29 = 0;
64    f30 = f31 = f32 = f33 = f34 = f35 = f36 = f37 = f38 = f39 = 0;
65    f40 = f41 = f42 = f43 = f44 = f45 = f46 = f47 = f48 = f49 = 0;
66    f50 = f51 = f52 = f53 = f54 = f55 = f56 = f57 = f58 = f59 = 0;
67  }
68
69  sc_process_handle m1, m2, m3, m4, m5, m6;
70  sc_signal<bool> clk, reset, sreset, areset;
71  int count;
72  int f0, f1, f2, f3, f4, f5, f6, f7, f8, f9;
73  int f10, f11, f12, f13, f14, f15, f16, f17, f18, f19;
74  int f20, f21, f22, f23, f24, f25, f26, f27, f28, f29;
75  int f30, f31, f32, f33, f34, f35, f36, f37, f38, f39;
76  int f40, f41, f42, f43, f44, f45, f46, f47, f48, f49;
77  int f50, f51, f52, f53, f54, f55, f56, f57, f58, f59;
78
79  void ctrl()
80  {
81    count = 1;
82    reset.write(false);
83    sreset.write(false);
84    areset.write(false);
85    clk.write(false);
86    wait(10, SC_NS);
87
88    count = 2;
89    reset.write(true);
90    wait(10, SC_NS);
91
92    count = 3;
93    reset.write(false);
94    wait(10, SC_NS);
95
96    count = 4;
97    reset.write(true);
98    wait(10, SC_NS);
99
100    count = 5;
101    clk.write(true);
102    wait(10, SC_NS);
103
104    count = 6;
105    clk.write(false);
106    wait(10, SC_NS);
107
108    count = 7;
109    reset.write(false);
110    wait(10, SC_NS);
111
112    count = 8;
113    clk.write(true);
114    wait(10, SC_NS);
115
116    count = 9;
117    clk.write(false);
118    wait(10, SC_NS);
119
120    count = 10;
121    clk.write(true);
122    wait(10, SC_NS);
123
124    count = 11;
125    reset.write(true);
126    wait(10, SC_NS);
127
128    count = 12;
129    reset.write(false);
130    wait(10, SC_NS);
131
132    count = 13;
133    reset.write(true);
134    wait(10, SC_NS);
135
136    count = 14;
137    clk.write(false);
138    wait(sc_time(200, SC_NS) - sc_time_stamp());
139
140    count = 15;
141    clk.write(true);
142    wait(10, SC_NS);
143
144    count = 16;
145    clk.write(false);
146    wait(10, SC_NS);
147
148    count = 17;
149    clk.write(true);
150    wait(10, SC_NS);
151
152    count = 18;
153    reset.write(false);
154    wait(10, SC_NS);
155
156    count = 19;
157    reset.write(true);
158    wait(10, SC_NS);
159
160    count = 20;
161    reset.write(false);
162    wait(10, SC_NS);
163
164    count = 21;
165    clk.write(false);
166    wait(sc_time(300, SC_NS) - sc_time_stamp());
167
168    count = 22;
169    clk.write(true);
170    wait(10, SC_NS);
171
172    count = 23;
173    clk.write(false);
174    m1.disable();
175    m2.disable();
176
177    sc_spawn_options opt3;
178    opt3.spawn_method();
179    opt3.set_sensitivity( &clk.posedge_event() );
180    opt3.reset_signal_is(sreset, true);
181    opt3.async_reset_signal_is(areset, true);
182    m3 = sc_spawn(sc_bind( &Top::spawned_method, this ), "m3", &opt3);
183
184    sc_spawn_options opt4;
185    opt4.spawn_method();
186    opt4.set_sensitivity( &m3.reset_event() );
187    opt4.dont_initialize();
188    m4 = sc_spawn(sc_bind( &Top::reset_handler, this), "m4", &opt4);
189
190    sc_spawn_options opt5;
191    opt5.spawn_method();
192    m5 = sc_spawn(sc_bind( &Top::reset_or_terminated_handler, this), "m5", &opt5);
193
194    std::vector<sc_event*> vec = this->get_child_events();
195    sc_assert( vec.size() == 0 );
196    wait(10, SC_NS);
197
198    m6 = sc_spawn(sc_bind( &Top::multiple_reset_handler, this) );
199
200    count = 24;
201    clk.write(true);
202    wait(10, SC_NS);
203
204    count = 25;
205    clk.write(false);
206    wait(10, SC_NS);
207
208    count = 26;
209    sreset.write(true);
210    wait(10, SC_NS);
211
212    count = 27;
213    clk.write(true);
214    wait(sc_time(500, SC_NS) - sc_time_stamp());
215
216    count = 28;
217    clk.write(false);
218    sreset.write(false);
219    wait(10, SC_NS);
220
221    count = 29;
222    m3.reset();
223    wait(10, SC_NS);
224
225    count = 30;
226    areset.write(true);
227    wait(10, SC_NS);
228
229    count = 31;
230    areset.write(false);
231    wait(10, SC_NS);
232
233    count = 32;
234    areset.write(true);
235    wait(10, SC_NS);
236
237    count = 33;
238    clk.write(true);
239    wait(10, SC_NS);
240
241    count = 34;
242    clk.write(false);
243    wait(10, SC_NS);
244
245    count = 35;
246    areset.write(false);
247    wait(sc_time(600, SC_NS) - sc_time_stamp());
248
249    count = 36;
250    m3.kill();
251    wait(10, SC_NS);
252
253    count = 37;
254    m1.reset();
255    wait(10, SC_NS);
256
257    count = 38;
258    m2.reset();
259    wait(10, SC_NS);
260
261
262  }
263
264  void method_sync_reset()
265  {
266    if (reset)
267      switch (count)
268      {
269        case  5: sc_assert( sc_time_stamp() == sc_time( 40, SC_NS) ); f0=1; break;
270        case 15: sc_assert( sc_time_stamp() == sc_time(200, SC_NS) ); f3=1; break;
271        case 17: sc_assert( sc_time_stamp() == sc_time(220, SC_NS) ); f4=1; break;
272        default: sc_assert( false );
273      }
274    else
275      switch (count)
276      {
277        case  8: sc_assert( sc_time_stamp() == sc_time( 70, SC_NS) ); f1=1; break;
278        case 10: sc_assert( sc_time_stamp() == sc_time( 90, SC_NS) ); f2=1; break;
279        case 22: sc_assert( sc_time_stamp() == sc_time(300, SC_NS) ); f5=1; break;
280        case 37: sc_assert( sc_time_stamp() == sc_time(610, SC_NS) ); f55=1; break;
281        default: sc_assert( false );
282      }
283  }
284
285  void method_async_reset()
286  {
287    if (reset)
288      switch (count)
289      {
290        case  2: sc_assert( sc_time_stamp() == sc_time( 10, SC_NS) ); f10=1; break;
291        case  4: sc_assert( sc_time_stamp() == sc_time( 30, SC_NS) ); f11=1; break;
292        case  5: sc_assert( sc_time_stamp() == sc_time( 40, SC_NS) ); f12=1; break;
293        case 11: sc_assert( sc_time_stamp() == sc_time(100, SC_NS) ); f15=1; break;
294        case 13: sc_assert( sc_time_stamp() == sc_time(120, SC_NS) ); f16=1; break;
295        case 15: sc_assert( sc_time_stamp() == sc_time(200, SC_NS) ); f17=1; break;
296        case 17: sc_assert( sc_time_stamp() == sc_time(220, SC_NS) ); f18=1; break;
297        case 19: sc_assert( sc_time_stamp() == sc_time(240, SC_NS) ); f19=1; break;
298        default: sc_assert( false );
299      }
300    else
301      switch (count)
302      {
303        case  8: sc_assert( sc_time_stamp() == sc_time( 70, SC_NS) ); f13=1; break;
304        case 10: sc_assert( sc_time_stamp() == sc_time( 90, SC_NS) ); f14=1; break;
305        case 22: sc_assert( sc_time_stamp() == sc_time(300, SC_NS) ); f20=1; break;
306        case 38: sc_assert( sc_time_stamp() == sc_time(620, SC_NS) ); f57=1; break;
307        default: sc_assert( false );
308      }
309  }
310
311  void spawned_method()
312  {
313    switch (count)
314    {
315      case 23: sc_assert( sc_time_stamp() == sc_time(310, SC_NS) ); f30=1; break;
316      case 24: sc_assert( sc_time_stamp() == sc_time(320, SC_NS) ); f31=1; break;
317      case 27: sc_assert( sc_time_stamp() == sc_time(350, SC_NS) ); f32=1; break;
318      case 29: sc_assert( sc_time_stamp() == sc_time(510, SC_NS) ); f34=1; break;
319      case 30: sc_assert( sc_time_stamp() == sc_time(520, SC_NS) ); f36=1; break;
320      case 32: sc_assert( sc_time_stamp() == sc_time(540, SC_NS) ); f38=1; break;
321      case 33: sc_assert( sc_time_stamp() == sc_time(550, SC_NS) ); f40=1; break;
322      default: sc_assert( false );
323    }
324  }
325
326  void reset_handler()
327  {
328    switch (count)
329    {
330      case 27: sc_assert( sc_time_stamp() == sc_time(350, SC_NS) ); f33=1; break;
331      case 29: sc_assert( sc_time_stamp() == sc_time(510, SC_NS) ); f35=1; break;
332      case 30: sc_assert( sc_time_stamp() == sc_time(520, SC_NS) ); f37=1; break;
333      case 32: sc_assert( sc_time_stamp() == sc_time(540, SC_NS) ); f39=1; break;
334      case 33: sc_assert( sc_time_stamp() == sc_time(550, SC_NS) ); f41=1; break;
335      default: sc_assert( false );
336    }
337  }
338
339  sc_event_or_list event_list;
340
341  void reset_or_terminated_handler()
342  {
343    switch (count)
344    {
345      case 23: sc_assert( sc_time_stamp() == sc_time(310, SC_NS) ); f42=1; break;
346      case 27: sc_assert( sc_time_stamp() == sc_time(350, SC_NS) ); f43=1; break;
347      case 29: sc_assert( sc_time_stamp() == sc_time(510, SC_NS) ); f44=1; break;
348      case 30: sc_assert( sc_time_stamp() == sc_time(520, SC_NS) ); f45=1; break;
349      case 32: sc_assert( sc_time_stamp() == sc_time(540, SC_NS) ); f46=1; break;
350      case 33: sc_assert( sc_time_stamp() == sc_time(550, SC_NS) ); f47=1; break;
351      case 36: sc_assert( sc_time_stamp() == sc_time(600, SC_NS) ); f48=1; break;
352      default: sc_assert( false );
353    }
354    event_list = m3.reset_event() | m3.terminated_event();
355    next_trigger(event_list);
356  }
357
358  void multiple_reset_handler()
359  {
360    sc_event_or_list or_list;
361    or_list |= m1.reset_event();
362    or_list |= m2.reset_event();
363    or_list |= m3.reset_event();
364    or_list |= m4.reset_event();
365    or_list |= m5.reset_event();
366
367    while (true)
368    {
369      wait(or_list);
370      switch (count)
371      {
372        case 27: sc_assert( sc_time_stamp() == sc_time(350, SC_NS) ); f50=1; break;
373        case 29: sc_assert( sc_time_stamp() == sc_time(510, SC_NS) ); f51=1; break;
374        case 30: sc_assert( sc_time_stamp() == sc_time(520, SC_NS) ); f52=1; break;
375        case 32: sc_assert( sc_time_stamp() == sc_time(540, SC_NS) ); f53=1; break;
376        case 33: sc_assert( sc_time_stamp() == sc_time(550, SC_NS) ); f54=1; break;
377        case 37: sc_assert( sc_time_stamp() == sc_time(610, SC_NS) ); f56=1; break;
378        case 38: sc_assert( sc_time_stamp() == sc_time(620, SC_NS) ); f58=1; break;
379        default: sc_assert( false );
380      }
381    }
382  }
383
384  SC_HAS_PROCESS(Top);
385};
386
387int sc_main(int argc, char* argv[])
388{
389  sc_allow_process_control_corners = true; // Andy's hack to switch on async_reset with method
390
391  Top top("top");
392
393  sc_start();
394
395  sc_assert( top.f0 );
396  sc_assert( top.f1 );
397  sc_assert( top.f2 );
398  sc_assert( top.f3 );
399  sc_assert( top.f4 );
400  sc_assert( top.f5 );
401  sc_assert( top.f10 );
402  sc_assert( top.f11 );
403  sc_assert( top.f12 );
404  sc_assert( top.f13 );
405  sc_assert( top.f14 );
406  sc_assert( top.f15 );
407  sc_assert( top.f16 );
408  sc_assert( top.f17 );
409  sc_assert( top.f18 );
410  sc_assert( top.f19 );
411  sc_assert( top.f20 );
412
413  sc_assert( top.f30 );
414  sc_assert( top.f31 );
415  sc_assert( top.f32 );
416  sc_assert( top.f33 );
417  sc_assert( top.f34 );
418  sc_assert( top.f35 );
419  sc_assert( top.f36 );
420  sc_assert( top.f37 );
421  sc_assert( top.f38 );
422  sc_assert( top.f39 );
423  sc_assert( top.f40 );
424  sc_assert( top.f41 );
425  sc_assert( top.f42 );
426  sc_assert( top.f43 );
427  sc_assert( top.f44 );
428  sc_assert( top.f45 );
429  sc_assert( top.f46 );
430  sc_assert( top.f47 );
431  sc_assert( top.f48 );
432
433  sc_assert( top.f50 );
434  sc_assert( top.f51 );
435  sc_assert( top.f52 );
436  sc_assert( top.f53 );
437  sc_assert( top.f54 );
438  sc_assert( top.f55 );
439  sc_assert( top.f56 );
440  sc_assert( top.f57 );
441  sc_assert( top.f58 );
442
443  cout << endl << "Success" << endl;
444  return 0;
445}
446
447