HDLRuby 2.10.5 → 2.11.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (38) hide show
  1. checksums.yaml +4 -4
  2. data/HDLRuby.gemspec +1 -0
  3. data/README.md +8 -4
  4. data/Rakefile +8 -0
  5. data/{lib/HDLRuby/sim/Makefile → ext/hruby_sim/Makefile_csim} +0 -0
  6. data/ext/hruby_sim/extconf.rb +13 -0
  7. data/ext/hruby_sim/hruby_rcsim_build.c +1188 -0
  8. data/{lib/HDLRuby/sim → ext/hruby_sim}/hruby_sim.h +255 -16
  9. data/{lib/HDLRuby/sim → ext/hruby_sim}/hruby_sim_calc.c +310 -181
  10. data/{lib/HDLRuby/sim → ext/hruby_sim}/hruby_sim_core.c +34 -17
  11. data/{lib/HDLRuby/sim → ext/hruby_sim}/hruby_sim_list.c +0 -0
  12. data/{lib/HDLRuby/sim → ext/hruby_sim}/hruby_sim_stack_calc.c +4 -1
  13. data/{lib/HDLRuby/sim → ext/hruby_sim}/hruby_sim_stack_calc.c.sav +0 -0
  14. data/ext/hruby_sim/hruby_sim_tree_calc.c +375 -0
  15. data/{lib/HDLRuby/sim → ext/hruby_sim}/hruby_sim_vcd.c +5 -5
  16. data/{lib/HDLRuby/sim → ext/hruby_sim}/hruby_sim_vizualize.c +2 -2
  17. data/{lib/HDLRuby/sim → ext/hruby_sim}/hruby_value_pool.c +4 -1
  18. data/lib/HDLRuby/hdr_samples/bstr_bench.rb +2 -0
  19. data/lib/HDLRuby/hdr_samples/case_bench.rb +2 -2
  20. data/lib/HDLRuby/hdr_samples/counter_bench.rb +0 -1
  21. data/lib/HDLRuby/hdr_samples/counter_dff_bench.rb +46 -0
  22. data/lib/HDLRuby/hdr_samples/dff_bench.rb +1 -1
  23. data/lib/HDLRuby/hdr_samples/print_bench.rb +62 -0
  24. data/lib/HDLRuby/hdr_samples/rom.rb +5 -3
  25. data/lib/HDLRuby/hdr_samples/simple_counter_bench.rb +43 -0
  26. data/lib/HDLRuby/hdrcc.rb +54 -8
  27. data/lib/HDLRuby/hruby_bstr.rb +1175 -917
  28. data/lib/HDLRuby/hruby_high.rb +200 -90
  29. data/lib/HDLRuby/hruby_high_fullname.rb +82 -0
  30. data/lib/HDLRuby/hruby_low.rb +41 -23
  31. data/lib/HDLRuby/hruby_low2c.rb +7 -0
  32. data/lib/HDLRuby/hruby_rcsim.rb +978 -0
  33. data/lib/HDLRuby/hruby_rsim.rb +1134 -0
  34. data/lib/HDLRuby/hruby_rsim_vcd.rb +322 -0
  35. data/lib/HDLRuby/hruby_values.rb +362 -18
  36. data/lib/HDLRuby/hruby_verilog.rb +21 -3
  37. data/lib/HDLRuby/version.rb +1 -1
  38. metadata +24 -13
@@ -0,0 +1,978 @@
1
+ require 'set'
2
+ require 'HDLRuby'
3
+ require 'hruby_high_fullname'
4
+ require 'hruby_sim/hruby_sim'
5
+
6
+
7
+ module HDLRuby::High
8
+
9
+
10
+ ##
11
+ # Library for describing the hybrid Ruby-C simulator of HDLRuby
12
+ #
13
+ ########################################################################
14
+
15
+ ## Provides tools for converting HDLRuby::High objects to C.
16
+ module High2C
17
+
18
+ ## Gives the width of an int in the current computer.
19
+ def self.int_width
20
+ # puts "int_width=#{[1.to_i].pack("i").size*8}"
21
+ return [1.to_i].pack("i").size*8
22
+ end
23
+
24
+ ## Converts string +str+ to a C-compatible string.
25
+ def self.c_string(str)
26
+ str = str.gsub(/\n/,"\\n")
27
+ str.gsub!(/\t/,"\\t")
28
+ return str
29
+ end
30
+
31
+ ## Converts a +name+ to a C-compatible name.
32
+ def self.c_name(name)
33
+ name = name.to_s
34
+ # Convert special characters.
35
+ name = name.each_char.map do |c|
36
+ if c=~ /[a-z0-9]/ then
37
+ c
38
+ elsif c == "_" then
39
+ "__"
40
+ else
41
+ "_" + c.ord.to_s
42
+ end
43
+ end.join
44
+ # First character: only letter is possible.
45
+ unless name[0] =~ /[a-z_]/ then
46
+ name = "_" + name
47
+ end
48
+ return name
49
+ end
50
+
51
+ @@hdrobj2c = {}
52
+
53
+ ## Generates a uniq name for an object.
54
+ def self.obj_name(obj)
55
+ id = obj.hierarchy.map! {|obj| obj.object_id}
56
+ oname = @@hdrobj2c[id]
57
+ unless oname then
58
+ oname = "_" << @@hdrobj2c.size.to_s(36)
59
+ @@hdrobj2c[id] = oname
60
+ end
61
+ return oname
62
+ end
63
+
64
+ ## Generates the name of a type.
65
+ def self.type_name(obj)
66
+ return "type#{Low2C.obj_name(obj)}"
67
+ end
68
+
69
+ ## Generates the name of a unit.
70
+ def self.unit_name(obj)
71
+ return "#{obj.to_s.upcase}"
72
+ end
73
+ end
74
+
75
+
76
+ RCSim = RCSimCinterface
77
+
78
+
79
+
80
+ ## Starts the simulation for top system +top+.
81
+ # NOTE: +name+ is the name of the simulation and +vcd+ tells if
82
+ # the vcd generation is used and +outpath+ is the path where
83
+ # the faile is to save.
84
+ def self.rcsim(top,name,outpath,vcd)
85
+ RCSim.rcsim_main(top.rcsystemT,outpath +"/" + name,vcd)
86
+ end
87
+
88
+
89
+
90
+ ## Extends the SystemT class for hybrid Ruby-C simulation.
91
+ class SystemT
92
+
93
+ attr_reader :rcsystemT # The access to the C version of the systemT
94
+
95
+ # Generate the C description of the systemT.
96
+ # +rcowner+ is the owner if any.
97
+ def to_rcsim(rcowner = nil)
98
+ # puts "to_rcsim for systemT=#{self.name}(#{self})"
99
+ # Create the systemT C object.
100
+ @rcsystemT = RCSim.rcsim_make_systemT(self.name.to_s)
101
+ # Sets the owner if any.
102
+ if rcowner then
103
+ RCSim.rcsim_set_owner(@rcsystemT,rcowner)
104
+ end
105
+ # Create and add the interface signals.
106
+ # self.each_input do |sig|
107
+ # rcsig = sig.to_rcsim(@rcsystemT)
108
+ # RCSim.rcsim_add_systemT_input(@rcsystemT,rcsig)
109
+ # end
110
+ RCSim.rcsim_add_systemT_inputs(@rcsystemT,
111
+ self.each_input.map do |sig|
112
+ sig.to_rcsim(@rcsystemT)
113
+ end)
114
+ # self.each_output do |sig|
115
+ # rcsig = sig.to_rcsim(@rcsystemT)
116
+ # RCSim.rcsim_add_systemT_output(@rcsystemT,rcsig)
117
+ # end
118
+ RCSim.rcsim_add_systemT_outputs(@rcsystemT,
119
+ self.each_output.map do |sig|
120
+ sig.to_rcsim(@rcsystemT)
121
+ end)
122
+ # self.each_inout do |sig|
123
+ # rcsig = sig.to_rcsim(@rcsystemT)
124
+ # RCSim.rcsim_add_systemT_inout(@rcsystemT,rcsig)
125
+ # end
126
+ RCSim.rcsim_add_systemT_inouts(@rcsystemT,
127
+ self.each_inout.map do |sig|
128
+ sig.to_rcsim(@rcsystemT)
129
+ end)
130
+ # Create and add the scope.
131
+ RCSim.rcsim_set_systemT_scope(@rcsystemT,
132
+ self.scope.to_rcsim(@rcsystemT))
133
+
134
+ # The owner is set afterward.
135
+ # # Set the owner if any.
136
+ # if @owner then
137
+ # if @owner.is_a?(SystemI) then
138
+ # puts "@owner=#{@owner} rcsystemI=#{@owner.rcsystemI.class}"
139
+ # RCSim.rcsim_set_owner(@rcsystemT,@owner.rcsystemI)
140
+ # end
141
+ # # The non-SystemI owner are discarded for the simulation.
142
+ # end
143
+
144
+ return @rcsystemT
145
+ end
146
+ end
147
+
148
+
149
+ ## Extends the Scope class for hybrid Ruby-C simulation.
150
+ class Scope
151
+
152
+ attr_reader :rcscope # The access to the C version of the scope.
153
+
154
+ # Generate the C description of the scope comming from object
155
+ # whose C description is +rcowner+
156
+ def to_rcsim(rcowner)
157
+ # puts "to_rcsim for scope=#{self}"
158
+ # Create the scope C object.
159
+ @rcscope = RCSim.rcsim_make_scope(self.name.to_s)
160
+
161
+ # Set the owner.
162
+ RCSim.rcsim_set_owner(@rcscope,rcowner)
163
+
164
+ # Of the scope is a son of a SystemT, the owner of the sub objects
165
+ # will be this systemT. Otherwise, it is the scope.
166
+ subowner = self.parent.is_a?(SystemT) ? rcowner : @rcscope
167
+
168
+ # Create and add the inner signals.
169
+ # self.each_inner do |sig|
170
+ # rcsig = sig.to_rcsim(@rcscope)
171
+ # RCSim.rcsim_add_scope_inner(@rcscope,rcsig)
172
+ # end
173
+ RCSim.rcsim_add_scope_inners(@rcscope,self.each_inner.map do |sig|
174
+ # sig.to_rcsim(@rcscope)
175
+ sig.to_rcsim(subowner)
176
+ end)
177
+
178
+ # Create and add the system instances.
179
+ # self.each_systemI do |sys|
180
+ # rcsys = sys.to_rcsim(@rcscope)
181
+ # RCSim.rcsim_add_scope_systemI(@rcscope,rcsys)
182
+ # end
183
+ RCSim.rcsim_add_scope_systemIs(@rcscope,
184
+ self.each_systemI.map do |sys|
185
+ # sys.to_rcsim(@rcscope)
186
+ sys.to_rcsim(subowner)
187
+ end)
188
+
189
+ # Create and add the behaviors.
190
+ # self.each_behavior do |beh|
191
+ # rcbeh = beh.to_rcsim(@rcscope)
192
+ # RCSim.rcsim_add_scope_behavior(@rcscope,rcbeh)
193
+ # end
194
+ RCSim.rcsim_add_scope_behaviors(@rcscope,
195
+ self.each_behavior.map do |beh|
196
+ # beh.to_rcsim(@rcscope)
197
+ beh.to_rcsim(subowner)
198
+ end)
199
+
200
+ # Create and add the connections.
201
+ # self.each_connection do |cnx|
202
+ # rccnx = cnx.to_rcsim(@rcscope)
203
+ # # Connections are actually converted to behaviors.
204
+ # RCSim.rcsim_add_scope_behavior(@rcscope,rccnx)
205
+ # end
206
+ RCSim.rcsim_add_scope_behaviors(@rcscope,
207
+ self.each_connection.map do |cxt|
208
+ # cxt.to_rcsim(@rcscope)
209
+ cxt.to_rcsim(subowner)
210
+ end)
211
+
212
+ # Create and add the codes.
213
+ # TODO!!
214
+
215
+ # Create and add the sub scopes.
216
+ # self.each_scope do |sub|
217
+ # rcsub = sub.to_rcsim(@rcscope)
218
+ # RCSim.rcsim_add_scope_scope(@rcscope,rcsub)
219
+ # end
220
+ RCSim.rcsim_add_scope_scopes(@rcscope,self.each_scope.map do |sub|
221
+ # sub.to_rcsim(@rcscope)
222
+ sub.to_rcsim(subowner)
223
+ end)
224
+
225
+ return @rcscope
226
+ end
227
+ end
228
+
229
+
230
+
231
+ ## Extends the Type class for hybrid Ruby-C simulation.
232
+ class Type
233
+
234
+ attr_reader :rctype # The access to the C version of the scope.
235
+
236
+ # Generate the C description of the type comming from object
237
+ # whose C description is +rcowner+.
238
+ # NOTE: +rcowner+ is not used here.
239
+ def to_rcsim
240
+ # Create the type C object.
241
+ if self.name == :bit || self.name == :unsigned then
242
+ @rctype = RCSim.rcsim_get_type_bit()
243
+ elsif self.name == :signed then
244
+ @rctype = RCSim.rcsim_get_type_signed()
245
+ else
246
+ raise "Unknown type: #{self.name}"
247
+ end
248
+ return @rctype
249
+ end
250
+ end
251
+
252
+ ## Extends the TypeDef class for hybrid Ruby-C simulation.
253
+ class TypeDef
254
+
255
+ # Generate the C description of the type.
256
+ def to_rcsim
257
+ # Create the type C object.
258
+ @rctype = self.def.to_rcsim
259
+ return @rctype
260
+ end
261
+ end
262
+
263
+ ## Extends the TypeVector class for hybrid Ruby-C simulation.
264
+ class TypeVector
265
+
266
+ # Generate the C description of the type.
267
+ def to_rcsim
268
+ # Create the type C object.
269
+ @rctype = RCSim.rcsim_get_type_vector(self.base.to_rcsim,self.size)
270
+ return @rctype
271
+ end
272
+ end
273
+
274
+ ## Extends the TypeTuple class for hybrid Ruby-C simulation.
275
+ class TypeTuple
276
+ # Add the possibility to change the direction.
277
+ def direction=(dir)
278
+ @direction = dir == :little ? :little : :big
279
+ end
280
+
281
+ # Generate the C description of the type.
282
+ def to_rcsim
283
+ # @rctype = self.to_vector.to_rcsim
284
+ @rctype = RCSim.rcsim_get_type_vector(Bit.to_rcsim,self.width)
285
+ return @rctype
286
+ end
287
+ end
288
+
289
+
290
+ ## Extends the TypeStruct class for hybrid Ruby-C simulation.
291
+ class TypeStruct
292
+ # Add the possibility to change the direction.
293
+ def direction=(dir)
294
+ @direction = dir == :little ? :little : :big
295
+ end
296
+
297
+ # Generate the C description of the type.
298
+ def to_rcsim
299
+ # @rctype = self.to_vector.to_rcsim
300
+ @rctype = RCSim.rcsim_get_type_vector(Bit.to_rcsim,self.width)
301
+ return @rctype
302
+ end
303
+ end
304
+
305
+
306
+ ## Module for extending the behavior classes for hybrid Ruby-C simulation.
307
+ module RCSimBehavior
308
+
309
+ attr_reader :rcbehavior
310
+
311
+ # Generate the C description of the behavior comming from object
312
+ # whose C description is +rcowner+
313
+ def to_rcsim(rcowner)
314
+ # puts "to_rcsim for behavior=#{self}"
315
+ # Process the sensitivity list.
316
+ # Is it a clocked behavior?
317
+ events = self.each_event.to_a
318
+ # puts "events=#{events.map {|ev| ev.ref.object.name }}"
319
+ if !self.is_a?(TimeBehavior) && events.empty? then
320
+ # No events, this is not a clock behavior.
321
+ # And it is not a time behavior neigther.
322
+ # Generate the events list from the right values.
323
+ # First get the references.
324
+ refs = self.block.each_node_deep.select do |node|
325
+ node.is_a?(RefObject) && !node.leftvalue? &&
326
+ !node.parent.is_a?(RefObject)
327
+ end.to_a
328
+ # puts "refs=#{refs}"
329
+ # Keep only one ref per signal.
330
+ refs.uniq! { |node| node.fullname }
331
+ # Remove the inner signals from the list.
332
+ self.block.each_inner do |inner|
333
+ refs.delete_if {|r| r.name == inner.name }
334
+ end
335
+ # Generate the event.
336
+ events = refs.map {|ref| Event.new(:anyedge,ref.clone) }
337
+ # Add them to the behavior for further processing.
338
+ events.each {|event| self.add_event(event) }
339
+ end
340
+
341
+ # Create the behavior C object.
342
+ # puts "make behavior with self.class=#{self.class}"
343
+ @rcbehavior = RCSim.rcsim_make_behavior(self.is_a?(TimeBehavior))
344
+
345
+ # Set the owner.
346
+ RCSim.rcsim_set_owner(@rcbehavior,rcowner)
347
+
348
+ # Create and add the events.
349
+ # self.each_event do |ev|
350
+ # RCSim.rcsim_add_behavior_event(@rcbehavior,ev.to_rcsim)
351
+ # end
352
+ RCSim.rcsim_add_behavior_events(@rcbehavior,
353
+ self.each_event.map do |ev|
354
+ # puts "adding event: #{ev.ref.object.name}(#{ev.type})"
355
+ ev.to_rcsim(@rcbehavior)
356
+ end)
357
+
358
+ # Create and add the block.
359
+ RCSim.rcsim_set_behavior_block(@rcbehavior,self.block.to_rcsim)
360
+
361
+ return @rcbehavior
362
+ end
363
+ end
364
+
365
+
366
+ ## Extends the Behavior class for hybrid Ruby-C simulation.
367
+ class Behavior
368
+ include RCSimBehavior
369
+ end
370
+
371
+ ## Extends the TimeBehavior class for hybrid Ruby-C simulation.
372
+ class TimeBehavior
373
+ include RCSimBehavior
374
+ end
375
+
376
+
377
+ ## Extends the Event class for hybrid Ruby-C simulation.
378
+ class Event
379
+
380
+ attr_reader :rcevent
381
+
382
+ # Generate the C description of the event comming from object
383
+ # whose C description is +rcowner+
384
+ def to_rcsim(rcowner)
385
+ # Create the event C object.
386
+ @rcevent = RCSim.rcsim_make_event(self.type,self.ref.to_rcsim)
387
+
388
+ # Set the owner.
389
+ RCSim.rcsim_set_owner(@rcevent,rcowner)
390
+
391
+ return @rcevent
392
+ end
393
+ end
394
+
395
+
396
+ ## Extends the SignalI class for hybrid Ruby-C simulation.
397
+ class SignalI
398
+
399
+ attr_reader :rcsignalI
400
+
401
+ # Generate the C description of the signal comming from object
402
+ # whose C description is +rcowner+
403
+ def to_rcsim(rcowner)
404
+ # Create the signal C object.
405
+ @rcsignalI = RCSim.rcsim_make_signal(self.name.to_s,
406
+ self.type.to_rcsim)
407
+ # puts "to_rcsim for signal=(#{self.name})#{self}, @rcsignalI=#{@rcsignalI}"
408
+
409
+ # Set the owner.
410
+ RCSim.rcsim_set_owner(@rcsignalI,rcowner)
411
+
412
+ # Set the initial value if any.
413
+ if self.value then
414
+ RCSim.rcsim_set_signal_value(@rcsignalI,self.value.to_rcsim)
415
+ end
416
+
417
+ return @rcsignalI
418
+ end
419
+ end
420
+
421
+
422
+ ## Extends the SignalC class for hybrid Ruby-C simulation.
423
+ class SignalC
424
+
425
+ attr_reader :rcsignalC
426
+
427
+ # Generate the C description of the signal comming from object
428
+ # whose C description is +rcowner+
429
+ def to_rcsim(rcowner)
430
+ # Create the signal C object.
431
+ @rcsignalC = RCSim.rcsim_make_signal(self.name.to_s,
432
+ self.type.to_rcsim)
433
+
434
+ # Set the owner.
435
+ RCSim.rcsim_set_owner(@rcsignalC,rcowner)
436
+
437
+ # Set the initial value.
438
+ RCSim.rcsim_set_signal_value(@rcsignalC,self.value.to_rcsim)
439
+
440
+ return @rcsignalC
441
+ end
442
+ end
443
+
444
+
445
+ ## Extends the SystemI class for hybrid Ruby-C simulation.
446
+ class SystemI
447
+
448
+ attr_reader :rcsystemI
449
+
450
+ # Generate the C description of the signal comming from object
451
+ # whose C description is +rcowner+
452
+ def to_rcsim(rcowner)
453
+ # puts "to_rcsim for systemI=#{self.name}(#{self})"
454
+ # Create the system instance C object.
455
+ @rcsystemI = RCSim.rcsim_make_systemI(self.name.to_s,
456
+ self.systemT.to_rcsim)
457
+ # # Set the owner of the systemT.
458
+ # RCSim.rcsim_set_owner(self.systemT.rcsystemT,@rcsystemI)
459
+ # Set the owner of the systemT as the same as the systemI since
460
+ # it is an Eigen system.
461
+ RCSim.rcsim_set_owner(self.systemT.rcsystemT,rcowner)
462
+
463
+ # Set the owner.
464
+ RCSim.rcsim_set_owner(@rcsystemI,rcowner)
465
+
466
+ # Add the alternate system types.
467
+ # self.each_systemT do |systemT|
468
+ # rcsys = systemT.to_rcsim(@rcsystemI)
469
+ # RCSim.rcsim_add_systemI_systemT(@rcsystemI,rcsys)
470
+ # end
471
+ RCSim.rcsim_add_systemI_systemTs(@rcsystemI,
472
+ self.each_systemT.select do |sys|
473
+ sys != self.systemT
474
+ end.map do |sys|
475
+ sys.to_rcsim(@rcsystemI)
476
+ end)
477
+
478
+ return @rcsystemI
479
+ end
480
+ end
481
+
482
+
483
+ ## Extends the Chunk class for hybrid Ruby-C simulation.
484
+ class Chunk
485
+ # TODO!!
486
+ end
487
+
488
+ ## Extends the Code class for hybrid Ruby-C simulation.
489
+ class Code
490
+ # TODO!!
491
+ end
492
+
493
+
494
+ ## Extends the Statement class for hybrid Ruby-C simulation.
495
+ class Statement
496
+
497
+ attr_reader :rcstatement
498
+
499
+ # Generate the C description of the statement.
500
+ def to_rcsim
501
+ raise "to_rcsim must be implemented in #{self.class}"
502
+ end
503
+ end
504
+
505
+
506
+ ## Extends the Transmit class for hybrid Ruby-C simulation.
507
+ class Transmit
508
+ attr_reader :rcstatement
509
+
510
+ # Generate the C description of the transmit.
511
+ def to_rcsim
512
+ # Create the transmit C object.
513
+ @rcstatement = RCSim.rcsim_make_transmit(self.left.to_rcsim,
514
+ self.right.to_rcsim)
515
+
516
+ return @rcstatement
517
+ end
518
+ end
519
+
520
+
521
+ ## Extends the Print class for hybrid Ruby-C simulation.
522
+ class Print
523
+ attr_reader :rcstatement
524
+
525
+ # Generate the C description of the print.
526
+ def to_rcsim
527
+ # Create the print C object.
528
+ @rcstatement = RCSim.rcsim_make_print()
529
+
530
+ # Adds the arguments.
531
+ # self.each_arg do |arg|
532
+ # RCSim.rcsim_add_print_arg(@rcstatement,arg.to_rcsim)
533
+ # end
534
+ RCSim.rcsim_add_print_args(@rcstatement,
535
+ self.each_arg.map(&:to_rcsim))
536
+
537
+ return @rcstatement
538
+ end
539
+ end
540
+
541
+
542
+ ## Extends the TimeTerminate class for hybrid Ruby-C simulation.
543
+ class TimeTerminate
544
+ attr_reader :rcstatement
545
+
546
+ # Generate the C description of the terminate.
547
+ def to_rcsim
548
+ # Create the terminate C object.
549
+ @rcstatement = RCSim.rcsim_make_timeTerminate()
550
+
551
+ return @rcstatement
552
+ end
553
+ end
554
+
555
+ ## Extends the Configure class for hybrid Ruby-C simulation.
556
+ class Configure
557
+ attr_reader :rcstatement
558
+ # TODO!!!
559
+ end
560
+
561
+
562
+ ## Extends the If class for hybrid Ruby-C simulation.
563
+ class If
564
+ attr_reader :rcstatement
565
+
566
+ # Generate the C description of the hardware if.
567
+ def to_rcsim
568
+ # Create the hardware if C object.
569
+ @rcstatement = RCSim.rcsim_make_hif(self.condition.to_rcsim,
570
+ self.yes.to_rcsim,
571
+ self.no ? self.no.to_rcsim : nil)
572
+
573
+ # Add the alternate ifs if any.
574
+ # self.each_noif do |cond,stmnt|
575
+ # RCSim.rcsim_add_hif_noif(@rcstatement,cond.to_rcsim,stmnt.to_rcsim)
576
+ # end
577
+ rcsim_conds = self.each_noif.map {|cond,stmnt| cond.to_rcsim }
578
+ rcsim_stmnts = self.each_noif.map {|cond,stmnt| stmnt.to_rcsim }
579
+ RCSim.rcsim_add_hif_noifs(@rcstatement,rcsim_conds,rcsim_stmnts)
580
+
581
+ return @rcstatement
582
+ end
583
+ end
584
+
585
+
586
+ ## Extends the When class for hybrid Ruby-C simulation.
587
+ class When
588
+ # Nothing to add.
589
+ end
590
+
591
+ ## Extends the Case class for hybrid Ruby-C simulation.
592
+ class Case
593
+ attr_reader :rcstatement
594
+
595
+ # Generate the C description of the hardware case.
596
+ def to_rcsim
597
+ # Create the hardware case C object.
598
+ @rcstatement = RCSim.rcsim_make_hcase(self.value.to_rcsim,
599
+ self.default ? self.default.to_rcsim : nil)
600
+
601
+ # Add the hardware whens.
602
+ # self.each_when do |wh|
603
+ # RCSim.rcsim_add_hcase_when(@rcstatement,
604
+ # wh.match.to_rcsim,wh.statement.to_rcsim)
605
+ # end
606
+ rcsim_matches = self.each_when.map {|wh| wh.match.to_rcsim }
607
+ rcsim_stmnts = self.each_when.map {|wh| wh.statement.to_rcsim }
608
+ RCSim.rcsim_add_hcase_whens(@rcstatement,rcsim_matches,rcsim_stmnts)
609
+
610
+ return @rcstatement
611
+ end
612
+ end
613
+
614
+
615
+ ## Extends the Delay class for hybrid Ruby-C simulation.
616
+ class Delay
617
+ # Nothing to do.
618
+ end
619
+
620
+ ## Extends the TimeWait class for hybrid Ruby-C simulation.
621
+ class TimeWait
622
+ attr_reader :rcstatement
623
+
624
+ # Generate the C description of the time wait.
625
+ def to_rcsim
626
+ # Create the time wait C object.
627
+ @rcstatement = RCSim.rcsim_make_timeWait(self.delay.unit,
628
+ self.delay.value.to_i)
629
+
630
+ return @rcstatement
631
+ end
632
+ end
633
+
634
+
635
+ ## Extends the TimeRepeat class for hybrid Ruby-C simulation.
636
+ class TimeRepeat
637
+ attr_reader :rcstatement
638
+ # TODO!!!
639
+ end
640
+
641
+
642
+ ## Module for extending the Block classes for hybrid Ruby-C simulation.
643
+ module RCSimBlock
644
+ attr_reader :rcstatement
645
+
646
+ # Generate the C description of the hardware case.
647
+ # +owner+ is a link to the C description of the owner behavior if any.
648
+ def to_rcsim(owner = nil)
649
+ # Create the block C object.
650
+ @rcstatement = RCSim.rcsim_make_block(self.mode)
651
+
652
+ # Sets the owner if any.
653
+ if owner then
654
+ RCSim.rcsim_set_block_owner(@rcstatement,owner)
655
+ end
656
+
657
+ # Add the inner signals.
658
+ # self.each_inner do |inner|
659
+ # RCSim.rcsim_add_block_inner(@rcstatement,inner.to_rcsim(@rcstatement))
660
+ # end
661
+ RCSim.rcsim_add_block_inners(@rcstatement,
662
+ self.each_inner.map do |sig|
663
+ sig.to_rcsim(@rcstatement)
664
+ end)
665
+
666
+ # Add the statements.
667
+ # self.each_statement do |stmnt|
668
+ # RCSim.rcsim_add_block_statement(@rcstatement,stmnt.to_rcsim)
669
+ # end
670
+ RCSim.rcsim_add_block_statements(@rcstatement,
671
+ self.each_statement.map do |stmnt|
672
+ stmnt.to_rcsim
673
+ end)
674
+
675
+ return @rcstatement
676
+ end
677
+ end
678
+
679
+ ## Extends the Block class for hybrid Ruby-C simulation.
680
+ class Block
681
+ include RCSimBlock
682
+ end
683
+
684
+ ## Extends the TimeBlock class for hybrid Ruby-C simulation.
685
+ class TimeBlock
686
+ include RCSimBlock
687
+ end
688
+
689
+
690
+ ## Extends the Connection class for hybrid Ruby-C simulation.
691
+ class Connection
692
+ attr_reader :rcbehavior
693
+
694
+ # Generate the C description of the connection.
695
+ # +rcowner+ is a link to the C description of the owner scope.
696
+ def to_rcsim(rcowner)
697
+ # puts "make behavior with self.class=#{self.class}"
698
+ # Create the connection C object, actually it is a behavior.
699
+ @rcbehavior = RCSim.rcsim_make_behavior(false)
700
+
701
+ # Set the owner.
702
+ RCSim.rcsim_set_owner(@rcbehavior,rcowner)
703
+
704
+ # Create and add the events.
705
+ rcevs = []
706
+ self.right.each_node_deep do |node|
707
+ if node.is_a?(RefObject) then
708
+ ev = RCSim.rcsim_make_event(:anyedge,node.to_rcsim)
709
+ RCSim.rcsim_set_owner(ev,@rcbehavior)
710
+ rcevs << ev
711
+ end
712
+ end
713
+ RCSim.rcsim_add_behavior_events(@rcbehavior,rcevs)
714
+
715
+ # Create and set the block.
716
+ rcblock = RCSim.rcsim_make_block(:par)
717
+ # RCSim.rcsim_add_block_statement(
718
+ # RCSim.rcsim_make_transmit(self.left.to_rcsim,
719
+ # self.right.to_rcsim))
720
+ # puts "self.left=#{self.left} self.right=#{self.right}"
721
+ RCSim.rcsim_add_block_statements(rcblock,
722
+ [RCSim.rcsim_make_transmit(self.left.to_rcsim, self.right.to_rcsim)])
723
+ RCSim.rcsim_set_behavior_block(@rcbehavior,rcblock)
724
+
725
+ return @rcbehavior
726
+ end
727
+ end
728
+
729
+
730
+ ## Extends the Expression class for hybrid Ruby-C simulation.
731
+ class Expression
732
+
733
+ # attr_reader :rcexpression
734
+
735
+ # Generate the C description of the expression.
736
+ def to_rcsim
737
+ raise "to_rcsim must be implemented in #{self.class}"
738
+ end
739
+ end
740
+
741
+
742
+ ## Extends the Value class for hybrid Ruby-C simulation.
743
+ class Value
744
+ # attr_reader :rcexpression
745
+
746
+ # Generate the C description of the value.
747
+ def to_rcsim
748
+ # Create the value C object.
749
+ if self.content.is_a?(::Integer) then
750
+ if self.content.bit_length <= 63 then
751
+ return RCSim.rcsim_make_value_numeric(self.type.to_rcsim,
752
+ self.content)
753
+ else
754
+ str = self.content.to_s(2)
755
+ if str[-1] == "-" then
756
+ str[-1] = "1"
757
+ elsif str[-1] == "1" then
758
+ str = "0" + str
759
+ end
760
+ return RCSim.rcsim_make_value_bitstring(self.type.to_rcsim,
761
+ str.reverse)
762
+ end
763
+ else
764
+ return RCSim.rcsim_make_value_bitstring(self.type.to_rcsim,
765
+ self.content.to_s.reverse)
766
+ end
767
+ end
768
+ end
769
+
770
+ ## Extends the StringE class for hybrid Ruby-C simulation.
771
+ class StringE
772
+
773
+ # Generate the C description of the value.
774
+ def to_rcsim
775
+ # Create the value C object.
776
+ return RCSim.rcsim_make_stringE(self.content);
777
+ end
778
+ end
779
+
780
+
781
+ ## Extends the Cast class for hybrid Ruby-C simulation.
782
+ class Cast
783
+ # attr_reader :rcexpression
784
+
785
+ # Generate the C description of the cast.
786
+ def to_rcsim
787
+ # puts "Cast to width=#{self.type.width} and child=#{self.child}"
788
+ # Shall we reverse when casting?
789
+ if self.type.direction != self.child.type.direction then
790
+ # Yes, reverse the direction of the child.
791
+ if self.child.type.respond_to?(:direction=) then
792
+ self.child.type.direction = self.type.direction
793
+ end
794
+ end
795
+ # Create the cast C object.
796
+ return RCSim.rcsim_make_cast(self.type.to_rcsim,self.child.to_rcsim)
797
+ end
798
+ end
799
+
800
+
801
+ ## Extends the Operation class for hybrid Ruby-C simulation.
802
+ class Operation
803
+ # Nothing to do.
804
+ end
805
+
806
+ ## Extends the Unary class for hybrid Ruby-C simulation.
807
+ class Unary
808
+ attr_reader :rcexpression
809
+
810
+ # Generate the C description of the unary operation.
811
+ def to_rcsim
812
+ # Create the unary C object.
813
+ return RCSim.rcsim_make_unary(self.type.to_rcsim,self.operator,
814
+ self.child.to_rcsim)
815
+ end
816
+ end
817
+
818
+ ## Extends the Binary class for hybrid Ruby-C simulation.
819
+ class Binary
820
+ # attr_reader :rcexpression
821
+
822
+ # Generate the C description of the binary operation.
823
+ def to_rcsim
824
+ # Create the binary C object.
825
+ return RCSim.rcsim_make_binary(self.type.to_rcsim,self.operator,
826
+ self.left.to_rcsim,
827
+ self.right.to_rcsim)
828
+ end
829
+ end
830
+
831
+
832
+ ## Extends the Select class for hybrid Ruby-C simulation.
833
+ class Select
834
+ # attr_reader :rcexpression
835
+
836
+ # Generate the C description of the select operation.
837
+ def to_rcsim
838
+ # Create the select C object.
839
+ rcexpression = RCSim.rcsim_make_select(self.type.to_rcsim,
840
+ self.select.to_rcsim)
841
+
842
+ # Add the choice expressions. */
843
+ # self.each_choice do |choice|
844
+ # rcsim_add_select_choice(rcexpression,choice.to_rcsim)
845
+ # end
846
+ RCSim.rcsim_add_select_choices(rcexpression,
847
+ self.each_choice.map(&:to_rcsim))
848
+
849
+ return rcexpression
850
+ end
851
+ end
852
+
853
+
854
+ ## Extends the Concat class for hybrid Ruby-C simulation.
855
+ class Concat
856
+ # attr_reader :rcexpression
857
+
858
+ # Generate the C description of the concat operation.
859
+ def to_rcsim
860
+ # Create the concat C object.
861
+ rcexpression = RCSim.rcsim_make_concat(self.type.to_rcsim,
862
+ self.type.direction)
863
+
864
+ # Add the concatenated expressions. */
865
+ # self.each_expression do |expr|
866
+ # RCSim.rcsim_add_concat_expression(rcexpression,expr.to_rcsim)
867
+ # end
868
+ RCSim.rcsim_add_concat_expressions(rcexpression,
869
+ self.each_expression.map(&:to_rcsim))
870
+
871
+ return rcexpression
872
+ end
873
+ end
874
+
875
+
876
+
877
+ ## Extends the Ref class for hybrid Ruby-C simulation.
878
+ class Ref
879
+ # attr_reader :rcref
880
+ # alias_method :rcexpression, :rcref
881
+
882
+ # Generate the C description of the reference.
883
+ def to_rcsim
884
+ raise "to_rcsim must be implemented in #{self.class}"
885
+ end
886
+ end
887
+
888
+
889
+ ## Extends the RefConcat class for hybrid Ruby-C simulation.
890
+ class RefConcat
891
+ # attr_reader :rcref
892
+ # alias_method :rcexpression, :rcref
893
+
894
+ # Generate the C description of the reference concat.
895
+ def to_rcsim
896
+ # Create the reference concat C object.
897
+ rcref = RCSim.rcsim_make_refConcat(self.type.to_rcsim,
898
+ self.type.direction)
899
+
900
+ # Add the concatenated expressions. */
901
+ # self.each_ref do |ref|
902
+ # RCSim.rcsim_add_refConcat_ref(rcref,ref.to_rcsim)
903
+ # end
904
+ RCSim.rcsim_add_refConcat_refs(rcref,self.each_ref(&:to_rcsim))
905
+
906
+ return rcref
907
+ end
908
+ end
909
+
910
+
911
+ ## Extends the RefIndex class for hybrid Ruby-C simulation.
912
+ class RefIndex
913
+ # attr_reader :rcref
914
+ # alias_method :rcexpression, :rcref
915
+
916
+ # Generate the C description of the reference index.
917
+ def to_rcsim
918
+ # Create the reference index C object.
919
+ return RCSim.rcsim_make_refIndex(self.type.to_rcsim,
920
+ self.index.to_rcsim,self.ref.to_rcsim)
921
+ end
922
+ end
923
+
924
+
925
+ ## Extends the RefRange class for hybrid Ruby-C simulation.
926
+ class RefRange
927
+ # attr_reader :rcref
928
+ # alias_method :rcexpression, :rcref
929
+
930
+ # Generate the C description of the reference range.
931
+ def to_rcsim
932
+ # Create the reference range C object.
933
+ return RCSim.rcsim_make_refRange(self.type.to_rcsim,
934
+ self.range.first.to_rcsim,
935
+ self.range.last.to_rcsim,
936
+ self.ref.to_rcsim)
937
+ end
938
+ end
939
+
940
+
941
+ ## Extends the RefName class for hybrid Ruby-C simulation.
942
+ class RefName
943
+ # Should not be used with rcsim.
944
+ end
945
+
946
+
947
+ ## Extends the RefThis class for hybrid Ruby-C simulation.
948
+ class RefThis
949
+ # attr_reader :rcref
950
+ # alias_method :rcexpression, :rcref
951
+
952
+ # Generate the C description of the reference range.
953
+ def to_rcsim
954
+ return nil
955
+ end
956
+ end
957
+
958
+
959
+ ## Extends the RefObject class for hybrid Ruby-C simulation.
960
+ class RefObject
961
+ # attr_reader :rcref
962
+ # alias_method :rcexpression, :rcref
963
+
964
+ # Generate the C description of the reference object.
965
+ def to_rcsim
966
+ # puts "object=#{self.object.name}(#{self.object})"
967
+ if self.object.is_a?(SignalI)
968
+ return self.object.rcsignalI
969
+ elsif self.object.is_a?(SignalC)
970
+ return self.object.rcsignalC
971
+ else
972
+ raise "Invalid object: #{self.object}"
973
+ end
974
+ end
975
+ end
976
+
977
+
978
+ end