I know there are similar posts but I am having trouble getting the hang of it: I have a .c and a .h file:
graph.c
#ifndef graph
#define graph
/*1. standard headers*/
#include <stdbool.h>
/*2. user-def. headers*/
//#include ".."
/*3. global macros*/
//#define GLOB_MACRO …
/*4. global type decls.*/
struct graph;
typedef struct graph graph_t;
graph_t* graph_create(int n);
void graph_free(graph_t *g);
void graph_insert_edge(graph_t *g, int source, int target, double weight);
void graph_remove_edge(graph_t *g, int source, int target);
bool graph_has_edge(graph_t *g, int source, int target);
double graph_get_weight(graph_t *g, int source, int target);
void graph_print(graph_t *g);
/*5. glob. var. decls.*/
//extern … glob_var;
/*6. glob. func. decls*/
//[extern] … glob_func(…);
#endif
graph_m.c
// Driver Code
int main()
{
printf("test");
return 0;
}
But I get these compiler errors:
gcc -MM graph_m.c > .depend
gcc -pedantic -Wall -Wextra -Wvla -std=c11 -ggdb3 -c -o graph_m.o graph_m.c
In file included from graph_m.c:14:
graph.h:15:13: error: expected '{' before ';' token
15 | struct graph;
| ^
graph.h:16:22: warning: useless storage class specifier in empty declaration
16 | typedef struct graph graph_t;
| ^~~~~~~
graph.h:18:1: error: unknown type name 'graph_t'; use 'struct' keyword to refer to the type
18 | graph_t* graph_create(int n);
| ^~~~~~~
| struct
graph.h:19:17: error: unknown type name 'graph_t'; did you mean 'graph'?
19 | void graph_free(graph_t *g);
| ^~~~~~~
| graph
graph.h:21:24: error: unknown type name 'graph_t'; did you mean 'graph'?
21 | void graph_insert_edge(graph_t *g, int source, int target, double weight);
| ^~~~~~~
| graph
graph.h:22:24: error: unknown type name 'graph_t'; did you mean 'graph'?
22 | void graph_remove_edge(graph_t *g, int source, int target);
| ^~~~~~~
| graph
graph.h:24:21: error: unknown type name 'graph_t'; did you mean 'graph'?
24 | bool graph_has_edge(graph_t *g, int source, int target);
| ^~~~~~~
| graph
graph.h:25:25: error: unknown type name 'graph_t'; did you mean 'graph'?
25 | double graph_get_weight(graph_t *g, int source, int target);
| graph
graph_m.c:24:1: warning: unnamed struct/union that defines no instances
24 | } graph;
| ^
make: *** [<builtin>: graph_m.o] Error 1
root@8c9bf05a5390:/home/swo3/src/graph# In file included from graph_m.c:14:
graph.h:15:13: error: expected '{' before ';' token
15 | struct graph;
| ^
graph.h:16:22: warning: useless storage class specifier in empty declaration
16 | typedef struct graph graph_t;
| ^~~~~~~
graph.h:18:1: error: unknown type name 'graph_t'; use 'struct' keyword to refer to the type
18 | graph_t* graph_create(int n);
| ^~~~~~~
| struct
make: *** [<builtin>: graph_m.o] Error 1union that defines no instances?e weight);
So am I getting the order wrong? I have typedef and struct in play, and different filenames for the actual implementation for the header file, where I want to do two datatstructures in the background for graph.h, graph_m.c and another one.
CodePudding user response:
You have macro names clashing with other names.
You start with this:
#define graph
Then later you have this
struct graph;
Since macros do direct token substitution, after preprocessing the above line becomes:
struct ;
Which is invalid.
You need to change your macro name so it doesn't conflict. By convention, macros are typically uppercase, and header guard macros typically end in _H
. So change the first two lines to:
#ifndef GRAPH_H
#define GRAPH_H
CodePudding user response:
After #define graph
, macro processing replaces struct graph;
with struct ;
.
Use a different identifier for your preprocessor guard, such as graph_h
.