Skip to content

Commit

Permalink
Loop invariant code motion implemented.
Browse files Browse the repository at this point in the history
  • Loading branch information
schani committed Aug 15, 2009
1 parent 2de02c4 commit 6fcabfb
Show file tree
Hide file tree
Showing 7 changed files with 421 additions and 53 deletions.
2 changes: 1 addition & 1 deletion Makefile
Expand Up @@ -122,7 +122,7 @@ CXX = g++

export CFLAGS CC

COMMON_OBJECTS = mathmap_common.o builtins/builtins.o exprtree.o parser.o scanner.o vars.o tags.o tuples.o internals.o macros.o userval.o overload.o jump.o builtins/libnoise.o builtins/spec_func.o compiler.o bitvector.o expression_db.o drawable.o floatmap.o tree_vectors.o mmpools.o designer/designer.o designer/cycles.o designer/loadsave.o designer_filter.o native-filters/gauss.o compopt/dce.o compopt/resize.o backends/cc.o backends/lazy_creator.o $(FFTW_OBJECTS) $(LLVM_OBJECTS)
COMMON_OBJECTS = mathmap_common.o builtins/builtins.o exprtree.o parser.o scanner.o vars.o tags.o tuples.o internals.o macros.o userval.o overload.o jump.o builtins/libnoise.o builtins/spec_func.o compiler.o bitvector.o expression_db.o drawable.o floatmap.o tree_vectors.o mmpools.o designer/designer.o designer/cycles.o designer/loadsave.o designer_filter.o native-filters/gauss.o compopt/dce.o compopt/resize.o compopt/licm.o backends/cc.o backends/lazy_creator.o $(FFTW_OBJECTS) $(LLVM_OBJECTS)
#COMMON_OBJECTS += designer/widget.o
COMMON_OBJECTS += designer/cairo_widget.o

Expand Down
2 changes: 1 addition & 1 deletion backends/cc.c
Expand Up @@ -812,7 +812,7 @@ generate_plug_in (char *filter, char *output_filename,
return 0;
}

compiler_generate_ir_code(mathmap->main_filter, analyze_constants, 0, -1);
compiler_generate_ir_code(mathmap->main_filter, analyze_constants, 0, -1, FALSE);

out = fopen(output_filename, "w");

Expand Down
24 changes: 23 additions & 1 deletion bitvector.c
Expand Up @@ -3,7 +3,7 @@
*
* MathMap
*
* Copyright (C) 2004 Mark Probst
* Copyright (C) 2004-2009 Mark Probst
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
Expand Down Expand Up @@ -92,6 +92,28 @@ bit_vector_bit (bit_vector_t *bitvec, unsigned long which)
return (bitvec->data[which >> LONG_SHIFT] & BIT(which & LONG_MASK)) != 0;
}

void
bit_vector_add (bit_vector_t *bitvec, bit_vector_t *addee)
{
int i;

g_assert(bitvec->size == addee->size);

for (i = 0; i < BIT_SIZE_TO_LONG_SIZE(bitvec->size); ++i)
bitvec->data[i] |= addee->data[i];
}

void
bit_vector_dump (bit_vector_t *bitvec)
{
int i;

for (i = 0; i < bitvec->size; ++i)
if (bit_vector_bit(bitvec, i))
printf("%d ", i);
printf("\n");
}

#ifdef TEST_BITVECTOR
#include <stdio.h>

Expand Down
6 changes: 5 additions & 1 deletion bitvector.h
Expand Up @@ -3,7 +3,7 @@
*
* MathMap
*
* Copyright (C) 2004 Mark Probst
* Copyright (C) 2004-2009 Mark Probst
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License
Expand Down Expand Up @@ -38,3 +38,7 @@ void bit_vector_set (bit_vector_t *bitvec, unsigned long which);
void bit_vector_clear (bit_vector_t *bitvec, unsigned long which);

int bit_vector_bit (bit_vector_t *bitvec, unsigned long which);

void bit_vector_add (bit_vector_t *bitvec, bit_vector_t *addee);

void bit_vector_dump (bit_vector_t *bitvec);
12 changes: 11 additions & 1 deletion compiler-internals.h
Expand Up @@ -302,20 +302,28 @@ extern void compiler_replace_op_rhs_arg (statement_t *stmt, int arg_num, primary

extern value_set_t* compiler_new_value_set (void);
extern void compiler_value_set_add (value_set_t *set, value_t *val);
extern void compiler_value_set_add_set (value_set_t *set, value_set_t *addee);
extern gboolean compiler_value_set_contains (value_set_t *set, value_t *val);
extern value_set_t* compiler_value_set_copy (value_set_t *set);
extern void compiler_free_value_set (value_set_t *set);

extern statement_t* compiler_stmt_unlink (statement_t **stmtp);
extern statement_t** compiler_stmt_insert_before (statement_t *stmt, statement_t **insertion_point);

extern void compiler_for_each_value_in_rhs (rhs_t *rhs, void (*func) (value_t *value, void *info),
void *info);
extern void compiler_for_each_value_in_statements (statement_t *stmt,
void (*func) (value_t *value, statement_t *stmt, void *info),
void *info);
extern void compiler_for_each_value_in_statement (statement_t *stmt,
void (*func) (value_t *value, statement_t *stmt, void *info),
void *info);

extern int compiler_slice_code (statement_t *stmt, unsigned int slice_flag,
int (*predicate) (statement_t *stmt, void *info), void *info);

extern filter_code_t* compiler_generate_ir_code (filter_t *filter, int constant_analysis,
int convert_types, int timeout);
int convert_types, int timeout, gboolean debug_output);

extern filter_code_t** compiler_compile_filters (mathmap_t *mathmap, int timeout);

Expand All @@ -327,9 +335,11 @@ extern void compiler_slice_code_for_const (statement_t *stmt, int const_type);
extern gboolean compiler_opt_remove_dead_assignments (statement_t *first_stmt);
extern gboolean compiler_opt_orig_val_resize (statement_t **first_stmt);
extern gboolean compiler_opt_strip_resize (statement_t **first_stmt);
extern gboolean compiler_opt_loop_invariant_code_motion (statement_t **first_stmt);

#define COMPILER_FOR_EACH_VALUE_IN_RHS(rhs,func,...) do { long __clos[] = { __VA_ARGS__ }; compiler_for_each_value_in_rhs((rhs),(func),__clos); } while (0)
#define COMPILER_FOR_EACH_VALUE_IN_STATEMENTS(stmt,func,...) do { long __clos[] = { __VA_ARGS__ }; compiler_for_each_value_in_statements((stmt),(func),__clos); } while (0)
#define COMPILER_FOR_EACH_VALUE_IN_STATEMENT(stmt,func,...) do { long __clos[] = { __VA_ARGS__ }; compiler_for_each_value_in_statement((stmt),(func),__clos); } while (0)
#define COMPILER_SLICE_CODE(stmt,flag,func,...) do { long __clos[] = { __VA_ARGS__ }; compiler_slice_code((stmt),(flag),(func),__clos); } while (0)

#ifdef __cplusplus
Expand Down
144 changes: 96 additions & 48 deletions compiler.c
Expand Up @@ -173,14 +173,20 @@ compiler_value_set_add (value_set_t *set, value_t *val)
bit_vector_set(set, val->global_index);
}

void
compiler_value_set_add_set (value_set_t *set, value_set_t *addee)
{
bit_vector_add(set, addee);
}

gboolean
compiler_value_set_contains (value_set_t *set, value_t *val)
{
return bit_vector_bit(set, val->global_index);
}

static value_set_t*
value_set_copy (value_set_t *set)
value_set_t*
compiler_value_set_copy (value_set_t *set)
{
return copy_bit_vector(set);
}
Expand All @@ -191,6 +197,32 @@ compiler_free_value_set (value_set_t *set)
free_bit_vector(set);
}

statement_t*
compiler_stmt_unlink (statement_t **stmtp)
{
statement_t *stmt = *stmtp;

g_assert(stmt != NULL);

*stmtp = stmt->next;
stmt->next = NULL;
stmt->parent = NULL;
return stmt;
}

statement_t**
compiler_stmt_insert_before (statement_t *stmt, statement_t **insertion_point)
{
g_assert(stmt != NULL && stmt->next == NULL && stmt->parent == NULL);
g_assert(*insertion_point != NULL);

stmt->next = *insertion_point;
stmt->parent = stmt->next->parent;
*insertion_point = stmt;

return &stmt->next;
}

int
compiler_op_index (operation_t *op)
{
Expand Down Expand Up @@ -742,39 +774,44 @@ _call_func (value_t *value, void *info)
}

void
compiler_for_each_value_in_statements (statement_t *stmt, void (*func) (value_t *value, statement_t *stmt, void *info), void *info)
compiler_for_each_value_in_statement (statement_t *stmt, void (*func) (value_t *value, statement_t *stmt, void *info), void *info)
{
while (stmt != 0)
switch (stmt->kind)
{
switch (stmt->kind)
{
case STMT_NIL :
break;
case STMT_NIL :
break;

case STMT_PHI_ASSIGN :
COMPILER_FOR_EACH_VALUE_IN_RHS(stmt->v.assign.rhs2, &_call_func, func, stmt, info);
case STMT_ASSIGN :
COMPILER_FOR_EACH_VALUE_IN_RHS(stmt->v.assign.rhs, &_call_func, func, stmt, info);
func(stmt->v.assign.lhs, stmt, info);
break;
case STMT_PHI_ASSIGN :
COMPILER_FOR_EACH_VALUE_IN_RHS(stmt->v.assign.rhs2, &_call_func, func, stmt, info);
case STMT_ASSIGN :
COMPILER_FOR_EACH_VALUE_IN_RHS(stmt->v.assign.rhs, &_call_func, func, stmt, info);
func(stmt->v.assign.lhs, stmt, info);
break;

case STMT_IF_COND :
COMPILER_FOR_EACH_VALUE_IN_RHS(stmt->v.if_cond.condition, &_call_func, func, stmt, info);
compiler_for_each_value_in_statements(stmt->v.if_cond.consequent, func, info);
compiler_for_each_value_in_statements(stmt->v.if_cond.alternative, func, info);
compiler_for_each_value_in_statements(stmt->v.if_cond.exit, func, info);
break;
case STMT_IF_COND :
COMPILER_FOR_EACH_VALUE_IN_RHS(stmt->v.if_cond.condition, &_call_func, func, stmt, info);
compiler_for_each_value_in_statements(stmt->v.if_cond.consequent, func, info);
compiler_for_each_value_in_statements(stmt->v.if_cond.alternative, func, info);
compiler_for_each_value_in_statements(stmt->v.if_cond.exit, func, info);
break;

case STMT_WHILE_LOOP :
COMPILER_FOR_EACH_VALUE_IN_RHS(stmt->v.while_loop.invariant, &_call_func, func, stmt, info);
compiler_for_each_value_in_statements(stmt->v.while_loop.entry, func, info);
compiler_for_each_value_in_statements(stmt->v.while_loop.body, func, info);
break;
case STMT_WHILE_LOOP :
COMPILER_FOR_EACH_VALUE_IN_RHS(stmt->v.while_loop.invariant, &_call_func, func, stmt, info);
compiler_for_each_value_in_statements(stmt->v.while_loop.entry, func, info);
compiler_for_each_value_in_statements(stmt->v.while_loop.body, func, info);
break;

default :
g_assert_not_reached();
}
default :
g_assert_not_reached();
}
}

void
compiler_for_each_value_in_statements (statement_t *stmt, void (*func) (value_t *value, statement_t *stmt, void *info), void *info)
{
while (stmt != 0)
{
compiler_for_each_value_in_statement(stmt, func, info);
stmt = stmt->next;
}
}
Expand Down Expand Up @@ -3117,7 +3154,7 @@ analyze_least_const_type_multiply_used_in (statement_t *stmt, int in_loop, value
sub_least_const = analyze_least_const_type_multiply_used_in(stmt->v.while_loop.entry,
in_loop, multiply_assigned_set, changed);

copy = value_set_copy(multiply_assigned_set);
copy = compiler_value_set_copy(multiply_assigned_set);
assert(copy != 0);

/* we have to process the body twice because
Expand Down Expand Up @@ -4435,7 +4472,7 @@ check_ssa_with_undo (statement_t *stmts, statement_t *parent, GHashTable *curren
value_set_t *defined_set_copy;

current_value_hash_copy = direct_hash_table_copy(current_value_hash);
defined_set_copy = value_set_copy(defined_set);
defined_set_copy = compiler_value_set_copy(defined_set);

check_ssa_recursively(stmts, parent, current_value_hash_copy, defined_set_copy);

Expand Down Expand Up @@ -4636,7 +4673,7 @@ optimization_time_out (struct timeval *start, int timeout)
}

filter_code_t*
compiler_generate_ir_code (filter_t *filter, int constant_analysis, int convert_types, int timeout)
compiler_generate_ir_code (filter_t *filter, int constant_analysis, int convert_types, int timeout, gboolean debug_output)
{
gboolean changed;
filter_code_t *code;
Expand Down Expand Up @@ -4669,10 +4706,11 @@ compiler_generate_ir_code (filter_t *filter, int constant_analysis, int convert_
check_ssa(first_stmt);
#endif

#ifdef DEBUG_OUTPUT
printf("--------------------------------\n");
dump_code(first_stmt, 0);
#endif
if (debug_output)
{
printf("--------------------------------\n");
dump_code(first_stmt, 0);
}

optimize_closure_application(first_stmt);
CHECK_SSA;
Expand All @@ -4687,6 +4725,8 @@ compiler_generate_ir_code (filter_t *filter, int constant_analysis, int convert_
CHECK_SSA;
changed = optimize_make_tuple() || changed;
CHECK_SSA;
changed = compiler_opt_loop_invariant_code_motion(&first_stmt) || changed;
CHECK_SSA;
changed = common_subexpression_elimination() || changed;
CHECK_SSA;
changed = copy_propagation() || changed;
Expand All @@ -4696,16 +4736,18 @@ compiler_generate_ir_code (filter_t *filter, int constant_analysis, int convert_
changed = simplify_ops() || changed;
CHECK_SSA;

#ifdef DEBUG_OUTPUT
printf("-------------------------------- before resize\n");
dump_code(first_stmt, 0);
#endif
if (debug_output)
{
printf("-------------------------------- before resize\n");
dump_code(first_stmt, 0);
}
changed = compiler_opt_orig_val_resize(&first_stmt) || changed;
CHECK_SSA;
#ifdef DEBUG_OUTPUT
printf("-------------------------------- after resize\n");
dump_code(first_stmt, 0);
#endif
if (debug_output)
{
printf("-------------------------------- after resize\n");
dump_code(first_stmt, 0);
}

changed = compiler_opt_strip_resize(&first_stmt) || changed;
CHECK_SSA;
Expand All @@ -4729,10 +4771,11 @@ compiler_generate_ir_code (filter_t *filter, int constant_analysis, int convert_
analyze_constants();
#endif

#ifdef DEBUG_OUTPUT
printf("----------- final ---------------------\n");
dump_code(first_stmt, 0);
#endif
if (debug_output)
{
printf("----------- final ---------------------\n");
dump_code(first_stmt, 0);
}
check_ssa(first_stmt);

/* no statement reordering after this point */
Expand All @@ -4753,6 +4796,11 @@ compiler_compile_filters (mathmap_t *mathmap, int timeout)
filter_code_t **filter_codes;
int num_filters, i;
filter_t *filter;
#ifdef DEBUG_OUTPUT
gboolean debug_output = TRUE;
#else
gboolean debug_output = FALSE;
#endif

init_pools(&compiler_pools);
vector_variables = g_hash_table_new(g_direct_hash, g_direct_equal);
Expand All @@ -4773,7 +4821,7 @@ compiler_compile_filters (mathmap_t *mathmap, int timeout)
#ifdef DEBUG_OUTPUT
g_print("compiling filter %s\n", filter->name);
#endif
filter_codes[i] = compiler_generate_ir_code(filter, 1, 0, timeout);
filter_codes[i] = compiler_generate_ir_code(filter, 1, 0, timeout, debug_output && filter == mathmap->main_filter);
}

return filter_codes;
Expand Down

0 comments on commit 6fcabfb

Please sign in to comment.