[jhc] including C source files?

David Roundy daveroundy at gmail.com
Wed Sep 23 09:49:44 EDT 2009


On Wed, Sep 23, 2009 at 12:55 AM, John Meacham <john at repetae.net> wrote:
> On Fri, Sep 18, 2009 at 05:35:59PM -0400, David Roundy wrote:
>> This has the downside that the source code isn't portable to ghc,
>> which a pretty serious drawback.  Perhaps one answer is to teach
>> franchise to create a module that reexports stuff from Jhc.Options if
>> that is available, but that seems like a pretty heavy-weight answer
>> that is also extremely limited.
>
> Yeah. I figure a file with things like
>
> #if defined(__GHC__) && defined(__WIN32__)
> isWindows = True
> #else
> isWindows = False
> #endif
>
> could be included for other compilers. Franchise shouldn't have to do
> anything in particular other than include that module (which will just
> re-export Jhc.Options on jhc).

Yeah, that would be a reasonable approach.

> This is actually less of a limitation than it seems, even if arch
> specific hls are necessary, since jhc is a native cross compiler it can
> just generate hls for as many different OSes and configuration options
> as needed. So populating an hl repository wouldn't require wrangling
> dozens of different compilation environments.

Yeah, it'd be nice to have a standard way to distinguish between those
hls, either by the flag mentioned below, or just by making the library
search path target-OS-dependent.  The latter I could do within
franchise, but it'd be nicer to have that built into the default jhc
search path, so

jhc --list-libraries --cross -mwin32

would list the libraries in the win32 path (but not any unix-specific
ones--assuming we're on a unixy OS), and

jhc --list-libraries

would not list the win32-specific libraries.

Again, I could work around this by making franchise modify JHC_PATH,
but it'd be better to use the targets.ini framework within jhc, so
that franchise-installed libraries can be easily used with
non-franchise builds and vice versa.

>> And no, I don't have a good answer to any of these questions, except
>> to suggest probably libraries will *need* to support separate
>> compilation for separate targets.  Of course, one could already do
>> that by manipulating the JHC_PATH to maintain two sets of library
>> installations, but it'd be nice to have something like that supported
>> natively.  For instance, we could have platform-specific
>> subdirectories of directories within the path, so that franchise could
>> specify that a given library (which was built with a preproc
>> configuration for win32) will be put in the win32-specific path.
>
> yeah. I have a field in the library header to indicate if it was
> compiled in a platform-specific way. I don't currently set it to
> anything though. it actually includes the arch flags in the computation
> of the library hash, so its hash won't conflict with an incompatible
> build.

Is this something that we could define whenever --cross is used in
building an hl? That would seem quite reasonable to me...

>> Which reminds me... is there a way to store in a .hl file what
>> libraries it's to be linked with?
>
> C libraries? if you include them in foreign imports like so
>
> foreign import ccall "-lm math.h sinf" sinf :: Float -> Float
>
> then they will be propegated and linked against. This obviously isn't
> always ideal. What would be the best way to handle this do you think?

There are a couple of issues with this foreign import syntax.  One is
that it is jhc-specific, which precludes using it in portable
libraries (unless it's #ifdeffed, which is a pain).  Another is that
it is not always easy to figure out what the libraries are called (or
which ones are needed), so you might still need franchise or autoconf
to figure that out, and then it seems backwards to have to generate
your source code to include that information.  Of course, generating
the source could would have the advantage of making it easier to port
to other compilers, since you could just leave the -lm out if you
aren't building with jhc.  But usually it's easier and more flexible
(and intuitive) for a configure/build system to adjust the compile
command line rather than generating source code.

So I'd suggest recording any --optc=XXX flags in the .hl, and then
using those during the ultimate compile of an executable.  --optc is
otherwise meaningless on hl generation, since the C compiler is never
invoked, so this would allow franchise (or someone compiling by hand)
to specify any -l or -L flags that need to be passed to the compiler.
It would also allow "evil" things like changing the optimization
level, etc, but on the third (or fourth?) hand would allow users to
define preprocessor directives, etc.  A downside of this is that your
final gcc flags will be the concatenation those of all hl libraries
you use, so library writers will need to be cautious that their --optc
flags are idempotent and unlikely to conflict with other flags.  But
that's quite a reasonable constraint, I'd say.
-- 
David Roundy


More information about the jhc mailing list