matcom, dot with main

This commit is contained in:
fiplox 2022-01-02 16:48:29 +01:00
parent e075ac2da3
commit 0dc4ee873e
11 changed files with 277 additions and 84 deletions

View File

@ -51,9 +51,9 @@ distdir: $(DISTFILES)
$(CP) $(DISTFILES) $(distdir)
clean:
$(RM) $(OBJS) out.pdf
$(RM) $(OBJS)
fclean: clean
$(RM) $(NAME)
$(RM) $(NAME) out.pdf graph.dot
.PHONY: all clean fclean re dist distdir debug

View File

@ -7,19 +7,23 @@
#include <string.h>
#include "cparse.h"
graph_vec find_funcs(const char *path, graph_vec *g)
void find_funcs(const char *path, graph_vec *gv, graph_mco *gmc)
{
FILE *fp;
regex_t fdre, fcre;
int ret;
int ret, index, cur_node;
char line[1024];
char boum[1024];
char *token;
regmatch_t rm[2];
// TODO: rework regex to ignore static char *(spo_name_tab[SPO_COUNT]) =
// { "ms=", "me=", "hs=", "he=", "rs=", "re=", "lc=" };
const char *re_func_decl = "^(\\w+(\\s+)?\\ ?\\**\\ ?){2,}\\([^!@#$+%^]+?\\)\\s+";
bool in;
(void)gmc;
const char *re_func_decl = "^(\\**\\w+\\s+?\\ ?\\ ?){1,}\\([^!@#$+%^]+?\\)\\s+";
const char *re_func_call = "([a-zA-Z_0-9]+)\\(.*\\)";
token = malloc(1024 * sizeof(char));
char *ptrtok = token;
fp = fopen(path, "r");
if (fp == 0) {
fprintf(stderr, "Failed to open file '%s' (%d: %s)\n", path, errno, strerror(errno));
@ -37,9 +41,7 @@ graph_vec find_funcs(const char *path, graph_vec *g)
fclose(fp);
exit(2);
}
bool in = false;
int index;
int cur_node;
in = false;
while ((fgets(line, 1024, fp)) != NULL) {
if (in && line[0] == '}') {
in = false;
@ -47,41 +49,60 @@ graph_vec find_funcs(const char *path, graph_vec *g)
if (in) {
if (regexec(&fcre, line, 2, rm, 0) == 0) {
// printf("Line: <<%.*s>>\n", (int)(rm[0].rm_eo - rm[0].rm_so), line + rm[0].rm_so);
sprintf(boum, "%.*s", (int)(rm[1].rm_eo - rm[1].rm_so), line + rm[1].rm_so);
sprintf(token, "%.*s", (int)(rm[1].rm_eo - rm[1].rm_so), line + rm[1].rm_so);
if (strcmp(token, "defined") == 0)
continue;
// printf("%.*s\n", (int)(rm[1].rm_eo - rm[1].rm_so), line + rm[1].rm_so);
if ((index = vis_in(*g, boum)) > -1) {
if (g->node[cur_node]->nbs == g->node[cur_node]->cap)
g->node[cur_node]->succ =
reallocarray(g->node[cur_node]->succ, (g->node[cur_node]->cap += 5), sizeof(nodept));
g->node[cur_node]->succ[g->node[cur_node]->nbs] = g->node[index];
g->node[cur_node]->nbs++;
if ((index = vis_in(*gv, token)) > -1) {
if (gv->node[cur_node]->nbs == gv->node[cur_node]->cap)
gv->node[cur_node]->succ =
reallocarray(gv->node[cur_node]->succ, (gv->node[cur_node]->cap += 5), sizeof(nodept));
gv->node[cur_node]->succ[gv->node[cur_node]->nbs] = gv->node[index];
gv->node[cur_node]->nbs++;
mcinsert_edge(gmc, cur_node, index);
} else {
vinsert_node(g, boum);
if (g->node[cur_node]->nbs == g->node[cur_node]->cap)
g->node[cur_node]->succ =
reallocarray(g->node[cur_node]->succ, (g->node[cur_node]->cap += 5), sizeof(nodept));
g->node[cur_node]->succ[g->node[cur_node]->nbs] = g->node[g->n];
g->node[cur_node]->nbs++;
vinsert_node(gv, token);
if (gv->node[cur_node]->nbs == gv->node[cur_node]->cap)
gv->node[cur_node]->succ =
reallocarray(gv->node[cur_node]->succ, (gv->node[cur_node]->cap += 5), sizeof(nodept));
gv->node[cur_node]->succ[gv->node[cur_node]->nbs] = gv->node[gv->n];
gv->node[cur_node]->nbs++;
mcinsert_func(gmc, token);
mcinsert_edge(gmc, cur_node, -1);
}
}
} else if (regexec(&fdre, line, 2, rm, 0) == 0) { // function definition
sprintf(boum, "%.*s", (int)(rm[1].rm_eo - rm[1].rm_so), line + rm[1].rm_so);
if ((index = vis_in(*g, boum)) > -1) {
// printf("Line: <<%.*s>>\n", (int)(rm[0].rm_eo - rm[0].rm_so), line + rm[0].rm_so);
sprintf(token, "%.*s", (int)(rm[1].rm_eo - rm[1].rm_so), line + rm[1].rm_so);
// printf("%.*s\n", (int)(rm[1].rm_eo - rm[1].rm_so), line + rm[1].rm_so);
if (strcmp(token, "defined") == 0)
continue;
while (*token == '*')
token++;
if ((index = vis_in(*gv, token)) > -1) {
cur_node = index;
} else {
vinsert_node(g, boum);
cur_node = g->n;
// printf("%s\n", token);
vinsert_node(gv, token);
mcinsert_func(gmc, token);
cur_node = gv->n;
}
in = true;
}
}
token = ptrtok;
if (token) {
free(token);
}
regfree(&fdre);
regfree(&fcre);
fclose(fp);
return *g;
}
void findAndParse(const char *path, graph_vec *g)
void findAndParse(const char *path, graph_vec *gv, graph_mco *gmc)
{
char p[1024];
struct dirent *dp;
@ -95,14 +116,14 @@ void findAndParse(const char *path, graph_vec *g)
if (strncmp(dp->d_name, ".", 1) == 0)
continue;
snprintf(p, sizeof(p), "%s/%s", path, dp->d_name);
findAndParse(p, g);
findAndParse(p, gv, gmc);
} else {
char *f = strrchr(dp->d_name, '.');
if (f) {
if (strncmp(f, ".c", 2) == 0) {
char pa[255];
char pa[512];
sprintf(pa, "%s/%s", path, dp->d_name);
find_funcs(pa, g);
find_funcs(pa, gv, gmc);
}
}
}

View File

@ -1,4 +1,12 @@
#include "vec.h"
#ifndef CPARSE_H
void findAndParse(const char *path, graph_vec *g);
graph_vec find_funcs(const char *path, graph_vec *g);
#define CPARSE_H
#include "vec.h"
#include "matcom.h"
void findAndParse(const char *path, graph_vec *gv, graph_mco *gmc);
void find_funcs(const char *path, graph_vec *gv, graph_mco *gmc);
#endif /* end of include guard: CPARSE_H */

Binary file not shown.

View File

@ -15,24 +15,37 @@
// along with this program. If not, see <http://www.gnu.org/licenses/>.
#include "cparse.h"
#include "matcom.h"
#include "vec.h"
#include <stdio.h>
#include <string.h>
int main(int argc, char *argv[])
{
(void)argc;
(void)argv;
graph_vec g = vnew_graph();
// find_funcs("/home/user/dev/l2/algo2/pattern-search/src/rgxp.c", &g);
findAndParse("/tmp/neovim/src/nvim", &g);
// for (int j = 0; j <= g.n; j++) {
// printf("NODE %d: '%s'\n", j, g.node[j]->func);
// fix_str m = "main";
graph_vec gv = vnew_graph();
graph_mco gmc = mcgragh();
// find_funcs("/home/user/files/dot_files/st/x.c", &gv, &gmc);
// find_funcs("test.c", &gv, &gmc);
findAndParse("/home/user/files/dot_files/dwm/", &gv, &gmc);
// int n = mcis_in(gmc, m);
// printf("%d\n", n);
// mcprint_edges(gmc, n);
// for (int i = 0; i <= gmc.nbs; i++) {
// printf("Node %d: %s\n", i, gmc.func[i]);
// for (int j = 0; j <= gmc.nba; j++) {
// if (strcmp(gmc.func[i], gmc.func[gmc.vec[j].i]) == 0) {
// printf(" Succ %d: %s\n", gmc.vec[j].j, gmc.func[gmc.vec[j].j]);
// }
// }
// }
// int i = is_in(g, "nvim_buf_get_offset");
// if (i > -1) {
// puts("yes");
// print_node(g.node[i]);
// }
// } else
vdot_graph(g);
vdelete_graph(&g);
// printf("TEST: %s %d\n", gmc.func[2], gmc.vec[2].j);
//
// vprint_nodes(gv.node[n]);
mcdelete_graph(&gmc);
vdot_graph(gv, true);
vdelete_graph(&gv);
return 0;
}

89
src/matcom.c Normal file
View File

@ -0,0 +1,89 @@
#include "matcom.h"
#include <stdlib.h>
#include <assert.h>
#include <string.h>
#include <stdio.h>
graph_mco mcgragh(void)
{
graph_mco g;
g.nbs = -1;
g.nba = -1;
g.func = malloc((g.fcap = 10) * sizeof(fix_str));
assert(g.func);
g.vec = malloc((g.vcap = 10) * sizeof(struct edge));
assert(g.vec);
return g;
}
void mcinsert_func(graph_mco *g, fix_str i)
{
++g->nbs;
if (g->nbs == g->fcap) {
g->func = reallocarray(g->func, (g->fcap += 128), sizeof(fix_str));
assert(g->func);
}
strcpy(g->func[g->nbs], i);
}
void mcinsert_edge(graph_mco *g, int dep, int arr)
{
struct edge e;
++g->nba;
if (g->nba == g->vcap) {
g->vec = reallocarray(g->vec, (g->vcap += 128), sizeof(struct edge));
assert(g->vec);
}
e.i = dep;
if (arr == -1)
e.j = g->nbs;
else
e.j = arr;
g->vec[g->nba] = e;
}
void mcdelete_graph(graph_mco *g)
{
if (g->func)
free(g->func);
if (g->vec)
free(g->vec);
g->func = NULL;
g->vec = NULL;
}
int mcis_in(graph_mco g, fix_str func)
{
int i;
if (g.nba == 0)
return -1;
for (i = 0; i <= g.nba; i++) {
if (strcmp(g.func[i], func) == 0) {
return i;
}
}
return -1;
}
static void mcprint_succ(graph_mco g, int succ)
{
printf(" Succ: %s\n", g.func[succ]);
}
void mcprint_edges(graph_mco g, int n)
{
int i;
printf("NODE %d: %s\n", n, g.func[n]);
for (i = 0; i <= g.nba; ++i) {
if (g.vec[i].i == n) {
mcprint_succ(g, g.vec[i].j);
}
}
for (i = 0; i <= g.nba; ++i) {
if (g.vec[i].i == n) {
if (g.vec[g.vec[i].j].i != -1)
mcprint_edges(g, g.vec[g.vec[i].j].i);
}
}
}

View File

@ -1,3 +1,7 @@
#ifndef MATCOM_H
#define MATCOM_H
typedef char fix_str[256];
typedef struct graph_mco graph_mco;
@ -7,24 +11,19 @@ struct edge {
};
struct graph_mco {
int nbs; // nombre de sommets
int nba; // nombre d'aretes
fix_str *func; // noms de fonction
int nbs; // nombre de sommets
int nba; // nombre d'aretes
int vcap; // capacité de vec
int fcap; // capacité de vec
fix_str *func; // noms de fonction
struct edge *vec; // vecteur d'aretes
};
graph_mco mcgragh(void)
{
graph_mco g;
g.nbs = 0;
g.nba = -1;
g.func = malloc(10 * sizeof(fix_str));
assert(g.func);
g.vec = malloc(10 * sizeof(struct edge));
assert(g.vec);
}
graph_mco mcgragh(void);
void mcinsert_func(graph_mco *g, fix_str i);
void mcinsert_edge(graph_mco *g, int dep, int arr);
void mcdelete_graph(graph_mco *g);
int mcis_in(graph_mco g, fix_str func);
void mcprint_edges(graph_mco g, int n);
void mcinsert_edge(graph_mco *g, fix_str i, int dep, int arr)
{
}
#endif /* end of include guard: MATCOM_H */

View File

@ -4,11 +4,11 @@
#include <stdlib.h>
#include <string.h>
graph_vec vnew_graph(void)
{
graph_vec g;
g.n = -1;
g.n = -1;
g.cap = 10;
g.node = malloc(10 * sizeof(nodept));
assert(g.node);
@ -24,6 +24,7 @@ void vinsert_node(graph_vec *g, fix_str str)
assert(n);
n->num = g->n;
n->nbs = 0;
n->vu = 0;
n->cap = 5;
n->succ = malloc(5 * sizeof(nodept));
strcpy(n->func, str);
@ -60,16 +61,27 @@ int vis_in(graph_vec g, fix_str func)
return -1;
}
void vprint_node(nodept node)
static void vprint_succ(nodept node)
{
// int i;
printf(" Succ: %s\n", node->func);
// for (i = 0; i < node->nbs; ++i) {
// printf("SUCC %d: %s\n", i, node->succ[i]->func);
// }
}
void vprint_nodes(nodept node)
{
int i;
if (node->vu == 1)
return;
node->vu = 1;
printf("NODE: %s\n", node->func);
for (i = 0; i < node->nbs; ++i) {
printf("SUCC %d: %s\n", i, node->succ[i]->func);
vprint_succ(node->succ[i]);
}
for (i = 0; i < node->nbs; ++i) {
if (node->succ[i]->num != node->num && node->succ[i]->nbs != 0)
vprint_node(node->succ[i]);
vprint_nodes(node->succ[i]);
}
}
@ -78,13 +90,28 @@ void vwrite_node_dot(FILE *fp, graph_vec g)
int i, j;
for (i = 0; i <= g.n; i++) {
for (j = 0; j < g.node[i]->nbs; j++) {
// printf("\t%s -> %s;\n", node->func, node->succ[i]->func);
fprintf(fp, "\t%s -> %s;\n", g.node[i]->func, g.node[i]->succ[j]->func);
// printf("\t%s -> %s;\n", node->func, node->succ[i]->func);
fprintf(fp, "\t%s -> %s;\n", g.node[i]->func, g.node[i]->succ[j]->func);
}
}
}
void vdot_graph(graph_vec g)
void main_graph(FILE *fp, nodept node)
{
int i;
if (node->vu == 1)
return;
node->vu = 1;
printf("NODE: %s\n", node->func);
for (i = 0; i < node->nbs; ++i) {
fprintf(fp, "\t%s -> %s;\n", node->func, node->succ[i]->func);
}
for (i = 0; i < node->nbs; ++i) {
main_graph(fp, node->succ[i]);
}
}
void vdot_graph(graph_vec g, bool main)
{
FILE *fp;
@ -92,8 +119,19 @@ void vdot_graph(graph_vec g)
fprintf(fp, "digraph main {\n");
vwrite_node_dot(fp, g);
// write_node_dot(fp, node->succ[2]->succ[1]->succ[0]);
if (main) {
fix_str m = "main";
int n = vis_in(g, m);
if (n != -1) {
main_graph(fp, g.node[n]);
} else {
fprintf(stderr, "main not found.\n");
exit(1);
}
} else {
vwrite_node_dot(fp, g);
}
fprintf(fp, "}");

View File

@ -1,3 +1,7 @@
#ifndef VEC_H
#define VEC_H
#include <stdbool.h>
typedef char fix_str[256];
@ -11,6 +15,7 @@ struct nodes {
};
struct node {
int vu;
int num; // le numero de noeud
int nbs; // nombre de successeurs
fix_str func; // noms de fonctions
@ -22,5 +27,7 @@ graph_vec vnew_graph(void);
void vinsert_node(graph_vec *g, fix_str str);
void vdelete_graph(graph_vec *g);
int vis_in(graph_vec g, fix_str func);
void vprint_node(nodept node);
void vdot_graph(graph_vec g);
void vdot_graph(graph_vec g, bool main);
void vprint_nodes(nodept node);
#endif /* end of include guard: VEC_H */

BIN
src/vec.o

Binary file not shown.

30
test.c
View File

@ -1,5 +1,14 @@
#include <stdio.h>
int aurevoir(void);
void bar(void);
void bonjour(void);
void bye(void);
void hello(void);
void bar(void);
int foo(void);
int toto(int a, int b);
int aurevoir(void)
{
return 42;
@ -13,7 +22,7 @@ void bonjour(void)
void bye(void)
{
puts("Byte...");
puts("Bye...");
}
void hello(void)
@ -23,24 +32,33 @@ void hello(void)
bonjour();
}
void foo(void)
void bar(void)
{
toto(1, 1);
}
int foo(void)
{
hello();
bar();
return 1;
}
int add(int a, int b)
int toto(int a, int b)
{
aurevoir();
if (a != 1)
foo();
else
aurevoir();
return a + b;
}
int main(void)
{
int res;
foo();
res = add(21, 21);
res = toto(21, 21);
printf("%i\n", res);
return 0;