This is the mail archive of the
gcc@gcc.gnu.org
mailing list for the GCC project.
Re: Projects for beginners
- To: fjh at cs dot mu dot oz dot au
- Subject: Re: Projects for beginners
- From: kenner at vlsi1 dot ultra dot nyu dot edu (Richard Kenner)
- Date: Fri, 2 Feb 01 11:02:53 EST
- Cc: gcc at gcc dot gnu dot org
Now suppose I want to add a new routine which prints an integer to a
file. This routine takes a parameter of type `FILE *', so this header
now has a dependency on <stdio.h>.
Your suggested policy would forbid me from adding this routine to the
header file. What should I do instead?
In this case, we'd say that requiring stdio.h is acceptable (or else
protect it with an #ifdef BUFSIZ) like we do now.
The point is to organize things in hierarchies so that higher level things
get built on lower-level things.
We then make a "gcc.h" that includes all the low-level things.
I see two approaches here from a formal point of view.
The first is that we can think of a header file as a specification of some
facility. That facility depends one some other facilities in a way that we
don't need the user of a facility to bother with. This is very much like the
concept of packages in Ada and similar languages.
If we do this then indeed each such file needs "guards". However, to
do this we need one .h file for each .c file to provide the interface to it.
I'm not against reorganizing the include files in this manner, but it's a
large job and involves far more than adding guards. Doing it right would
likely even mean moving functions around and splitting up some file.
I think that would be a major improvement in the compiler, but, as I said,
it a very large job and one that actually requires quite a bit of
detailed knowlege of the compiler.
The other approach is more in line with the current structure of the header
files, which are more oriented towards concepts and levels of hierarchy.
So we have low-level things such as bitmaps, machine modes, etc. Then we
have RTL and trees. Then we have various interface routines.
Each part of the compiler either operates on RTL, trees, or both. Depending
on which is the case, it would include one or three "core" include files.
Then it includes the files for whichever high level things it needs.
In this case, you don't need guards because you've structured things in
a clean hierarchical method.
My concern with guards is that if we don't go to the full first scheme, it's
going to be too easy to have accidental "level violations" given the somewhat
ad-hoc structure of our .h files.