Determining Tree-Traversals Orientation using Feedback-Directed Analysis Stephen Curial, Kevin Andrusky and José Nelson Amaral University of Alberta Stephen.

Slides:



Advertisements
Similar presentations
1 Lecture 10 Intermediate Representations. 2 front end »produces an intermediate representation (IR) for the program. optimizer »transforms the code in.
Advertisements

S. Sudarshan Based partly on material from Fawzi Emad & Chau-Wen Tseng
Computer Science C++ High School Level By Guillermo Moreno.
1 A Two-Level Binary Expression ‘-’ ‘8’ ‘5’ treePtr INORDER TRAVERSAL : has value 3 PREORDER TRAVERSAL: POSTORDER TRAVERSAL: 8 5 -
1 Trees Tree nomenclature Implementation strategies Traversals –Depth-first –Breadth-first Implementing binary trees Reading: L&C 9.1 – 9.7.
Data Structures: Trees i206 Fall 2010 John Chuang Some slides adapted from Marti Hearst, Brian Hayes, or Glenn Brookshear.
Tree-Traversal Orientation Analysis Stephen Curial, Kevin Andrusky and José Nelson Amaral University of Alberta Stephen Curial, Kevin Andrusky and José.
A Context-Sensitive Pointer Analysis Phase in Open64 Compiler Tianwei Sheng, Wenguang Chen, Weimin Zheng Tsinghua University.
Liang, Introduction to Java Programming, Sixth Edition, (c) 2007 Pearson Education, Inc. All rights reserved L12 (Chapter 20) Lists, Stacks,
Chapter 12 C Data Structures Acknowledgment The notes are adapted from those provided by Deitel & Associates, Inc. and Pearson Education Inc.
Transforming Infix to Postfix
© Copyright 1992–2004 by Deitel & Associates, Inc. and Pearson Education Inc. All Rights Reserved. Chapter 12 – Data Structures Outline 12.1Introduction.
Preorder Traversal with a Stack Push the root onto the stack. While the stack is not empty n pop the stack and visit it.
Loop Induction Variable Canonicalization. Motivation Background: Open64 Compilation Scheme Loop Induction Variable Canonicalization Project Tracing and.
1 Foundations of Software Design Fall 2002 Marti Hearst Lecture 17: Binary Search Trees; Heaps.
More Trees COL 106 Amit Kumar and Shweta Agrawal Most slides courtesy : Douglas Wilhelm Harder, MMath, UWaterloo
C o n f i d e n t i a l Developed By Nitendra NextHome Subject Name: Data Structure Using C Title: Overview of Data Structure.
Nirmalya Roy School of Electrical Engineering and Computer Science Washington State University Cpt S 122 – Data Structures Data Structures Trees.
1 HEAPS & PRIORITY QUEUES Array and Tree implementations.
1 Chapter 18 Trees Objective To learn general trees and recursion binary trees and recursion tree traversal.
Chapter 12 Data Structure Associate Prof. Yuh-Shyan Chen Dept. of Computer Science and Information Engineering National Chung-Cheng University.
Reference: Vinu V Das, Principles of Data Structures using C and C++
Chapter 8 Data Abstractions Introduction to CS 1 st Semester, 2015 Sanghyun Park.
1 Trees Tree nomenclature Implementation strategies Traversals –Depth-first –Breadth-first Implementing binary search trees.
 2007 Pearson Education, Inc. All rights reserved C Data Structures.
ECE 103 Engineering Programming Chapter 61 Abstract Data Types Herbert G. Mayer, PSU CS Status 6/4/2014 Initial content copied verbatim from ECE 103 material.
Chapter 5 Binary Trees. Definitions and Properties A binary tree is made up of a finite set of elements called nodes A binary tree is made up of a finite.
Binary Trees Chapter Definition And Application Of Binary Trees Binary tree: a nonlinear linked list in which each node may point to 0, 1, or two.
1 Trees A tree is a data structure used to represent different kinds of data and help solve a number of algorithmic problems Game trees (i.e., chess ),
An experimental study of priority queues By Claus Jensen University of Copenhagen.
Starting at Binary Trees
Programming Practice 3 - Dynamic Data Structure
Chapter 16 – Data Structures and Recursion. Data Structures u Built-in –Array –struct u User developed –linked list –stack –queue –tree Lesson 16.1.
CMPUT Compiler Design and Optimization1 CMPUT680 - Fall 2006 Topic 3: Intermediate Representation in the ORC José Nelson Amaral
Data Flow Analysis for Software Prefetching Linked Data Structures in Java Brendon Cahoon Dept. of Computer Science University of Massachusetts Amherst,
CISC220 Fall 2009 James Atlas Dec 07: Final Exam Review.
Copyright © 2012 Pearson Education, Inc. Chapter 20: Binary Trees.
1 Trees General Trees  Nonrecursive definition: a tree consists of a set of nodes and a set of directed edges that connect pairs of nodes.
Copyright © 2015, 2012, 2009 Pearson Education, Inc., Publishing as Addison-Wesley All rights reserved. Chapter 20: Binary Trees.
CS 367 Introduction to Data Structures Lecture 8.
CMSC 202, Version 5/02 1 Trees. CMSC 202, Version 5/02 2 Tree Basics 1.A tree is a set of nodes. 2.A tree may be empty (i.e., contain no nodes). 3.If.
COSC 2P03 Week 21 Stacks – review A Last-In First-Out (LIFO) structure Basic Operations: –push : insert data item onto top of stack –pop : remove data.
Graph Traversal Text Weiss, § 9.6 Depth-First Search Think Stack Breadth-First Search Think Queue.
1 Trees General Trees  Nonrecursive definition: a tree consists of a set of nodes and a set of directed edges that connect pairs of nodes.
Copyright © 2009 Pearson Education, Inc. Publishing as Pearson Addison-Wesley Chapter 20: Binary Trees.
DS.T.1 Trees Chapter 4 Overview Tree Concepts Traversals Binary Trees Binary Search Trees AVL Trees Splay Trees B-Trees.
Trees Binary Trees Extended Binary Trees. Tree A Tree consist of Nodes connected by Edges. Node is represented by Circle Edges as Lines or Arrows A Tree.
Data Structure By Amee Trivedi.
Chapter 12 – Data Structures
Stacks – review A Last-In First-Out (LIFO) structure Basic Operations:
12 C Data Structures.
Experimental evaluation of Navigation piles
Dynamic Memory Allocation
Trees.
Hashing Exercises.
i206: Lecture 13: Recursion, continued Trees
Chapter 20: Binary Trees.
Stacks – review A Last-In First-Out (LIFO) structure Basic Operations:
Chapter 21: Binary Trees.
CS212: Data Structures and Algorithms
Trees 1: Theory, Models, Generic Heap Algorithms, Priority Queues
Review & Lab assignments
A Robust Data Structure
Data Structures – Week #5
Chapter 20: Binary Trees.
Trees.
Binary Search Tree.
(via graph coloring and spilling)
Topic 2b ISA Support for High-Level Languages
Binary Tree Iterators Tree Traversals: preorder, inorder, postorder
Presentation transcript:

Determining Tree-Traversals Orientation using Feedback-Directed Analysis Stephen Curial, Kevin Andrusky and José Nelson Amaral University of Alberta Stephen Curial, Kevin Andrusky and José Nelson Amaral University of Alberta

Why do we need to know the orientation of tree-traversals? High Memory Latency Memory Wall Compilers can improve spatial locality Using data transformations Must know the data access pattern before re- arranging High Memory Latency Memory Wall Compilers can improve spatial locality Using data transformations Must know the data access pattern before re- arranging Image Courtesy [1]

Overview We develop a compiler based analysis to determine the Tree-Traversal Orientation. Given a program as input, the compiler automatically inserts instrumentation into the the program to create an instrumented executable that will determine an orientation score for each tree in the program.

Overview We develop a compiler based analysis to determine the Tree-Traversal Orientation. Given a program as input, the compiler automatically inserts instrumentation into the the program to create an instrumented executable that will determine an orientation score for each tree in the program.

dfs(tree *t){ if(t = NULL) return; dfs(t->left); dfs(t->right); } Overview Program Source Instrumented Executable Orientation Score ? Compiler Tree Analysis Library

Tree-Traversal Orientation Analysis Returns an orientation score  [-1,1] 1 is depth-first traversal -1 is breadth first traversal 0 is an unknown traversal Returns an orientation score  [-1,1] 1 is depth-first traversal -1 is breadth first traversal 0 is an unknown traversal DFS BFS 0 1

Overview struct tree *t1, *t2; init(t1,t2); dfs(t1); bfs(t2); … …… t1t2 orientation score = 1.0 orientation score = -1.0

Calculating the Orientation Score Every memory access to a tree is classified as: Depth-First Breadth-First Both Neither The orientation score of each tree is calculated as: Every memory access to a tree is classified as: Depth-First Breadth-First Both Neither The orientation score of each tree is calculated as:

Calculating the Orientation Score A linked-list access can be classified as both Breadth- and Depth-First. If a memory access to a 1-arity tree is classified as both Breadth- and Depth-First It will be considered Depth-First. This result will likely be more useful to clients of the analysis. A linked-list access can be classified as both Breadth- and Depth-First. If a memory access to a 1-arity tree is classified as both Breadth- and Depth-First It will be considered Depth-First. This result will likely be more useful to clients of the analysis.

Determining if a Access is Depth-First The TAL maintains a stack of choice- points for each tree. Each choice-point consists of: 1. the address of a node, t, in the tree, 2. all n children of t, c 1 … c n, and 3. a boolean value representing if the node has been visited The TAL maintains a stack of choice- points for each tree. Each choice-point consists of: 1. the address of a node, t, in the tree, 2. all n children of t, c 1 … c n, and 3. a boolean value representing if the node has been visited

Determining if a Access is Depth-First Every time a node is visited, a choice-point for each of its children is pushed onto the stack abcdef 7654 …

Determining if a Access is Depth-First Every time a node is visited, a choice-point for each of its children is pushed onto the stack abcdef 7654 … 2 3

Determining if a Access is Depth-First Every time a node is visited, a choice-point for each of its children is pushed onto the stack abcdef 7654 … Dark color means visited

Determining if a Access is Depth-First Every time a node is visited, a choice-point for each of its children is pushed onto the stack abcdef 7654 …

Determining if a Access is Depth-First Every time a node is visited, a choice-point for each of its children is pushed onto the stack abcdef 7654 …

Determining if a Access is Depth-First Every time a node is visited, a choice-point for each of its children is pushed onto the stack abcdef 7654 …

Determining if a Access is Depth-First A choice-point is popped off the stack when a tree node lower in the stack is visited and all of the choice-points above have been visited. All the choice points up to the node that was visited are popped abcdef 7654 …

Determining if a Access is Depth-First A choice-point is popped off the stack when a tree node lower in the stack is visited and all of the choice-points above have been visited. All the choice points up the node that was visited are popped abcdef 7654 …

Determining if a Access is Depth-First A choice-point is popped off the stack when a tree node lower in the stack is visited and all of the choice-points above have been visited. All the choice points up the node that was visited are popped abcdef 7654 … a b

Determining if a Access is Depth-First An access to tree node t is classified as depth-first if and only if: 1. The address of cp top is equal to the address of t; OR 2. The address of child c i of cp top is equal to the address of t; OR 3. There exists and ancestor cp anc of cp top such that the address of cp anc is equal to the address of t and all of the choice-points on the stack above cp anc have been visited. An access to tree node t is classified as depth-first if and only if: 1. The address of cp top is equal to the address of t; OR 2. The address of child c i of cp top is equal to the address of t; OR 3. There exists and ancestor cp anc of cp top such that the address of cp anc is equal to the address of t and all of the choice-points on the stack above cp anc have been visited. cp top

Determining if a Access is Depth-First An access to tree node t is classified as depth-first if and only if: 1. The address of cp top is equal to the address of t; OR 2. The address of child c i of cp top is equal to the address of t; OR 3. There exists and ancestor cp anc of cp top such that the address of cp anc is equal to the address of t and all of the choice-points on the stack above cp anc have been visited. An access to tree node t is classified as depth-first if and only if: 1. The address of cp top is equal to the address of t; OR 2. The address of child c i of cp top is equal to the address of t; OR 3. There exists and ancestor cp anc of cp top such that the address of cp anc is equal to the address of t and all of the choice-points on the stack above cp anc have been visited. cp top

Determining if a Access is Depth-First An access to tree node t is classified as depth-first if and only if: 1. The address of cp top is equal to the address of t; OR 2. The address of child c i of cp top is equal to the address of t; OR 3. There exists and ancestor cp anc of cp top such that the address of cp anc is equal to the address of t and all of the choice-points on the stack above cp anc have been visited. An access to tree node t is classified as depth-first if and only if: 1. The address of cp top is equal to the address of t; OR 2. The address of child c i of cp top is equal to the address of t; OR 3. There exists and ancestor cp anc of cp top such that the address of cp anc is equal to the address of t and all of the choice-points on the stack above cp anc have been visited. cp top

Determining if a Access is Depth-First An access to tree node t is classified as depth-first if and only if: 1. The address of cp top is equal to the address of t; OR 2. The address of child c i of cp top is equal to the address of t; OR 3. There exists and ancestor cp anc of cp top such that the address of cp anc is equal to the address of t and all of the choice-points on the stack above cp anc have been visited. An access to tree node t is classified as depth-first if and only if: 1. The address of cp top is equal to the address of t; OR 2. The address of child c i of cp top is equal to the address of t; OR 3. There exists and ancestor cp anc of cp top such that the address of cp anc is equal to the address of t and all of the choice-points on the stack above cp anc have been visited. cp anc cp top

Determining if a Access is Breadth-First The TAL maintains an open and next list for each tree. They are stored a double-ended bit-vectors. The TAL maintains an open and next list for each tree. They are stored a double-ended bit-vectors abcdef abcdef Open Next

Determining if a Access is Breadth-First When tree node t is accessed: The children of t are added to the next list. If t is in the open list it is removed from the open list and the access is classified as breadth first. When the open list is empty it is swapped with the next list. When tree node t is accessed: The children of t are added to the next list. If t is in the open list it is removed from the open list and the access is classified as breadth first. When the open list is empty it is swapped with the next list abcdef 7654 … Open Next

Determining if a Access is Breadth-First When tree node t is accessed: The children of t are added to the next list. If t is in the open list it is removed from the open list and the access is classified as breadth first. When the open list is empty it is swapped with the next list. When tree node t is accessed: The children of t are added to the next list. If t is in the open list it is removed from the open list and the access is classified as breadth first. When the open list is empty it is swapped with the next list abcdef 7654 … 23 Open Next

Determining if a Access is Breadth-First When tree node t is accessed: The children of t are added to the next list. If t is in the open list it is removed from the open list and the access is classified as breadth first. When the open list is empty it is swapped with the next list. When tree node t is accessed: The children of t are added to the next list. If t is in the open list it is removed from the open list and the access is classified as breadth first. When the open list is empty it is swapped with the next list abcdef 7654 … 23 Open Next

Determining if a Access is Breadth-First When tree node t is accessed: The children of t are added to the next list. If t is in the open list it is removed from the open list and the access is classified as breadth first. When the open list is empty it is swapped with the next list. When tree node t is accessed: The children of t are added to the next list. If t is in the open list it is removed from the open list and the access is classified as breadth first. When the open list is empty it is swapped with the next list abcdef 7654 … 23 Open Next

Determining if a Access is Breadth-First When tree node t is accessed: The children of t are added to the next list. If t is in the open list it is removed from the open list and the access is classified as breadth first. When the open list is empty it is swapped with the next list. When tree node t is accessed: The children of t are added to the next list. If t is in the open list it is removed from the open list and the access is classified as breadth first. When the open list is empty it is swapped with the next list abcdef 7654 … 3 Open Next

Determining if a Access is Breadth-First When tree node t is accessed: The children of t are added to the next list. If t is in the open list it is removed from the open list and the access is classified as breadth first. When the open list is empty it is swapped with the next list. When tree node t is accessed: The children of t are added to the next list. If t is in the open list it is removed from the open list and the access is classified as breadth first. When the open list is empty it is swapped with the next list abcdef 7654 … 3 45 Open Next

Determining if a Access is Breadth-First When tree node t is accessed: The children of t are added to the next list. If t is in the open list it is removed from the open list and the access is classified as breadth first. When the open list is empty it is swapped with the next list. When tree node t is accessed: The children of t are added to the next list. If t is in the open list it is removed from the open list and the access is classified as breadth first. When the open list is empty it is swapped with the next list abcdef 7654 … 4567 Open Next

Determining if a Access is Breadth-First When tree node t is accessed: The children of t are added to the next list. If t is in the open list it is removed from the open list and the access is classified as breadth first. When the open list is empty it is swapped with the next list. When tree node t is accessed: The children of t are added to the next list. If t is in the open list it is removed from the open list and the access is classified as breadth first. When the open list is empty it is swapped with the next list abcdef 7654 … 4567 Open Next

Determining if a Access is Breadth-First When tree node t is accessed: The children of t are added to the next list. If t is in the open list it is removed from the open list and the access is classified as breadth first. When the open list is empty it is swapped with the next list. When tree node t is accessed: The children of t are added to the next list. If t is in the open list it is removed from the open list and the access is classified as breadth first. When the open list is empty it is swapped with the next list abcdef 7654 … Open Next

Implementation Built in the Open Research Compiler (ORC) Operates on the WHIRL (Winning Hierarchical Intermediate Representation Language) IR. Analysis requires Interprocedural Analysis (IPA). Automatically identifies link-based tree data structures using Ghiya and Hendren’s analysis [2] or programmer annotations. Instrumentation can be inserted into each procedure without IPA. Built in the Open Research Compiler (ORC) Operates on the WHIRL (Winning Hierarchical Intermediate Representation Language) IR. Analysis requires Interprocedural Analysis (IPA). Automatically identifies link-based tree data structures using Ghiya and Hendren’s analysis [2] or programmer annotations. Instrumentation can be inserted into each procedure without IPA.

Implementation Calls our Tree Analysis Library (TAL) register_tree_access_with_children() Takes Parameters: void *addr_deref int tree_id int num_children void *child_addr, … Calls our Tree Analysis Library (TAL) register_tree_access_with_children() Takes Parameters: void *addr_deref int tree_id int num_children void *child_addr, …

Implementation Analysis is safe and will not cause a correct program to fail. Replace calls to malloc/calloc/realloc with TALs wrapper functions. If memory allocation fails, the analysis is abandoned and the memory used by the analysis is freed. Memory address are calculated and accessed for the instrumentation in locations that are safe. i.e. Will not dereference null pointers if( tree != NULL && tree->data == 1) Analysis is safe and will not cause a correct program to fail. Replace calls to malloc/calloc/realloc with TALs wrapper functions. If memory allocation fails, the analysis is abandoned and the memory used by the analysis is freed. Memory address are calculated and accessed for the instrumentation in locations that are safe. i.e. Will not dereference null pointers if( tree != NULL && tree->data == 1)

How do we identify tree references? Example Code: /* inorder tree traversal */ void inorder_traverse_tree(struct tn *tree_ptr) { if(tree_ptr == NULL) return; inorder_traverse_tree(tree_ptr->left); tree_ptr->data++; inorder_traverse_tree(tree_ptr->right); } Example Code: /* inorder tree traversal */ void inorder_traverse_tree(struct tn *tree_ptr) { if(tree_ptr == NULL) return; inorder_traverse_tree(tree_ptr->left); tree_ptr->data++; inorder_traverse_tree(tree_ptr->right); }

How do we identify tree references? LOC 1 94 void inorder_traverse_tree(struct tn *tree_ptr) LOC 1 95 { FUNC_ENTRY IDNAME 0 BODY BLOCK END_BLOCK BLOCK END_BLOCK BLOCK PRAGMA (0x0) # PREAMBLE_END LOC 1 96 if(tree_ptr == NULL) IF U8U8LDID 0 T U8INTCONST 0 (0x0) I4U8EQ THEN BLOCK LOC 1 97 return; RETURN END_BLOCK ELSE LOC 1 96 BLOCK END_BLOCK END_IF LOC 1 94 void inorder_traverse_tree(struct tn *tree_ptr) LOC 1 95 { FUNC_ENTRY IDNAME 0 BODY BLOCK END_BLOCK BLOCK END_BLOCK BLOCK PRAGMA (0x0) # PREAMBLE_END LOC 1 96 if(tree_ptr == NULL) IF U8U8LDID 0 T U8INTCONST 0 (0x0) I4U8EQ THEN BLOCK LOC 1 97 return; RETURN END_BLOCK ELSE LOC 1 96 BLOCK END_BLOCK END_IF LOC LOC inorder_traverse_tree(tree_ptr->left); U8U8LDID 0 T U8U8ILOAD 8 T T U8PARM 2 T # by_value VCALL 126 # flags 0x7e LOC tree_ptr->data++; U8U8LDID 0 T I4I4ILOAD 0 T T I4INTCONST 1 (0x1) I4ADD U8U8LDID 0 T I4ISTORE 0 T LOC inorder_traverse_tree(tree_ptr->right); U8U8LDID 0 T U8U8ILOAD 16 T T U8PARM 2 T # by_value VCALL 126 # flags 0x7e RETURN END_BLOCK

How do we identify tree references? LOC 1 94 void inorder_traverse_tree(struct tn *tree_ptr) LOC 1 95 { FUNC_ENTRY IDNAME 0 BODY BLOCK END_BLOCK BLOCK END_BLOCK BLOCK PRAGMA (0x0) # PREAMBLE_END LOC 1 96 if(tree_ptr == NULL) IF U8U8LDID 0 T U8INTCONST 0 (0x0) I4U8EQ THEN BLOCK LOC 1 97 return; RETURN END_BLOCK ELSE LOC 1 96 BLOCK END_BLOCK END_IF LOC 1 94 void inorder_traverse_tree(struct tn *tree_ptr) LOC 1 95 { FUNC_ENTRY IDNAME 0 BODY BLOCK END_BLOCK BLOCK END_BLOCK BLOCK PRAGMA (0x0) # PREAMBLE_END LOC 1 96 if(tree_ptr == NULL) IF U8U8LDID 0 T U8INTCONST 0 (0x0) I4U8EQ THEN BLOCK LOC 1 97 return; RETURN END_BLOCK ELSE LOC 1 96 BLOCK END_BLOCK END_IF LOC LOC inorder_traverse_tree(tree_ptr->left); U8U8LDID 0 T U8U8ILOAD 8 T T U8PARM 2 T # by_value VCALL 126 # flags 0x7e LOC tree_ptr->data++; U8U8LDID 0 T I4I4ILOAD 0 T T I4INTCONST 1 (0x1) I4ADD U8U8LDID 0 T I4ISTORE 0 T LOC inorder_traverse_tree(tree_ptr->right); U8U8LDID 0 T U8U8ILOAD 16 T T U8PARM 2 T # by_value VCALL 126 # flags 0x7e RETURN END_BLOCK FUNC_ENTRY (inorder_traverse_tree) IDNAME (tree_ptr) BLOCK LOC 1 94 void inorder_traverse_tree(struct tn *tree_ptr) LOC 1 95 { FUNC_ENTRY IDNAME 0 BODY BLOCK END_BLOCK BLOCK END_BLOCK BLOCK void inorder_traverse_tree(struct tn *tree_ptr)

How do we identify tree references? LOC 1 94 void inorder_traverse_tree(struct tn *tree_ptr) LOC 1 95 { FUNC_ENTRY IDNAME 0 BODY BLOCK END_BLOCK BLOCK END_BLOCK BLOCK PRAGMA (0x0) # PREAMBLE_END LOC 1 96 if(tree_ptr == NULL) IF U8U8LDID 0 T U8INTCONST 0 (0x0) I4U8EQ THEN BLOCK LOC 1 97 return; RETURN END_BLOCK ELSE LOC 1 96 BLOCK END_BLOCK END_IF LOC 1 94 void inorder_traverse_tree(struct tn *tree_ptr) LOC 1 95 { FUNC_ENTRY IDNAME 0 BODY BLOCK END_BLOCK BLOCK END_BLOCK BLOCK PRAGMA (0x0) # PREAMBLE_END LOC 1 96 if(tree_ptr == NULL) IF U8U8LDID 0 T U8INTCONST 0 (0x0) I4U8EQ THEN BLOCK LOC 1 97 return; RETURN END_BLOCK ELSE LOC 1 96 BLOCK END_BLOCK END_IF LOC LOC inorder_traverse_tree(tree_ptr->left); U8U8LDID 0 T U8U8ILOAD 8 T T U8PARM 2 T # by_value VCALL 126 # flags 0x7e LOC tree_ptr->data++; U8U8LDID 0 T I4I4ILOAD 0 T T I4INTCONST 1 (0x1) I4ADD U8U8LDID 0 T I4ISTORE 0 T LOC inorder_traverse_tree(tree_ptr->right); U8U8LDID 0 T U8U8ILOAD 16 T T U8PARM 2 T # by_value VCALL 126 # flags 0x7e RETURN END_BLOCK FUNC_ENTRY (inorder_traverse_tree) IDNAME (tree_ptr) BLOCK IF EQ LDID (tree_ptr) INTCONST 0x0 RETURN BLOCK (then) LOC 1 96 if(tree_ptr == NULL) IF U8U8LDID 0 T U8INTCONST 0 (0x0) I4U8EQ THEN BLOCK LOC 1 97 return; RETURN END_BLOCK if(tree_ptr == NULL)

How do we identify tree references? LOC 1 94 void inorder_traverse_tree(struct tn *tree_ptr) LOC 1 95 { FUNC_ENTRY IDNAME 0 BODY BLOCK END_BLOCK BLOCK END_BLOCK BLOCK PRAGMA (0x0) # PREAMBLE_END LOC 1 96 if(tree_ptr == NULL) IF U8U8LDID 0 T U8INTCONST 0 (0x0) I4U8EQ THEN BLOCK LOC 1 97 return; RETURN END_BLOCK ELSE LOC 1 96 BLOCK END_BLOCK END_IF LOC 1 94 void inorder_traverse_tree(struct tn *tree_ptr) LOC 1 95 { FUNC_ENTRY IDNAME 0 BODY BLOCK END_BLOCK BLOCK END_BLOCK BLOCK PRAGMA (0x0) # PREAMBLE_END LOC 1 96 if(tree_ptr == NULL) IF U8U8LDID 0 T U8INTCONST 0 (0x0) I4U8EQ THEN BLOCK LOC 1 97 return; RETURN END_BLOCK ELSE LOC 1 96 BLOCK END_BLOCK END_IF LOC LOC inorder_traverse_tree(tree_ptr->left); U8U8LDID 0 T U8U8ILOAD 8 T T U8PARM 2 T # by_value VCALL 126 # flags 0x7e LOC tree_ptr->data++; U8U8LDID 0 T I4I4ILOAD 0 T T I4INTCONST 1 (0x1) I4ADD U8U8LDID 0 T I4ISTORE 0 T LOC inorder_traverse_tree(tree_ptr->right); U8U8LDID 0 T U8U8ILOAD 16 T T U8PARM 2 T # by_value VCALL 126 # flags 0x7e RETURN END_BLOCK BLOCK VCALL PARAM ILOAD (offset 8) LDID (tree_ptr) LOC inorder_traverse_tree(tree_ptr->left); U8U8LDID 0 T U8U8ILOAD 8 T T U8PARM 2 T # by_value VCALL 126 # flags 0x7e inorder_traverse_tree(tree_ptr->left);

How do we identify tree references? LOC 1 94 void inorder_traverse_tree(struct tn *tree_ptr) LOC 1 95 { FUNC_ENTRY IDNAME 0 BODY BLOCK END_BLOCK BLOCK END_BLOCK BLOCK PRAGMA (0x0) # PREAMBLE_END LOC 1 96 if(tree_ptr == NULL) IF U8U8LDID 0 T U8INTCONST 0 (0x0) I4U8EQ THEN BLOCK LOC 1 97 return; RETURN END_BLOCK ELSE LOC 1 96 BLOCK END_BLOCK END_IF LOC 1 94 void inorder_traverse_tree(struct tn *tree_ptr) LOC 1 95 { FUNC_ENTRY IDNAME 0 BODY BLOCK END_BLOCK BLOCK END_BLOCK BLOCK PRAGMA (0x0) # PREAMBLE_END LOC 1 96 if(tree_ptr == NULL) IF U8U8LDID 0 T U8INTCONST 0 (0x0) I4U8EQ THEN BLOCK LOC 1 97 return; RETURN END_BLOCK ELSE LOC 1 96 BLOCK END_BLOCK END_IF LOC LOC inorder_traverse_tree(tree_ptr->left); U8U8LDID 0 T U8U8ILOAD 8 T T U8PARM 2 T # by_value VCALL 126 # flags 0x7e LOC tree_ptr->data++; U8U8LDID 0 T I4I4ILOAD 0 T T I4INTCONST 1 (0x1) I4ADD U8U8LDID 0 T I4ISTORE 0 T LOC inorder_traverse_tree(tree_ptr->right); U8U8LDID 0 T U8U8ILOAD 16 T T U8PARM 2 T # by_value VCALL 126 # flags 0x7e RETURN END_BLOCK BLOCK VCALL PARAM ILOAD (offset 8) LDID (tree_ptr) ISTORE (offset 8) LDID (tree_ptr) ADD INTCONST 0x1 ILOAD (offset 0) LDID (tree_ptr) LOC tree_ptr->data++; U8U8LDID 0 T I4I4ILOAD 0 T T I4INTCONST 1 (0x1) I4ADD U8U8LDID 0 T I4ISTORE 0 T tree_ptr->data++;

How do we identify tree references? LOC 1 94 void inorder_traverse_tree(struct tn *tree_ptr) LOC 1 95 { FUNC_ENTRY IDNAME 0 BODY BLOCK END_BLOCK BLOCK END_BLOCK BLOCK PRAGMA (0x0) # PREAMBLE_END LOC 1 96 if(tree_ptr == NULL) IF U8U8LDID 0 T U8INTCONST 0 (0x0) I4U8EQ THEN BLOCK LOC 1 97 return; RETURN END_BLOCK ELSE LOC 1 96 BLOCK END_BLOCK END_IF LOC 1 94 void inorder_traverse_tree(struct tn *tree_ptr) LOC 1 95 { FUNC_ENTRY IDNAME 0 BODY BLOCK END_BLOCK BLOCK END_BLOCK BLOCK PRAGMA (0x0) # PREAMBLE_END LOC 1 96 if(tree_ptr == NULL) IF U8U8LDID 0 T U8INTCONST 0 (0x0) I4U8EQ THEN BLOCK LOC 1 97 return; RETURN END_BLOCK ELSE LOC 1 96 BLOCK END_BLOCK END_IF LOC LOC inorder_traverse_tree(tree_ptr->left); U8U8LDID 0 T U8U8ILOAD 8 T T U8PARM 2 T # by_value VCALL 126 # flags 0x7e LOC tree_ptr->data++; U8U8LDID 0 T I4I4ILOAD 0 T T I4INTCONST 1 (0x1) I4ADD U8U8LDID 0 T I4ISTORE 0 T LOC inorder_traverse_tree(tree_ptr->right); U8U8LDID 0 T U8U8ILOAD 16 T T U8PARM 2 T # by_value VCALL 126 # flags 0x7e RETURN END_BLOCK BLOCK VCALL PARAM ILOAD (offset 8) LDID (tree_ptr) VCALL PARAM ILOAD (offset 16) LDID (tree_ptr) ISTORE (offset 8) LDID (tree_ptr) ADD INTCONST 0x1 ILOAD (offset 0) LDID (tree_ptr) LOC inorder_traverse_tree(tree_ptr->right); U8U8LDID 0 T U8U8ILOAD 16 T T U8PARM 2 T # by_value VCALL 126 # flags 0x7e inorder_traverse_tree(tree_ptr->right);

How do we identify tree references? LOC 1 94 void inorder_traverse_tree(struct tn *tree_ptr) LOC 1 95 { FUNC_ENTRY IDNAME 0 BODY BLOCK END_BLOCK BLOCK END_BLOCK BLOCK PRAGMA (0x0) # PREAMBLE_END LOC 1 96 if(tree_ptr == NULL) IF U8U8LDID 0 T U8INTCONST 0 (0x0) I4U8EQ THEN BLOCK LOC 1 97 return; RETURN END_BLOCK ELSE LOC 1 96 BLOCK END_BLOCK END_IF LOC 1 94 void inorder_traverse_tree(struct tn *tree_ptr) LOC 1 95 { FUNC_ENTRY IDNAME 0 BODY BLOCK END_BLOCK BLOCK END_BLOCK BLOCK PRAGMA (0x0) # PREAMBLE_END LOC 1 96 if(tree_ptr == NULL) IF U8U8LDID 0 T U8INTCONST 0 (0x0) I4U8EQ THEN BLOCK LOC 1 97 return; RETURN END_BLOCK ELSE LOC 1 96 BLOCK END_BLOCK END_IF LOC LOC inorder_traverse_tree(tree_ptr->left); U8U8LDID 0 T U8U8ILOAD 8 T T U8PARM 2 T # by_value VCALL 126 # flags 0x7e LOC tree_ptr->data++; U8U8LDID 0 T I4I4ILOAD 0 T T I4INTCONST 1 (0x1) I4ADD U8U8LDID 0 T I4ISTORE 0 T LOC inorder_traverse_tree(tree_ptr->right); U8U8LDID 0 T U8U8ILOAD 16 T T U8PARM 2 T # by_value VCALL 126 # flags 0x7e RETURN END_BLOCK BLOCK VCALL PARAM ILOAD (offset 8) LDID (tree_ptr) VCALL PARAM ILOAD (offset 16) LDID (tree_ptr) ISTORE (offset 8) LDID (tree_ptr) ADD INTCONST 0x1 ILOAD (offset 0) LDID (tree_ptr) FUNC_ENTRY (inorder_traverse_tree) IDNAME (tree_ptr) BLOCK IF EQ LDIDINTCONST 0x0 RETURN BLOCK (then)

How do we identify tree references? LOC 1 94 void inorder_traverse_tree(struct tn *tree_ptr) LOC 1 95 { FUNC_ENTRY IDNAME 0 BODY BLOCK END_BLOCK BLOCK END_BLOCK BLOCK PRAGMA (0x0) # PREAMBLE_END LOC 1 96 if(tree_ptr == NULL) IF U8U8LDID 0 T U8INTCONST 0 (0x0) I4U8EQ THEN BLOCK LOC 1 97 return; RETURN END_BLOCK ELSE LOC 1 96 BLOCK END_BLOCK END_IF LOC 1 94 void inorder_traverse_tree(struct tn *tree_ptr) LOC 1 95 { FUNC_ENTRY IDNAME 0 BODY BLOCK END_BLOCK BLOCK END_BLOCK BLOCK PRAGMA (0x0) # PREAMBLE_END LOC 1 96 if(tree_ptr == NULL) IF U8U8LDID 0 T U8INTCONST 0 (0x0) I4U8EQ THEN BLOCK LOC 1 97 return; RETURN END_BLOCK ELSE LOC 1 96 BLOCK END_BLOCK END_IF LOC LOC inorder_traverse_tree(tree_ptr->left); U8U8LDID 0 T U8U8ILOAD 8 T T U8PARM 2 T # by_value VCALL 126 # flags 0x7e LOC tree_ptr->data++; U8U8LDID 0 T I4I4ILOAD 0 T T I4INTCONST 1 (0x1) I4ADD U8U8LDID 0 T I4ISTORE 0 T LOC inorder_traverse_tree(tree_ptr->right); U8U8LDID 0 T U8U8ILOAD 16 T T U8PARM 2 T # by_value VCALL 126 # flags 0x7e RETURN END_BLOCK BLOCK VCALL PARAM VCALL PARAM ISTORE (offset 8) LDID (tree_ptr) ADD INTCONST 0x1 FUNC_ENTRY (inorder_traverse_tree) IDNAME (tree_ptr) BLOCK IF EQ LDIDINTCONST 0x0 RETURN BLOCK (then) Where do we access trees in memory? ILOAD (offset 8) LDID (tree_ptr) ILOAD (offset 16) LDID (tree_ptr) ILOAD (offset 0) LDID (tree_ptr)

How do we identify tree references? LOC 1 94 void inorder_traverse_tree(struct tn *tree_ptr) LOC 1 95 { FUNC_ENTRY IDNAME 0 BODY BLOCK END_BLOCK BLOCK END_BLOCK BLOCK PRAGMA (0x0) # PREAMBLE_END LOC 1 96 if(tree_ptr == NULL) IF U8U8LDID 0 T U8INTCONST 0 (0x0) I4U8EQ THEN BLOCK LOC 1 97 return; RETURN END_BLOCK ELSE LOC 1 96 BLOCK END_BLOCK END_IF LOC 1 94 void inorder_traverse_tree(struct tn *tree_ptr) LOC 1 95 { FUNC_ENTRY IDNAME 0 BODY BLOCK END_BLOCK BLOCK END_BLOCK BLOCK PRAGMA (0x0) # PREAMBLE_END LOC 1 96 if(tree_ptr == NULL) IF U8U8LDID 0 T U8INTCONST 0 (0x0) I4U8EQ THEN BLOCK LOC 1 97 return; RETURN END_BLOCK ELSE LOC 1 96 BLOCK END_BLOCK END_IF LOC LOC inorder_traverse_tree(tree_ptr->left); U8U8LDID 0 T U8U8ILOAD 8 T T U8PARM 2 T # by_value VCALL 126 # flags 0x7e LOC tree_ptr->data++; U8U8LDID 0 T I4I4ILOAD 0 T T I4INTCONST 1 (0x1) I4ADD U8U8LDID 0 T I4ISTORE 0 T LOC inorder_traverse_tree(tree_ptr->right); U8U8LDID 0 T U8U8ILOAD 16 T T U8PARM 2 T # by_value VCALL 126 # flags 0x7e RETURN END_BLOCK BLOCK VCALL PARAM VCALL PARAM ISTORE (offset 8) LDID (tree_ptr) ADD INTCONST 0x1 FUNC_ENTRY (inorder_traverse_tree) IDNAME (tree_ptr) BLOCK IF EQ LDIDINTCONST 0x0 RETURN BLOCK (then) This is where our extension to the ORC inserts code into the WHIRL Tree. ILOAD (offset 8) LDID (tree_ptr) ILOAD (offset 16) LDID (tree_ptr) ILOAD (offset 0) LDID (tree_ptr)

The Nodes we Insert Into WHIRL U8U8LDID 0 T U8PARM 2 T # by_value U4INTCONST 1 (0x1) U4PARM 2 T # by_value U4INTCONST 2 (0x2) U4PARM 2 T # by_value U8U8LDID 0 T U8U8ILOAD 8 T T U8PARM 2 T # by_value U8U8LDID 0 T U8U8ILOAD 16 T T U8PARM 2 T # by_value VCALL 126 # flags 0x7e U8U8LDID 0 T U8PARM 2 T # by_value U4INTCONST 1 (0x1) U4PARM 2 T # by_value U4INTCONST 2 (0x2) U4PARM 2 T # by_value U8U8LDID 0 T U8U8ILOAD 8 T T U8PARM 2 T # by_value U8U8LDID 0 T U8U8ILOAD 16 T T U8PARM 2 T # by_value VCALL 126 # flags 0x7e

The Nodes we Insert Into WHIRL VCALL (register_tree_access_with_children) ILOAD (offset 16) ILOAD (offset 8) PARM INTCONST 0x1 INTCONST 0x2 LDID (tree_ptr) LDID (tree_ptr) PARM LDID (tree_ptr)

Experimental Setup Open Research Compiler v2.1 Optimization level -O3 1.3 GHz Itanium2 1 GB of RAM Open Research Compiler v2.1 Optimization level -O3 1.3 GHz Itanium2 1 GB of RAM

Analysis Results (Synthetic Benchmark) Benchmark Orientation Score ExpectedExperimental Random Depth Breadth-First Depth-Breadth Non-Standard Multi Depth Breadth Search Binary Search

Analysis Results (Olden Benchmark) Benchmark Orientation Score ExpectedExperimental BH Bisort Health MSTLow positive PerimeterLow positive Power Treeadd TSPLow positive

Runtime Overhead (Synthetic Benchmark) Benchmark Runtime (s) OriginalInstrumented Random Depth Breadth-First Depth-Breadth Non-Standard Multi Depth Breadth Search Binary Search

Runtime Overhead (Olden Benchmark) Benchmark Runtime (s) OriginalInstrumented BH Bisort Health MST Perimeter Power Treeadd TSP

Memory Overhead (Synthetic Benchmark) Benchmark Memory Usage (kbytes) OriginalInstrumented Random Depth Breadth-First Depth-Breadth Non-Standard Multi Depth Breadth Search Binary Search

Memory Overhead (Olden Benchmark) Benchmark Memory Usage (kbytes) OriginalInstrumented BH3 520 Bisort Health MST Perimeter Power Treeadd3 008 TSP

Conclusion Developed an efficient analysis to automatically determine the orientation of tree traversals Instrumented applications only require 7% more memory Developed an efficient analysis to automatically determine the orientation of tree traversals Instrumented applications only require 7% more memory

Questions?

References [1] Jason Patterson. Modern Microprocessors A 90 Minute Guide! cessors/ cessors/ [2] R. Ghiya, L. J. Hendren. Is it a tree, a dag, or a cyclic graph? A shape analysis for heap directed pointers in C. POPL 1996 [1] Jason Patterson. Modern Microprocessors A 90 Minute Guide! cessors/ cessors/ [2] R. Ghiya, L. J. Hendren. Is it a tree, a dag, or a cyclic graph? A shape analysis for heap directed pointers in C. POPL 1996