From: Sebastian Buchwald Date: Fri, 3 Oct 2008 18:07:15 +0000 (+0000) Subject: - integrated new PBQP solver into existing PBQP transformation, so it can be easily... X-Git-Url: http://nsz.repo.hu/git/?a=commitdiff_plain;h=724875e6dd0a014986b5b279266e40e0187aba2a;p=libfirm - integrated new PBQP solver into existing PBQP transformation, so it can be easily compared to the Scholz solver - you can switch between the solver using the "USE_KAPS" macro - removed code that create a zero matrix for each pbqp edge, before the real edge costs are created [r22440] --- diff --git a/html_dumper.c b/html_dumper.c new file mode 100644 index 000000000..bbb8372eb --- /dev/null +++ b/html_dumper.c @@ -0,0 +1,136 @@ +#include "adt/array.h" +#include "assert.h" + +#include "pbqp_edge_t.h" +#include "pbqp_node_t.h" +#include "html_dumper.h" +#include "kaps.h" +#include "pbqp_t.h" + +/* print vector */ +static void dump_vector(FILE *f, vector *vec) +{ + unsigned index; + assert(vec); + + fprintf(f, "( "); + unsigned len = vec->len; + assert(len> 0); + for (index = 0; index < len; ++index) { + fprintf(f, "%6d", vec->entries[index].data); + } + fprintf(f, " )\n"); +} + +static void dump_matrix(FILE *f, pbqp_matrix *mat) +{ + unsigned row, col; + assert(mat); + num *p = mat->entries; + + assert(mat->cols > 0); + assert(mat->rows > 0); + fprintf(f, "\t\\begin{pmatrix}\n"); + for (row = 0; row < mat->rows; ++row) { + fprintf(f, "\t %6d", *p++); + for (col = 1; col < mat->cols; ++col) { + fprintf(f, "& %6d", *p++); + } + fprintf(f, "\\\\\n"); + } + fprintf(f, "\t\\end{pmatrix}\n"); +} + +static void dump_edge_costs(pbqp *pbqp) +{ + unsigned src_index; + + assert(pbqp); + assert(pbqp->dump_file); + + fputs("

", pbqp->dump_file); + for (src_index = 0; src_index < pbqp->num_nodes; ++src_index) { + pbqp_node *src_node = get_node(pbqp, src_index); + unsigned edge_index; + unsigned len = ARR_LEN(src_node->edges); + for (edge_index = 0; edge_index < len; ++edge_index) { + pbqp_edge *edge = src_node->edges[edge_index]; + unsigned tgt_index = edge->tgt; + if (src_index < tgt_index) { + fputs("\n", pbqp->dump_file); + fprintf(pbqp->dump_file, "\t\\overline\n{C}_{%d,%d}=\n", + src_index, tgt_index); + dump_matrix(pbqp->dump_file, edge->costs); + fputs("
", pbqp->dump_file); + } + } + } + fputs("

", pbqp->dump_file); +} + +static void dump_node_costs(pbqp *pbqp) +{ + unsigned index; + + assert(pbqp); + assert(pbqp->dump_file); + + /* dump node costs */ + fputs("

", pbqp->dump_file); + for (index = 0; index < pbqp->num_nodes; ++index) { + pbqp_node *node = get_node(pbqp, index); + fprintf(pbqp->dump_file, "\tc%d = ", index); + dump_vector(pbqp->dump_file, node->costs); + fputs("
\n", pbqp->dump_file); + } + fputs("

", pbqp->dump_file); +} + +static void dump_section(FILE *f, int level, char *txt) +{ + assert(f); + + fprintf(f, "%s\n", level, txt, level); +} + +void dump_graph(pbqp *pbqp) +{ + unsigned src_index; + + assert(pbqp != NULL); + assert(pbqp->dump_file != NULL); + + fputs("

\n\n\tgraph input {\n", pbqp->dump_file); + for (src_index = 0; src_index < pbqp->num_nodes; ++src_index) { + fprintf(pbqp->dump_file, "\t n%d;\n", src_index); + } + + for (src_index = 0; src_index < pbqp->num_nodes; ++src_index) { + pbqp_node *node = get_node(pbqp, src_index); + unsigned len = ARR_LEN(node->edges); + unsigned edge_index; + for (edge_index = 0; edge_index < len; ++edge_index) { + unsigned tgt_index = node->edges[edge_index]->tgt; + + if (src_index < tgt_index) { + fprintf(pbqp->dump_file, "\t n%d -- n%d;\n", src_index, + tgt_index); + } + } + } + fputs("\t}\n\n

\n", pbqp->dump_file); +} + +void dump_input(pbqp *pbqp) +{ + assert(pbqp); + assert(pbqp->dump_file); + + dump_section(pbqp->dump_file, 1, "1. PBQP Problem"); + dump_section(pbqp->dump_file, 2, "1.1 Topology"); + dump_graph(pbqp); + dump_section(pbqp->dump_file, 2, "1.2 Cost Vectors"); + dump_node_costs(pbqp); + dump_section(pbqp->dump_file, 2, "1.3 Cost Matrices"); + dump_edge_costs(pbqp); +} diff --git a/html_dumper.h b/html_dumper.h new file mode 100644 index 000000000..5b7ac2d78 --- /dev/null +++ b/html_dumper.h @@ -0,0 +1,8 @@ +#ifndef KAPS_HTML_DUMPER_H +#define KAPS_HTML_DUMPER_H + +#include "pbqp_t.h" + +void dump_input(pbqp *pbqp); + +#endif /* KAPS_HTML_DUMPER_H */ diff --git a/kaps.c b/kaps.c index b3beff6a7..7a819e498 100644 --- a/kaps.c +++ b/kaps.c @@ -1,35 +1,36 @@ #include "adt/array.h" #include "kaps.h" +#include "matrix.h" +#include "pbqp_edge.h" #include "pbqp_edge_t.h" #include "pbqp_node.h" #include "pbqp_node_t.h" #include "vector.h" -pbqp_node *get_node(pbqp *pbqp, int index) +pbqp_node *get_node(pbqp *pbqp, unsigned index) { return pbqp->nodes[index]; } -pbqp_edge *get_edge(pbqp *pbqp, int src_index, int tgt_index) +pbqp_edge *get_edge(pbqp *pbqp, unsigned src_index, unsigned tgt_index) { int i; int len; - if (src_index < tgt_index) { + if (tgt_index < src_index) { return get_edge(pbqp, tgt_index, src_index); } pbqp_node *src_node = get_node(pbqp, src_index); assert(src_node); - pbqp_node *tgt_node = get_node(pbqp, tgt_index); - assert(tgt_node); + assert(get_node(pbqp, tgt_index)); len = ARR_LEN(src_node->edges); for (i = 0; i < len; ++i) { pbqp_edge *cur_edge = src_node->edges[i]; - if (cur_edge->tgt == tgt_node) { + if (cur_edge->tgt == tgt_index) { return cur_edge; } } @@ -37,7 +38,7 @@ pbqp_edge *get_edge(pbqp *pbqp, int src_index, int tgt_index) return NULL; } -pbqp *alloc_pbqp(int number_nodes) +pbqp *alloc_pbqp(unsigned number_nodes) { pbqp* pbqp = xmalloc(sizeof(*pbqp)); @@ -57,24 +58,37 @@ void free_pbqp(pbqp *pbqp) xfree(pbqp); } -void add_node_costs(pbqp *pbqp, int node_index, vector *costs) +void add_node_costs(pbqp *pbqp, unsigned node_index, vector *costs) { pbqp_node *node = get_node(pbqp, node_index); if (node == NULL) { node = alloc_node(pbqp, costs); + pbqp->nodes[node_index] = node; } else { vector_add(node->costs, costs); } } -void add_edge_costs(pbqp *pbqp, int src_index, int tgt_index, matrix *costs) +void add_edge_costs(pbqp *pbqp, unsigned src_index, unsigned tgt_index, + pbqp_matrix *costs) { pbqp_edge *edge = get_edge(pbqp, src_index, tgt_index); if (edge == NULL) { edge = alloc_edge(pbqp, src_index, tgt_index, costs); } else { - matrix_add(edge->costs, costs); + pbqp_matrix_add(edge->costs, costs); } } + +num get_solution(pbqp *pbqp) +{ + return pbqp->solution; +} + +void set_dumpfile(pbqp *pbqp, FILE *f) +{ + assert(pbqp); + pbqp->dump_file = f; +} diff --git a/kaps.h b/kaps.h index 34191778d..41851fb69 100644 --- a/kaps.h +++ b/kaps.h @@ -6,7 +6,7 @@ /** * Create an empty PBQP instance with the given number of nodes. */ -pbqp* alloc_pbqp(int number_nodes); +pbqp* alloc_pbqp(unsigned number_nodes); /** * Free the given PBQP. @@ -16,14 +16,18 @@ void free_pbqp(pbqp *pbqp); /** * Add costs vector to given node. */ -void add_node_costs(pbqp *pbqp, int node_index, vector *costs); +void add_node_costs(pbqp *pbqp, unsigned node_index, vector *costs); /** * Add costs matrix between given nodes. */ -void add_edge_costs(pbqp *pbqp, int src_index, int tgt_index, matrix *costs); +void add_edge_costs(pbqp *pbqp, unsigned src_index, unsigned tgt_index, pbqp_matrix *costs); -pbqp_edge *get_edge(pbqp *pbqp, int src_index, int tgt_index); -pbqp_node *get_node(pbqp *pbqp, int index); +pbqp_edge *get_edge(pbqp *pbqp, unsigned src_index, unsigned tgt_index); +pbqp_node *get_node(pbqp *pbqp, unsigned index); + +num get_solution(pbqp *pbqp); + +void set_dumpfile(pbqp *pbqp, FILE *f); #endif /* KAPS_KAPS_H */ diff --git a/matrix.c b/matrix.c index 8356af016..f6b535623 100644 --- a/matrix.c +++ b/matrix.c @@ -3,11 +3,33 @@ #include "pbqp_t.h" #include "matrix.h" -matrix *matrix_copy(pbqp *pbqp, matrix *m) +pbqp_matrix *pbqp_matrix_alloc(pbqp *pbqp, unsigned rows, unsigned cols) +{ + pbqp_matrix *mat; + unsigned index; + + assert(cols> 0); + assert(rows> 0); + + unsigned length = rows * cols; + + mat = obstack_alloc(&pbqp->obstack, sizeof(*mat) + sizeof(num) * (length - 1)); + assert(mat); + + mat->cols = cols; + mat->rows = rows; + for (index = 0; index < length; ++index) { + mat->entries[index] = 0; + } + + return mat; +} + +pbqp_matrix *pbqp_matrix_copy(pbqp *pbqp, pbqp_matrix *m) { int i; int len; - matrix *copy = obstack_alloc(&pbqp->obstack, sizeof(*copy)); + pbqp_matrix *copy = obstack_alloc(&pbqp->obstack, sizeof(*copy)); assert(copy); @@ -20,7 +42,7 @@ matrix *matrix_copy(pbqp *pbqp, matrix *m) return copy; } -void matrix_add(matrix *sum, matrix *summand) +void pbqp_matrix_add(pbqp_matrix *sum, pbqp_matrix *summand) { int i; int len; @@ -36,3 +58,12 @@ void matrix_add(matrix *sum, matrix *summand) sum->entries[i] += summand->entries[i]; } } + +void pbqp_matrix_set(pbqp_matrix *mat, unsigned row, unsigned col, num value) +{ + assert(mat); + assert(col < mat->cols); + assert(row < mat->rows); + + mat->entries[row * mat->cols + col] = value; +} diff --git a/matrix.h b/matrix.h index 6b5360d65..d4337736f 100644 --- a/matrix.h +++ b/matrix.h @@ -3,10 +3,14 @@ #include "matrix_t.h" +pbqp_matrix *pbqp_matrix_alloc(pbqp *pbqp, unsigned rows, unsigned cols); + /* Copy the given matrix. */ -matrix *matrix_copy(pbqp *pbqp, matrix *m); +pbqp_matrix *pbqp_matrix_copy(pbqp *pbqp, pbqp_matrix *m); /* sum += summand */ -void matrix_add(matrix *sum, matrix *summand); +void pbqp_matrix_add(pbqp_matrix *sum, pbqp_matrix *summand); + +void pbqp_matrix_set(pbqp_matrix *mat, unsigned row, unsigned col, num value); #endif /* KAPS_MATRIX_H */ diff --git a/matrix_t.h b/matrix_t.h index f1435c4fe..bf4cfc4f9 100644 --- a/matrix_t.h +++ b/matrix_t.h @@ -1,12 +1,14 @@ #ifndef KAPS_MATRIX_T_H #define KAPS_MATRIX_T_H -typedef struct matrix matrix; +#include "pbqp_t.h" -struct matrix { - int rows; - int cols; - int entries[]; +typedef struct pbqp_matrix pbqp_matrix; + +struct pbqp_matrix { + unsigned rows; + unsigned cols; + num entries[]; }; #endif /* KAPS_MATRIX_T_H */ diff --git a/pbqp_edge.c b/pbqp_edge.c index e59b7e825..d94ade99c 100644 --- a/pbqp_edge.c +++ b/pbqp_edge.c @@ -9,7 +9,7 @@ #include "pbqp_node_t.h" #include "pbqp_t.h" -pbqp_edge *alloc_edge(pbqp *pbqp, int src_index, int tgt_index, matrix *costs) +pbqp_edge *alloc_edge(pbqp *pbqp, int src_index, int tgt_index, pbqp_matrix *costs) { if (tgt_index < src_index) { return alloc_edge(pbqp, tgt_index, src_index, costs); @@ -20,22 +20,20 @@ pbqp_edge *alloc_edge(pbqp *pbqp, int src_index, int tgt_index, matrix *costs) pbqp_node *src_node = get_node(pbqp, src_index); assert(src_node); - edge->src = src_node; pbqp_node *tgt_node = get_node(pbqp, tgt_index); assert(tgt_node); - edge->tgt = tgt_node; - edge->costs = matrix_copy(pbqp, costs); + edge->costs = pbqp_matrix_copy(pbqp, costs); /* * Connect edge with incident nodes. Since the edge is allocated, we know * that it don't appear in the edge lists of the nodes. */ ARR_APP1(pbqp_edge *, src_node->edges, edge); - edge->src = src_node; + edge->src = src_index; ARR_APP1(pbqp_edge *, tgt_node->edges, edge); - edge->tgt = tgt_node; + edge->tgt = tgt_index; return edge; } diff --git a/pbqp_edge.h b/pbqp_edge.h index 8679f17b5..67e8d603c 100644 --- a/pbqp_edge.h +++ b/pbqp_edge.h @@ -3,6 +3,6 @@ #include "pbqp_t.h" -pbqp_edge *alloc_edge(pbqp *pbqp, int src_index, int tgt_index, matrix *costs); +pbqp_edge *alloc_edge(pbqp *pbqp, int src_index, int tgt_index, pbqp_matrix *costs); #endif /* KAPS_PBQP_EDGE_H */ diff --git a/pbqp_edge_t.h b/pbqp_edge_t.h index 955774238..4f1b3fdd3 100644 --- a/pbqp_edge_t.h +++ b/pbqp_edge_t.h @@ -4,9 +4,9 @@ #include "pbqp_t.h" struct pbqp_edge { - pbqp_node *src; /* Source node. */ - pbqp_node *tgt; /* Target node. */ - matrix *costs; /* Cost matrix. */ + unsigned src; /* Source index. */ + unsigned tgt; /* Target index. */ + pbqp_matrix *costs; /* Cost matrix. */ }; #endif /* KAPS_PBQP_EDGE_T_H */ diff --git a/pbqp_t.h b/pbqp_t.h index 2a79aff99..dcda3479f 100644 --- a/pbqp_t.h +++ b/pbqp_t.h @@ -2,25 +2,27 @@ #define KAPS_PBQP_T_H #include +#include #include "adt/obstack.h" +typedef int num; + #include "matrix_t.h" #include "vector_t.h" -typedef int num; - typedef struct pbqp_edge pbqp_edge; typedef struct pbqp_node pbqp_node; typedef struct pbqp pbqp; -static const num INF_COST = INT_MAX; +static const num INF_COSTS = INT_MAX; struct pbqp { struct obstack obstack; /* Obstack. */ num solution; /* Computed solution. */ size_t num_nodes; /* Number of PBQP nodes. */ pbqp_node **nodes; /* Nodes of PBQP. */ + FILE *dump_file; /* File to dump in. */ }; #endif /* KAPS_PBQP_T_H */ diff --git a/vector.c b/vector.c index ed7d1ca95..0459afa4c 100644 --- a/vector.c +++ b/vector.c @@ -1,7 +1,28 @@ #include "adt/array.h" +#include "pbqp_t.h" #include "vector.h" +vector *vector_alloc(pbqp *pbqp, unsigned length) +{ + vector *vec; + unsigned index; + + assert(length > 0); + vec = obstack_alloc(&pbqp->obstack, sizeof(*vec) + sizeof(vec_elem) * (length - 1)); + assert(vec); + + vec->len = length; + for (index = 0; index < length; ++index) { + vec->entries[index].data = 0; +#if EXT_GRS_DEBUG + vec->entries[index].name = NULL; +#endif + } + + return vec; +} + vector *vector_copy(pbqp *pbqp, vector *v) { int i; @@ -31,6 +52,20 @@ void vector_add(vector *sum, vector *summand) len = sum->len; for (i = 0; i < len; ++i) { - sum->entries[i] += summand->entries[i]; + sum->entries[i].data += summand->entries[i].data; } } + +void vector_set(vector *vec, unsigned index, num value) +{ + assert(index < vec->len); + vec->entries[index].data = value; +} + +#if EXT_GRS_DEBUG +void vector_set_description(vector *vec, unsigned index, char *name) +{ + assert(index < vec->len); + vec->entries[index].name = name; +} +#endif diff --git a/vector.h b/vector.h index 410bd3a8b..3ab5bc67e 100644 --- a/vector.h +++ b/vector.h @@ -3,10 +3,18 @@ #include "vector_t.h" +vector *vector_alloc(pbqp *pbqp, unsigned length); + /* Copy the given vector. */ vector *vector_copy(pbqp *pbqp, vector *v); /* sum += summand */ void vector_add(vector *sum, vector *summand); +void vector_set(vector *vec, unsigned index, num value); + +#if EXT_GRS_DEBUG +void vector_set_description(vector *vec, unsigned index, char *name); +#endif + #endif /* KAPS_VECTOR_H */ diff --git a/vector_t.h b/vector_t.h index 6262c01c6..3024e03ef 100644 --- a/vector_t.h +++ b/vector_t.h @@ -1,14 +1,24 @@ #ifndef KAPS_VECTOR_T_H #define KAPS_VECTOR_T_H +#include "../debug.h" + #include "pbqp_t.h" -struct vector; +typedef struct vec_elem vec_elem; + +struct vec_elem { + num data; +#if EXT_GRS_DEBUG + char *name; +#endif +}; + typedef struct vector vector; struct vector { - int len; - int entries[]; + unsigned len; + vec_elem entries[]; }; #endif /* KAPS_VECTOR_T_H */