Check-in [592020ed7a]

Many hyperlinks are disabled.
Use anonymous login to enable hyperlinks.

Overview
Comment:Use the lexical-name algorithm for 'altered' for now. May change to value-driven later.
Timelines: family | ancestors | descendants | both | notworking | kbk-pre
Files: files | file ages | folders
SHA3-256: 592020ed7ac1c82cd2e093c83f1aa18b76b2ec3afade5c1902603ee5d5a25815
User & Date: kbk 2018-11-10 22:17:42.856
Context
2018-11-11
22:34
Add bitwise Boolean operations to constant folding. Modify partial redundancy elimination to use bit vectors for dataflow calculations and debug the dataflow equations. check-in: 71a4e793a1 user: kbk tags: kbk-pre
2018-11-10
22:17
Use the lexical-name algorithm for 'altered' for now. May change to value-driven later. check-in: 592020ed7a user: kbk tags: notworking, kbk-pre
19:10
Better copy prop exposes more opportunities for constant folding. check-in: edb0c23738 user: kbk tags: kbk-pre
Changes
Unified Diff Ignore Whitespace Patch
Changes to demos/perftest/tester.tcl.
1777
1778
1779
1780
1781
1782
1783
1784
1785
1786
1787
1788
1789
1790
1791
    }

}

proc cse {x a} {
    set s 0
    for {set i 0} {$i < $a} {incr i} {
	if {$i % 2 == 0} {
	    incr s [expr {2*$x + 1}]
	} else {
	    incr s [expr {2*$x + 2}]
	}
    }
    return $s
}







|







1777
1778
1779
1780
1781
1782
1783
1784
1785
1786
1787
1788
1789
1790
1791
    }

}

proc cse {x a} {
    set s 0
    for {set i 0} {$i < $a} {incr i} {
	if {($i & 1) == 0} {
	    incr s [expr {2*$x + 1}]
	} else {
	    incr s [expr {2*$x + 2}]
	}
    }
    return $s
}
Changes to quadcode/pre.tcl.
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
	    puts "    AVIN =  $inset"
	    puts "    AVOUT = $outset"
	}
    }

    # Find sets of expressions altered within each block

    set altered [my pre_altered $VN $AVIN $AVOUT]
    my debug-pre {
	puts "Altered expressions"
	set b -1
	foreach al $altered {
	    incr b
	    puts "  Block #$b: [dict keys $al]"
	}







|







126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
	    puts "    AVIN =  $inset"
	    puts "    AVOUT = $outset"
	}
    }

    # Find sets of expressions altered within each block

    set altered [my pre_altered $VN]
    my debug-pre {
	puts "Altered expressions"
	set b -1
	foreach al $altered {
	    incr b
	    puts "  Block #$b: [dict keys $al]"
	}
184
185
186
187
188
189
190
191
























192
193
194
195
196
197
198
    }

    # Compute LATER, which is an indication that an expression
    # may be moved later than an edge (LATER) or the start of
    # a block (LATERIN)

    lassign [my pre_later $antloc $EARLIEST] LATERIN LATER
    
























    return 0

}

# quadcode::transformer method pre_gvn --
#
#	Calculates a Global Value Numbering for values in a quadcode







|
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>







184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
    }

    # Compute LATER, which is an indication that an expression
    # may be moved later than an edge (LATER) or the start of
    # a block (LATERIN)

    lassign [my pre_later $antloc $EARLIEST] LATERIN LATER

    # Report on insertion and deletion points

    dict for {edge exprs} $LATER {
	lassign $edge from to
	dict for {e -} $exprs {
	    if {![dict exists [lindex $LATERIN $to] $e]} {
		puts "Insert $e on the flowgraph edge from $from to $to"
	    }
	}
    }

    set b -1
    foreach exprs $antloc laters $LATERIN {
	incr b
	if {$b == 0} continue
	puts "Block $b: ANTLOC = [dict keys $exprs]"
	puts "Block $b: LATERIN = [dict keys $laters]"
	dict for {e -} $exprs {
	    if {![dict exists $laters $e]} {
		puts "Remove $e from block $b"
	    }
	}
    }

    return 0

}

# quadcode::transformer method pre_gvn --
#
#	Calculates a Global Value Numbering for values in a quadcode
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528

529

530




531
532






533





534


































535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555

556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585

    return [list $AVIN $AVOUT]
    
}

# quadcode::transformer method pre_altered --
#
#	Computes the expressions altered in each block of the quadcode
#	sequence.
#
# Parameters:
#	VN - Dictionary that maps quadcode variable names to exemplars
#	     of their congruence classes.
#	AVIN - List of dictionaries. List indices are basic block numbers,
#	       dictionary keys are exemplars of values available on input
#	       to the basic block, dictionary values are immaterial.
#	AVOUT - List of dictionaries. List indices are basic block numbers,
#	        dictionary keys are exemplars of values available on output
#	        from the basic block, dictionary values are immaterial.
#
# Results:
#	Returns a list of dictionaries. List indices are basic block
#	numbers. Dictionary keys are exemplars of values altered in the
#	block. Dictionary values are immaterial.
#
# Algorithm is in Figure 7.1 on page 75 of [Simpson].
#

# FIXME: THIS IS WRONG:  We need to maintain dependencies per expression...

#        so we need a data structure that maintains the operands of




#	 all expressions in the program.







oo::define quadcode::transformer method pre_altered {VN AVIN AVOUT} {








































    set ALTERED {}

    # Walk through the basic blocks

    set b -1
    foreach bb $bbcontent avin $AVIN avout $AVOUT {
	incr b

	# Initially, altered_b is AVOUT_b - AVIN_b

	set altered $avin
	dict for {val -} $avout {
	    dict unset altered $val
	}

	# Walk through the quadcode instructions in a block

	set pc -1
	foreach q $bb {
	    incr pc
	    set arglist [lassign $q opcode result]

	    if {![dict exists $VN $result]} continue
	    set e [dict get $VN $result]

	    # Walk through the operands of an expression
	    foreach arg $arglist {
		if {![dict exists $VN $arg]} continue
		set o [dict get $VN $arg]

		# If an operand is in the altered set, add the
		# result to the altered set
		if {[dict exists $altered $o]} {
		    dict set altered $e {}
		}
	    }
	}

	my debug-pre {
	    puts "Altered in block #$b: $altered"
	}

	lappend ALTERED $altered
    }

    return $ALTERED
}

# quadcode::transformer method pre_antloc --
#
#	For each basic block in the program, compute the set of locally
#	anticipable expressions, that is, ones that can be moved ahead of







|
|


|
<
<
|
<
<
<
<


|
|
|

|
|
>
|
>
|
>
>
>
>
|

>
>
>
>
>
>
|
>
>
>
>
>

>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>


|
<

|


<
<
|
<
<
<
<
<
<



|
>

|
<
<
<
|
|
<
<
<
<
|
|
|
<
<
<
<
<
<


<







526
527
528
529
530
531
532
533
534
535
536
537


538




539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606

607
608
609
610


611






612
613
614
615
616
617
618



619
620




621
622
623






624
625

626
627
628
629
630
631
632

    return [list $AVIN $AVOUT]
    
}

# quadcode::transformer method pre_altered --
#
#	For each basic block in the program, compute the set of values
#	that are altered by fixed values in the block
#
# Parameters:
#	VN - Dictionary whose keys are quadcode values and whose values


#	     are exemplars of the corresponding expressions.




#
# Results:
#	Returns a list indexed by basic block number. The list values
#	are dictionaries whose keys are the exemplars of altered values
#	and whose values are immaterial
#
# This is the algorithm of Figure 7.2 on page 75 of [Simpson]

oo::define quadcode::transformer method pre_altered {VN} {

    variable ::quadcode::gvn_eliminable

    set S {}
    set D {}
    set isFixed {}

    # Walk through expressions in bottom-up order

    set b -1
    foreach bb $bbcontent {
	incr b
	set pc -1
	foreach q $bb {
	    incr pc

	    set argl [lassign $q opcode result]
	    if {![dict exists $VN $result]} continue
	    set e [dict get $VN $result]
	    if {[dict exists S $e]} continue
	    dict set S $e {}

	    # Keep track of which operands are fixed
	    if {![dict exists $gvn_eliminable $opcode]} {
		dict set isFixed $e {}
	    }

	    # Walk through operands of the expression

	    foreach a $argl {
		puts "expression has arg $a"
		if {![dict exists $VN $a]} continue
		set o [dict get $VN $a]
		puts "$e depends on $a => $o"

		# Set the dependencies of the result e to include
		# the operand o and its dependencies

		dict set S $e $o {}
		# If we haven't seen the operand, and this is a phi,
		# quit here. 
		if {![dict exists $S $o] && $opcode eq "phi"} continue
		dict for {ss -} [dict get $S $o] {
		    dict set S $e $ss {}
		}
	    }

	    # Set the dependents of fixed values 
	    
	    dict for {f -} [dict get $S $e] {
		if {![dict exists $isFixed $f]} continue
		dict set D $f $e {}
	    }
	}
    }

    set ALTERED {}

    # Walk through basic blocks

    set b -1
    foreach bb $bbcontent {
	incr b



	set altered {}






	set pc -1
	foreach q $bb {
	    incr pc
	    lassign $q opcode result
	    if {[dict exists $gvn_eliminable $opcode]} continue
	    if {![dict exists $VN $result]} continue
	    set x [dict get $VN $result]



	    if {![dict exists $D $x]} continue
	    dict for {v -} [dict get $D $x] {




		dict set altered $v {}
	    }
	}






	lappend ALTERED $altered
    }

    return $ALTERED
}

# quadcode::transformer method pre_antloc --
#
#	For each basic block in the program, compute the set of locally
#	anticipable expressions, that is, ones that can be moved ahead of