HDLRuby 3.7.9 → 3.8.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.
@@ -13,9 +13,11 @@ module HDLRuby::High::Std
13
13
  # the to_a method.
14
14
  module HEnumerable
15
15
 
16
- # Iterator on each element.
17
- def heach(&ruby_block)
18
- return self.to_a.each(&ruby_block)
16
+ # Convert to an array.
17
+ def h_to_a
18
+ res = []
19
+ self.heach {|e| res << e }
20
+ return res
19
21
  end
20
22
 
21
23
  # Iterator on each of the elements in range +rng+.
@@ -78,7 +80,8 @@ module HDLRuby::High::Std
78
80
 
79
81
  # Returns an HEnumerator generated from current enumerable and +arg+
80
82
  def hchain(arg)
81
- return self.heach + arg
83
+ # return self.heach + arg
84
+ return self.hto_a + arg.hto_a
82
85
  end
83
86
 
84
87
  # HW implementation of the Ruby chunk.
@@ -101,7 +104,9 @@ module HDLRuby::High::Std
101
104
  return HEnumeratorWrapper.new(self,:hmap)
102
105
  end
103
106
  # A block given? Create the result HEnumerable (a Ruby array).
104
- return self.heach.map(&ruby_block)
107
+ res = []
108
+ self.heach { |e| res << ruby_block.call(e) }
109
+ return res
105
110
  end
106
111
 
107
112
  # HW implementation of the Ruby flat_map.
@@ -111,7 +116,8 @@ module HDLRuby::High::Std
111
116
  return HEnumeratorWrapper.new(self,:hmap)
112
117
  end
113
118
  # A block given? Create the result HEnumerable (a Ruby array).
114
- return self.heach.flat_map(&ruby_block)
119
+ # return self.heach.flat_map(&ruby_block)
120
+ return self.hto_a.flat_map(&ruby_block)
115
121
  end
116
122
 
117
123
  # HW implementation of the Ruby compact.
@@ -160,7 +166,7 @@ module HDLRuby::High::Std
160
166
  return ifnone.call
161
167
  end
162
168
  # Convert to an array.
163
- ar = self.to_a
169
+ ar = self.hto_a
164
170
  # Use the ruby block in parallel.
165
171
  comp = ar.map { |elem| ruby_block.call(elem) }
166
172
  # Generate the look up circuit.
@@ -173,7 +179,15 @@ module HDLRuby::High::Std
173
179
 
174
180
  # HW implementation of the Ruby drop.
175
181
  def hdrop(n)
176
- return self.heach.drop(n)
182
+ # return self.heach.drop(n)
183
+ res = []
184
+ size = self.hsize
185
+ self.heach do |e|
186
+ # break if n == size
187
+ n += 1
188
+ res << e if n < size
189
+ end
190
+ return res
177
191
  end
178
192
 
179
193
  # HW implementation of the Ruby drop_while.
@@ -187,7 +201,8 @@ module HDLRuby::High::Std
187
201
  if !ruby_block then
188
202
  return HEnumeratorWrapper.new(self,:heach_cons,n)
189
203
  end
190
- return self.heach.each_cons(n,&ruby_block)
204
+ # return self.heach.each_cons(n,&ruby_block)
205
+ return self.hto_a.each_cons(n,&ruby_block)
191
206
  end
192
207
 
193
208
  # HW implementation of the Ruby each_entry.
@@ -202,7 +217,8 @@ module HDLRuby::High::Std
202
217
  if !ruby_block then
203
218
  return HEnumeratorWrapper.new(self,:heach_slice,n)
204
219
  end
205
- return self.heach.each_slice(n,&ruby_block)
220
+ # return self.heach.each_slice(n,&ruby_block)
221
+ return self.hto_a.each_slice(n,&ruby_block)
206
222
  end
207
223
 
208
224
  # HW implementation of the Ruby each_with_index.
@@ -212,7 +228,12 @@ module HDLRuby::High::Std
212
228
  if !ruby_block then
213
229
  return HEnumeratorWrapper.new(self,:heach_with_index)
214
230
  end
215
- self.heach.each_with_index(*args,&ruby_block)
231
+ # self.heach.each_with_index(*args,&ruby_block)
232
+ idx = 0
233
+ self.heach do |e|
234
+ ruby_block.call(*args,e,idx)
235
+ idx += 1
236
+ end
216
237
  end
217
238
 
218
239
  # HW implementation of the Ruby each_with_object.
@@ -222,12 +243,19 @@ module HDLRuby::High::Std
222
243
  if !ruby_block then
223
244
  return HEnumeratorWrapper.new(self,:heach_with_object)
224
245
  end
225
- self.heach.with_object(obj,&ruby_block)
246
+ # self.heach.with_object(obj,&ruby_block)
247
+ self.heach { |e| ruby_block.call(e,obj,&ruby_block) }
226
248
  end
227
249
 
228
- # HW implementation of the Ruby to_a.
250
+ # # HW implementation of the Ruby to_a.
251
+ # def hto_a
252
+ # return self.heach.to_a
253
+ # end
254
+
229
255
  def hto_a
230
- return self.heach.to_a
256
+ res = []
257
+ self.heach { |e| res << e }
258
+ return res
231
259
  end
232
260
 
233
261
  # HW implementation of the Ruby select.
@@ -249,7 +277,7 @@ module HDLRuby::High::Std
249
277
  # If there is an objet, look for it.
250
278
  ruby_block = proc { |e| e == obj } if obj
251
279
  # Convert to an array.
252
- ar = self.to_a
280
+ ar = self.hto_a
253
281
  size =ar.size
254
282
  # Use the ruby block in parallel.
255
283
  comp = self.hmap { |elem| ruby_block.call(elem) }
@@ -263,7 +291,14 @@ module HDLRuby::High::Std
263
291
 
264
292
  # HW implementation of the Ruby first.
265
293
  def hfirst(n=1)
266
- return self.heach.first(n)
294
+ # return self.heach.first(n)
295
+ res = []
296
+ self.heach do |e|
297
+ # break if n == 0
298
+ res << e if n > 0
299
+ n -= 1
300
+ end
301
+ return res
267
302
  end
268
303
 
269
304
  # HW implementation of the Ruby grep.
@@ -290,15 +325,36 @@ module HDLRuby::High::Std
290
325
  end
291
326
 
292
327
  # HW implementation of the Ruby inject.
293
- def hinject(*args,&ruby_block)
294
- return self.heach.inject(*args,&ruby_block)
328
+ def hinject(*args, &ruby_block)
329
+ # return self.heach.inject(*args,&ruby_block)
330
+ # return self.hto_a.inject(*args,&ruby_block)
331
+ if ruby_block then
332
+ # Case when a block is given.
333
+ res = args[0]
334
+ self.heach do |e|
335
+ res = res ? ruby_block.call(res,e) : e
336
+ end
337
+ else
338
+ # Case when a symbol is given.
339
+ sym, res = args[0], args[1]
340
+ self.heach do |e|
341
+ res = res ? res.send(sym,e) : e
342
+ end
343
+ end
344
+ return res
295
345
  end
296
346
 
297
347
  alias_method :hreduce, :hinject
298
348
 
349
+ # Specific to HDLRuby: inject with no default value through the call
350
+ # operator.
351
+ def call(*args, &ruby_block)
352
+ return self.hinject(*args,&ruby_block)
353
+ end
354
+
299
355
  # HW implementation of the Ruby lazy.
300
356
  # NOTE: to do, or may be not.
301
- def hlazy(*args,&ruby_block)
357
+ def hlazy(*args, &ruby_block)
302
358
  raise "hlazy is not supported yet."
303
359
  end
304
360
 
@@ -319,30 +375,11 @@ module HDLRuby::High::Std
319
375
  # The 2-value max unit.
320
376
  max2 = proc {|a,b| HDLRuby::High.top_user.mux(ruby_block.call(a,b),b,a) }
321
377
  # The single max hearch.
322
- m = self.reduce(&max2)
378
+ m = self.hreduce(&max2)
323
379
  res = [m]
324
380
  if n > 1 then
325
381
  raise "hmax not supported for more than one max element."
326
382
  end
327
- # # The other max hearch.
328
- # ar = self.to_a
329
- # sign = self.type.signed?
330
- # (n-1).times do
331
- # # Exclude the previous max.
332
- # ar = ar.map do |a|
333
- # if sign then
334
- # HDLRuby::High.top_user.mux(a == m, a, HDLRuby::High.cur_system.send("_b1#{"0" * (a.type.width-1)}"))
335
- # else
336
- # HDLRuby::High.top_user.mux(a == m, a, HDLRuby::High.cur_system.send("_b0#{"0" * (a.type.width-1)}"))
337
- # end
338
- # end
339
- # puts "#2 ar.size=#{ar.size}"
340
- # m = ar.reduce(&max2)
341
- # puts "#3"
342
- # res << m
343
- # puts "#4"
344
- # end
345
- # puts "#5"
346
383
  if scalar then
347
384
  # Scalar result case.
348
385
  return m
@@ -381,7 +418,7 @@ module HDLRuby::High::Std
381
418
  # The 2-value max unit.
382
419
  min2 = proc {|a,b| HDLRuby::High.top_user.mux(ruby_block.call(a,b),a,b) }
383
420
  # The single max hearch.
384
- m = self.reduce(&min2)
421
+ m = self.hreduce(&min2)
385
422
  res = [m]
386
423
  if n > 1 then
387
424
  raise "hmin not supported for more than one max element."
@@ -575,6 +612,13 @@ module HDLRuby::High::Std
575
612
  # The default comparator.
576
613
  ruby_block = proc { |a,b| a > b }
577
614
  end
615
+ # Create a namespace.
616
+ base_block = ruby_block
617
+ ruby_block = proc do |*args|
618
+ HDLRuby::High.top_user.sub do
619
+ base_block.call(*args)
620
+ end
621
+ end
578
622
  # Generate the compare and swap of two elements.
579
623
  compswap = proc do |a,b|
580
624
  if b then
@@ -625,7 +669,7 @@ module HDLRuby::High::Std
625
669
  &ruby_block)
626
670
  # No block given? Generate a new wrapper enumerator for smin_by.
627
671
  if !ruby_block then
628
- return SEnumeratorWrapper.new(self,:hsort_by,n)
672
+ return HEnumeratorWrapper.new(self,:hsort_by,n)
629
673
  end
630
674
  # A block is given, use smin with a proc that applies ruby_block
631
675
  # before comparing.
@@ -707,27 +751,9 @@ module HDLRuby::High::Std
707
751
  end
708
752
 
709
753
 
710
- # Describes hardware enumerator classes that allows to
711
- # generate HW iteration over HW or SW objects.
712
-
713
- # This is the abstract Enumerator class.
714
- class HEnumerator
715
- include HEnumerable
716
-
717
- # The methods that need to be defined.
718
- [:size, :type, :clone, :hto_a].each do |name|
719
- define_method(:name) do
720
- raise "Method '#{name}' must be defined for a valid sequencer enumerator."
721
- end
722
- end
723
-
724
- # Iterate on each element.
725
- def heach(&ruby_block)
726
- # No block given, returns self.
727
- return self unless ruby_block
728
- return self.hto_a.each(&ruby_block)
729
- end
730
-
754
+ # Module adding args in enumeration functionalities to object including
755
+ # the to_a method.
756
+ module HEnumArg
731
757
  # Iterator on each of the elements in range +rng+.
732
758
  # *NOTE*:
733
759
  # - Stop iteration when the end of the range is reached or when there
@@ -736,19 +762,18 @@ module HDLRuby::High::Std
736
762
  # creating a array is very expensive.
737
763
  def heach_range(rng,&ruby_block)
738
764
  # No block given, returns a new enumerator.
739
- return HEnumeratorWrapper.new(self,:heach_range) unless ruby_block
765
+ if !ruby_block then
766
+ return HEnumeratorWrapper.new(self,:heach_range)
767
+ end
740
768
  return self.to_a.each_range(rng,&ruby_block)
741
769
  end
742
770
 
743
- # Iterate on each element with arbitrary object +obj+.
744
- def heach_with_object(val,&ruby_block)
745
- return self.with_object(val,&ruby_block)
746
- end
747
-
748
771
  # Iterates with an index.
749
- def with_index(&ruby_block)
772
+ def hwith_index(&ruby_block)
750
773
  # No block given, returns a new enumerator.
751
- return HEnumeratorWrapper.new(self,:with_index) unless ruby_block
774
+ if !ruby_block then
775
+ return HEnumeratorWrapper.new(self,:hwith_index)
776
+ end
752
777
  # return self.hto_a.each_with_index(&ruby_block)
753
778
  i = 0
754
779
  return self.heach do |e|
@@ -758,15 +783,92 @@ module HDLRuby::High::Std
758
783
  end
759
784
  end
760
785
 
761
- # Return a new SEnumerator with an arbitrary arbitrary object +obj+.
762
- def with_object(obj)
786
+ # Return a new HEnumerator with an arbitrary arbitrary object +obj+.
787
+ def hwith_object(obj)
763
788
  # No block given, returns a new enumerator.
764
- return HEnumeratorWrapper.new(self,:with_object) unless ruby_block
789
+ if !ruby_block then
790
+ return HEnumeratorWrapper.new(self,:with_object)
791
+ end
765
792
  # return self.hto_a.each_with_object(&ruby_block)
766
793
  return self.heach do |e|
767
794
  ruby_block.call(e,obj)
768
795
  end
769
796
  end
797
+ end
798
+
799
+ # Describes hardware enumerator classes that allows to
800
+ # generate HW iteration over HW or SW objects.
801
+
802
+ # This is the abstract Enumerator class.
803
+ class HEnumerator
804
+ include Enumerable
805
+ include HEnumerable
806
+ include HEnumArg
807
+
808
+ # The methods that need to be defined.
809
+ [:size, :type, :clone, :hto_a].each do |name|
810
+ define_method(:name) do
811
+ raise "Method '#{name}' must be defined for a valid sequencer enumerator."
812
+ end
813
+ end
814
+
815
+ # Iterate on each element.
816
+ def heach(&ruby_block)
817
+ # No block given, returns self.
818
+ return self unless ruby_block
819
+ # Create a namespace.
820
+ base_block = ruby_block
821
+ ruby_block = proc do |*args|
822
+ HDLRuby::High.top_user.sub do
823
+ base_block.call(*args)
824
+ end
825
+ end
826
+ # Iterate.
827
+ if self.respond_to?(:[]) then
828
+ return self.size.times do |i|
829
+ ruby_block.call(self[i])
830
+ end
831
+ else
832
+ return self.hto_a.each(&ruby_block)
833
+ end
834
+ end
835
+
836
+ alias_method :each, :heach
837
+
838
+ # # Iterator on each of the elements in range +rng+.
839
+ # # *NOTE*:
840
+ # # - Stop iteration when the end of the range is reached or when there
841
+ # # are no elements left
842
+ # # - This is not a method from Ruby but one specific for hardware where
843
+ # # creating a array is very expensive.
844
+ # def heach_range(rng,&ruby_block)
845
+ # # No block given, returns a new enumerator.
846
+ # return HEnumeratorWrapper.new(self,:heach_range) unless ruby_block
847
+ # return self.to_a.each_range(rng,&ruby_block)
848
+ # end
849
+
850
+ # # Iterates with an index.
851
+ # def hwith_index(&ruby_block)
852
+ # # No block given, returns a new enumerator.
853
+ # return HEnumeratorWrapper.new(self,:hwith_index) unless ruby_block
854
+ # # return self.hto_a.each_with_index(&ruby_block)
855
+ # i = 0
856
+ # return self.heach do |e|
857
+ # res = ruby_block.call(e,i)
858
+ # i += 1
859
+ # res
860
+ # end
861
+ # end
862
+
863
+ # # Return a new HEnumerator with an arbitrary arbitrary object +obj+.
864
+ # def hwith_object(obj)
865
+ # # No block given, returns a new enumerator.
866
+ # return HEnumeratorWrapper.new(self,:with_object) unless ruby_block
867
+ # # return self.hto_a.each_with_object(&ruby_block)
868
+ # return self.heach do |e|
869
+ # ruby_block.call(e,obj)
870
+ # end
871
+ # end
770
872
 
771
873
  # Return a new HEnumerator going on iteration over enumerable +obj+
772
874
  def +(obj)
@@ -779,21 +881,22 @@ module HDLRuby::High::Std
779
881
  # other interation method over the first one.
780
882
  class HEnumeratorWrapper < HEnumerator
781
883
 
782
- # Create a new SEnumerator wrapper over +enum+ with +iter+ iteration
884
+ # Create a new HEnumerator wrapper over +enum+ with +iter+ iteration
783
885
  # method and +args+ argument.
784
- def initialize(enum,iter,*args)
785
- if enum.is_a?(HEnumerator) then
786
- @enumerator = enum.clone
787
- else
788
- @enumerator = enum.heach
789
- end
790
- @iterator = iter.to_sym
886
+ def initialize(enum,iter = nil,*args)
887
+ # if enum.is_a?(HEnumerator) then
888
+ # @enumerator = enum.clone
889
+ # else
890
+ # @enumerator = enum.heach
891
+ # end
892
+ @enumerator = enum
893
+ @iterator = iter ? iter.to_sym : nil
791
894
  @arguments = args
792
895
  end
793
896
 
794
897
  # The directly delegate methods.
795
898
  def size
796
- return @enumertor.size
899
+ return @enumerator.size
797
900
  end
798
901
  alias_method :hsize, :size
799
902
 
@@ -801,12 +904,6 @@ module HDLRuby::High::Std
801
904
  return @enumerator.type
802
905
  end
803
906
 
804
- def hto_a
805
- res = []
806
- self.heach { |e| res << e }
807
- return res
808
- end
809
-
810
907
  # Iterator on each of the elements in range +rng+.
811
908
  # *NOTE*:
812
909
  # - Stop iteration when the end of the range is reached or when there
@@ -827,29 +924,128 @@ module HDLRuby::High::Std
827
924
  # No block given, returns self.
828
925
  return self unless ruby_block
829
926
  # A block is given, iterate.
830
- return @enumerator.send(@iterator,*@arguments,&ruby_block)
927
+ if @iterator then
928
+ return @enumerator.send(@iterator,*@arguments,&ruby_block)
929
+ else
930
+ return @enumerator.heach(*@arguments,&ruby_block)
931
+ end
831
932
  end
832
933
  end
833
934
 
834
935
 
835
- module HDLRuby::High::HRef
836
- # Enhance the HRef module with sequencer iteration.
837
- # Properties of expressions are also required
838
- def self.included(klass)
839
- klass.class_eval do
840
- include HEnumerable
936
+ # module HDLRuby::High::HRef
937
+ module HDLRuby::High::HExpression
938
+ # # Enhance the HRef module with sequencer iteration.
939
+ # # Properties of expressions are also required
940
+ # def self.included(klass)
941
+ # klass.class_eval do
942
+ # include HEnumerable
943
+ # puts "current class=#{klass}"
944
+
945
+ # # Iterate over the elements.
946
+ # #
947
+ # # Returns an enumerator if no ruby block is given.
948
+ # def heach(&ruby_block)
949
+ # # No ruby block? Return an enumerator.
950
+ # # return to_enum(:each) unless ruby_block
951
+ # return self unless ruby_block
952
+ # # A block? Apply it on each element.
953
+ # self.type.range.heach do |i|
954
+ # yield(self[i])
955
+ # end
956
+ # end
957
+
958
+ # # Size.
959
+ # def hsize
960
+ # self.type.size
961
+ # end
962
+ # end
963
+ # end
964
+
965
+ # Iterate over the elements.
966
+ #
967
+ # Returns an enumerator if no ruby block is given.
968
+ def heach(&ruby_block)
969
+ # No ruby block? Return an enumerator.
970
+ # return self unless ruby_block
971
+ if !ruby_block then
972
+ return HEnumeratorWrapper.new(self)
973
+ end
974
+ # A block? Apply it on each element.
975
+ # Create a namespace.
976
+ base_block = ruby_block
977
+ ruby_block = proc do |*args|
978
+ HDLRuby::High.top_user.sub do
979
+ base_block.call(*args)
980
+ end
981
+ end
982
+ # Iterate.
983
+ self.type.range.heach do |i|
984
+ # yield(self[i])
985
+ ruby_block.call(self[i])
841
986
  end
842
987
  end
843
988
 
844
- # Convert to an array.
845
- alias_method :hto_a, :to_a
846
-
847
989
  # Size.
848
990
  def hsize
849
991
  self.type.size
850
992
  end
993
+
994
+ # Also adds the methods of HEnumerable.
995
+ HEnumerable.instance_methods.each do |meth|
996
+ define_method(meth,HEnumerable.instance_method(meth))
997
+ end
998
+
999
+ alias_method :to_a, :hto_a
1000
+ end
1001
+
1002
+
1003
+ module HDLRuby::High::HExpression
1004
+ # Enhance the HExpression module with sequencer iterations.
1005
+
1006
+ # HW times iteration.
1007
+ def htimes(&ruby_block)
1008
+ unless self.respond_to?(:to_i) then
1009
+ raise "htimes unsupported for such an expression: #{self}."
1010
+ end
1011
+ return self.to_i.htimes(&ruby_block)
1012
+ end
1013
+
1014
+ # HW upto iteration.
1015
+ def hupto(val,&ruby_block)
1016
+ unless self.respond_to?(:to_i) then
1017
+ raise "hupto unsupported for such an expression: #{self}."
1018
+ end
1019
+ return self.to_i.hupto(val,&ruby_block)
1020
+ end
1021
+
1022
+ # HW downto iteration.
1023
+ def sdownto(val,&ruby_block)
1024
+ unless self.respond_to?(:to_i) then
1025
+ raise "hupto unsupported for such an expression: #{self}."
1026
+ end
1027
+ return self.to_i.hdownto(val,&ruby_block)
1028
+ end
851
1029
  end
852
1030
 
1031
+ # class HDLRuby::High::Value
1032
+ # # Enhance the HRef module with sequencer iteration.
1033
+ # # Properties of expressions are also required
1034
+ # def self.included(klass)
1035
+ # klass.class_eval do
1036
+ # include HEnumerable
1037
+ # end
1038
+ # end
1039
+
1040
+ # # Convert to an array.
1041
+ # alias_method :hto_a, :to_a
1042
+
1043
+ # # Size.
1044
+ # def hsize
1045
+ # self.type.size
1046
+ # end
1047
+ # end
1048
+
853
1049
 
854
1050
  module ::Enumerable
855
1051
  # Enhance the Enumerable module with sequencer iteration.
@@ -869,23 +1065,59 @@ module HDLRuby::High::Std
869
1065
  end
870
1066
 
871
1067
 
1068
+ class ::Array
1069
+ # alias :heach :each
1070
+ # alias :hto_a :to_a
1071
+
1072
+ # Enhance the Array class with henumerable methods.
1073
+ include HEnumerable
1074
+
1075
+ # # Enhance the Array class with extra arguments in interation.
1076
+ # include HEnumArg
1077
+
1078
+ def heach(&ruby_block)
1079
+ if !ruby_block then
1080
+ return HEnumeratorWrapper.new(self)
1081
+ end
1082
+ # self.each { |e| HDLRuby::High.top_user.sub { ruby_block.call(e) } }
1083
+ self.each do |e|
1084
+ HDLRuby::High.top_user.sub do
1085
+ # HDLRuby::High.top_user.instance_exec(e,&ruby_block)
1086
+ ruby_block.call(e)
1087
+ end
1088
+ end
1089
+ end
1090
+ end
1091
+
1092
+
872
1093
  class ::Range
873
1094
  # Enhance the Range class with sequencer iteration.
874
1095
  include HEnumerable
875
1096
 
876
- # Conversion to array.
877
- def hto_a
878
- res = []
879
- self.heach { |i| res << i }
880
- return res
881
- end
1097
+ # # Enhance the Array class with extra arguments in interation.
1098
+ # include HEnumArg
1099
+
1100
+ # # Conversion to array.
1101
+ # def hto_a
1102
+ # res = []
1103
+ # self.heach { |i| res << i }
1104
+ # return res
1105
+ # end
882
1106
 
883
1107
  # Redefinition of heach to support also HDLRuby Values.
884
1108
  def heach(&ruby_block)
885
1109
  if self.first.is_a?(Value) or self.last.is_a?(Value) then
1110
+ # Value range case.
886
1111
  # No block given.
887
1112
  return self unless ruby_block
888
1113
  # A block is given, iterate on each element of the range
1114
+ # Create a namespace.
1115
+ base_block = ruby_block
1116
+ ruby_block = proc do |*args|
1117
+ HDLRuby::High.top_user.sub do
1118
+ base_block.call(*args)
1119
+ end
1120
+ end
889
1121
  # converted to values of the right type.
890
1122
  if first.is_a?(Value) then
891
1123
  typ = self.first.type
@@ -894,11 +1126,22 @@ module HDLRuby::High::Std
894
1126
  end
895
1127
  first = self.first.to_i
896
1128
  last = self.last.to_i
897
- (first..last).each do |i|
898
- ruby_block.call(i.as(typ))
1129
+ if first <= last then
1130
+ (first..last).each do |i|
1131
+ ruby_block.call(i.as(typ))
1132
+ end
1133
+ else
1134
+ (last..first).reverse_each do |i|
1135
+ ruby_block.call(i.as(typ))
1136
+ end
899
1137
  end
900
1138
  else
901
- return self.each(&ruby_block)
1139
+ # Other range cases.
1140
+ if self.first <= self.last then
1141
+ return self.each(&ruby_block)
1142
+ else
1143
+ return (self.last..self.first).reverse_each(&ruby_block)
1144
+ end
902
1145
  end
903
1146
  end
904
1147
 
@@ -2150,7 +2150,8 @@ module HDLRuby::High::Std
2150
2150
 
2151
2151
  # class HDLRuby::High::Value
2152
2152
  module HDLRuby::High::HExpression
2153
- # Enhance the Value class with sequencer iterations.
2153
+ # # Enhance the Value class with sequencer iterations.
2154
+ # Enhance the HExpression module with sequencer iterations.
2154
2155
 
2155
2156
  # HW times iteration.
2156
2157
  def stimes(&ruby_block)
@@ -1,3 +1,3 @@
1
1
  module HDLRuby
2
- VERSION = "3.7.9"
2
+ VERSION = "3.8.0"
3
3
  end