Gordon Burditt wrote:
[color=blue][color=green]
>>#include <bar.h> <foo>
>>
>>Where the code now says explicitly that the include bar.h is from
>>a package known as foo. Note, no paths in the include - the
>>include file is specified by WHAT it is and not by WHERE it is.
>>To support this the language needs only a minor extension - a
>>way to map a text file containing the list of packages to
>>their locations so that the compiler can pull in the right file.[/color]
>
>
> This sounds like an absolute nightmare to maintain, for a lot
> of reasons. It might work reasonably well if nobody using the
> compiler is allowed to write their own code, and everyone used
> package installers, but that sort of defeats the purpose of a
> compiler, doesn't it?
>
> 1. You need a global package naming registry. Yes, I really mean
> *GLOBAL*, if not intergalactic. And how many compilers support
> use of Chinese character sets in package names?[/color]
This differs how from the current situation? Where you either
have GL,X11 or the like in the path for the #include or on the
command line.
[color=blue]
> 2. Developers of code that is logically divided up need to get a
> package name from the package naming registry BEFORE THEY CAN
> CODE ANYTHING THAT USES IT.[/color]
No more so than now. If you write code that uses a GL path
to your includes, and it isn't OpenGL it will break with either model.
If avoiding conflicts was an issue one could always use a name
like: foo_xxxxxxxx, where xxxxxxxx is a bunch of random digits.
Then in the project map file use:
#define foo foo_xxxxxxxx
and you'll get the desired includes for the short
descriptive string "foo".
Honestly I don't see how #package leads to more conflicts than
does #include, basically they are handling the same data, just
in slightly different ways.
[color=blue]
> 3. You have a file that NEEDS to be edited by all those developing
> code, but one screwup can cause everyone's code to quit working,
> which begs for it to be writable by the administrator only.
> There's also the issue of how you keep it under source code control
> when pieces of the file each belong to different packages under
> development.[/color]
That's a good point. I suppose one could instead define a directory
where a bunch of these files live independent of each other and
read them all in as ordered by the #package statements.
(Ie, more or less like the existing include directories.) Just be
careful about overwriting existing files. In that
variant
#package X11
is pretty much equivalent to
#ifndef _loaded_X11
#include X11
#define _loaded_X11
#endif
except that the compiler handles the guard variables as part
of the language and the programmer doesn't need to do it explicitly
in the preprocessor as in the this example.
[color=blue]
> 4. There is no obvious way to merge these files from various packages,
> or to delete entries if you delete a package.[/color]
That's compiler and platform dependent, just like the existing
command line library declarations and search path declarations.
[color=blue]
> 5. This setup if used for self-reference (e.g. the foo package references
> its own include files with #include <foo> <bar.h>) makes absolutely
> sure you can't have a production and a test version of the same package
> that can co-exist.[/color]
That was the point of ...
[color=blue][color=green]
>>/* Enable the use of alternative include paths for packages,
>>for instance on development systems. This would not be
>>common. */
>>#if USEALT[/color]
>
>
> Where, pray tell, is USEALT supposed to be defined or not
> defined?[/color]
On the command line (or equivalent), so that the developer can
tell the compiler which set of includes to use.
[color=blue][color=green]
>>#package X11[/color]
>
>
> Oh, great! Now I not only have to merge the stuff from a bunch of
> packages, but I *HAVE TO MERGE THEM IN THE RIGHT ORDER!* And there
> might not even *BE* a right order, due to possible circular dependencies.[/color]
How does this differ from the current #include method? Try rearranging
the #include statements in a lot of code and you'll run into exactly
the same sorts of order dependencies. Use the reinterpretation of
#package to be the "include and set up guard variables implicitly"
as in the example above. What's the problem with that?
Your point about circular dependencies is valid - as originally
proposed it would be possible to define maps that could not
be loaded. Ie, A requires B be loaded, B requires A be loaded,
so neither can be loaded. Worse, I have actually seen cases
where packages are mutually dependent and cross include files
from each other. So there would need to be a mechanism to
handle this. The simplest one would be for such poorly written
packages to not use a package requirement statement for the other
package, that would suspend the check.
Ideally people wouldn't write this sort of code though.
[color=blue]
>
>
> And how does the software that does that know where the default map *IS*?[/color]
That's up to the compiler. Just like the compiler has to know
where the default includes are now.
[color=blue][color=green]
>>
>>#package X11
>>#package GL
>>#define THISPACKAGE "."
>>#package foo <THISPACKAGE/foo>
>>#package woo <THISPACKAGE/woo>[/color]
>
>
> Oh, yes, where exactly is "." when this set of specifications gets
> merged into the default system map when the package is installed?[/color]
The same problem currently obtains with include statements. Package
is no better and no worse in that regard.
[color=blue]
>
> Ok, how do I write a package specification that says I want
> GD version 1 *OR* GD version 2? They have different package names
> because they are so different, but my code knows how to handle
> either.[/color]
That is also a good point. You've doubtless seen some
pretty hairy tests in configure files trying to handle this
exact problem. Moreover, I've seen plenty of those hairy tests
fail because they couldn't figure that 2.2b was bigger than 2.1.
There's more to it, if both are present you might
prefer the most recent one. However when multiple versions
are present they invariably live in different places, so
#package foo path
would allow you to select the desired one. Writing this package
line would likely have to be done by a "configure" equivalent.
It might be good though to have something like
cmp_version(foo,version) ->
-1 0 1, so that the compiler could determine
with preprocessor statements when an unexpected version has been
encountered. That suggests:
#package foo path version
to define an explicit version number to go with the path.
[color=blue]
>
> It's NOT unambiguous without a global package registry, and even
> then, it precludes the possibility of having multiple versions of
> the same package available and being able to select one, as can
> be done now with things like "-I/usr/local/mysql5.1.82.3.5.6.7.2z/include"
> included in a Makefile.[/color]
#package mysql "/usr/local/mysql5.1.82.3.5.6.7.2z/include"
or
/* from default package file */
#package mysql 5.1.82
/* the software under development does */
#package mysql /* compiler uses default version */
#if (mysql,5.1.82) != 0
whatever
Probably version would have to be restricted to X.Y.Z format, or
even a plain integer. In my experience too much flexibility with
version numbers causes a lot of grief.
I'm not stating that this particular syntax is the best, it's just
an idea for discussion.
Regards,
David Mathog
mathog@caltech.edu