1+ namespace Benchmarks ;
2+
3+ public class Havlak : Benchmark
4+ {
5+ public override bool InnerBenchmarkLoop ( int innerIterations )
6+ {
7+ return VerifyResult ( ( new LoopTesterApp ( ) ) . main ( innerIterations , 50 , 10 /* was 100 */ , 10 , 5 ) , innerIterations ) ;
8+ }
9+
10+ public bool VerifyResult ( object result , int innerIterations )
11+ {
12+ int [ ] r = ( int [ ] ) result ;
13+
14+ if ( innerIterations == 15000 ) { return r [ 0 ] == 46602 && r [ 1 ] == 5213 ; }
15+ if ( innerIterations == 1500 ) { return r [ 0 ] == 6102 && r [ 1 ] == 5213 ; }
16+ if ( innerIterations == 150 ) { return r [ 0 ] == 2052 && r [ 1 ] == 5213 ; }
17+ if ( innerIterations == 15 ) { return r [ 0 ] == 1647 && r [ 1 ] == 5213 ; }
18+ if ( innerIterations == 1 ) { return r [ 0 ] == 1605 && r [ 1 ] == 5213 ; }
19+
20+ Console . WriteLine ( "No verification result for " + innerIterations + " found" ) ;
21+ Console . WriteLine ( "Result is: " + r [ 0 ] + ", " + r [ 1 ] ) ;
22+ return false ;
23+ }
24+
25+ public override object Execute ( )
26+ {
27+ throw new NotImplementedException ( ) ;
28+ }
29+
30+ public override bool VerifyResult ( object result )
31+ {
32+ throw new NotImplementedException ( ) ;
33+ }
34+
35+ sealed class BasicBlock : ICustomHash
36+ {
37+ public Vector < BasicBlock > InEdges { get ; }
38+ public Vector < BasicBlock > OutEdges { get ; }
39+
40+ private readonly int name ;
41+
42+ public BasicBlock ( int name )
43+ {
44+ this . name = name ;
45+ InEdges = new Vector < BasicBlock > ( ) ;
46+ OutEdges = new Vector < BasicBlock > ( ) ;
47+ }
48+
49+ public int GetNumPred ( ) { return InEdges . Size ( ) ; }
50+
51+ public void AddOutEdge ( BasicBlock to )
52+ {
53+ OutEdges . Append ( to ) ;
54+ }
55+
56+ public void AddInEdge ( BasicBlock from )
57+ {
58+ InEdges . Append ( from ) ;
59+ }
60+
61+ public int CustomHash ( )
62+ {
63+ return name ;
64+ }
65+ }
66+
67+ sealed class BasicBlockEdge
68+ {
69+ private readonly BasicBlock from ;
70+ private readonly BasicBlock to ;
71+
72+ BasicBlockEdge ( ControlFlowGraph cfg , int fromName , int toName )
73+ {
74+ from = cfg . CreateNode ( fromName ) ;
75+ to = cfg . CreateNode ( toName ) ;
76+
77+ from . AddOutEdge ( to ) ;
78+ to . AddInEdge ( from ) ;
79+
80+ cfg . AddEdge ( this ) ;
81+ }
82+ }
83+
84+ sealed class ControlFlowGraph
85+ {
86+ public Vector < BasicBlock > BasicBlocks { get ; }
87+
88+ private BasicBlock ? startNode ;
89+ private readonly Vector < BasicBlockEdge > edgeList ;
90+
91+ ControlFlowGraph ( )
92+ {
93+ BasicBlocks = new Vector < BasicBlock > ( ) ;
94+ edgeList = new Vector < BasicBlockEdge > ( ) ;
95+ }
96+
97+ public BasicBlock CreateNode ( int name )
98+ {
99+ BasicBlock node ;
100+
101+ if ( BasicBlocks . At ( name ) != null ) {
102+ node = BasicBlocks . At ( name ) ;
103+ } else {
104+ node = new BasicBlock ( name ) ;
105+ BasicBlocks . AtPut ( name , node ) ;
106+ }
107+
108+ if ( GetNumNodes ( ) == 1 )
109+ {
110+ startNode = node ;
111+ }
112+
113+ return node ;
114+ }
115+
116+ public void AddEdge ( BasicBlockEdge edge )
117+ {
118+ edgeList . Append ( edge ) ;
119+ }
120+
121+ public int GetNumNodes ( ) { return BasicBlocks . Size ( ) ; }
122+
123+ public BasicBlock ? GetStartBasicBlock ( ) { return startNode ; }
124+ }
125+
126+ sealed class LoopStructureGraph
127+ {
128+ private readonly SimpleLoop root ;
129+ private readonly Vector < SimpleLoop > loops ;
130+
131+ private int loopCounter ;
132+
133+ LoopStructureGraph ( )
134+ {
135+ loopCounter = 0 ;
136+ loops = new Vector < SimpleLoop > ( ) ;
137+ root = new SimpleLoop ( null , true ) ;
138+ root . NestingLevel = 0 ;
139+ root . Counter = loopCounter ;
140+ loopCounter += 1 ;
141+
142+ loops . Append ( root ) ;
143+ }
144+
145+ public SimpleLoop CreateLoop ( BasicBlock bb , bool isReducible )
146+ {
147+ SimpleLoop loop = new SimpleLoop ( bb , isReducible ) ;
148+ loop . Counter = loopCounter ;
149+ loopCounter += 1 ;
150+ loops . Append ( loop ) ;
151+ return loop ;
152+ }
153+
154+ public void CalculateNestingLevel ( )
155+ {
156+ // link up all 1st level loops to artificial root node.
157+ loops . ForEach ( liter => {
158+ if ( ! liter . IsRoot ) {
159+ if ( liter . Parent == null ) {
160+ liter . Parent = root ;
161+ }
162+ }
163+ } ) ;
164+
165+ // recursively traverse the tree and assign levels.
166+ CalculateNestingLevelRec ( root , 0 ) ;
167+ }
168+
169+ private void CalculateNestingLevelRec ( SimpleLoop loop , int depth )
170+ {
171+ loop . DepthLevel = depth ;
172+ loop . Children . ForEach ( liter => {
173+ CalculateNestingLevelRec ( liter , depth + 1 ) ;
174+
175+ loop . NestingLevel = Math . Max ( loop . NestingLevel , 1 + liter . NestingLevel ) ;
176+ } ) ;
177+ }
178+
179+ public int GetNumLoops ( ) { return loops . Size ( ) ; }
180+ }
181+
182+ sealed class SimpleLoop
183+ {
184+ private readonly IdentitySet < BasicBlock > basicBlocks ;
185+ private readonly IdentitySet < SimpleLoop > children ;
186+ private SimpleLoop ? parent ;
187+
188+ private readonly BasicBlock ? header ;
189+
190+ private readonly bool isReducible ;
191+
192+ private bool isRoot ;
193+ private int nestingLevel ;
194+
195+ private int counter ;
196+ private int depthLevel ;
197+
198+ SimpleLoop ( BasicBlock bb , bool isReducible )
199+ {
200+ this . isReducible = isReducible ;
201+ parent = null ;
202+ isRoot = false ;
203+ nestingLevel = 0 ;
204+ depthLevel = 0 ;
205+ basicBlocks = new IdentitySet < BasicBlock > ( ) ;
206+ children = new IdentitySet < SimpleLoop > ( ) ;
207+
208+ if ( bb != null ) {
209+ basicBlocks . Add ( bb ) ;
210+ }
211+
212+ header = bb ;
213+ }
214+ }
215+ }
0 commit comments