<ItemizedList>
<ListItem>
<Para>
-``Finalise'' is now spelt ``finalize'' in all function names.
+“Finalise” is now spelt “finalize” in all function names.
</Para>
</ListItem>
<Para>
<IndexTerm><Primary>-dppr-user option</Primary></IndexTerm>
<IndexTerm><Primary>-dppr-debug option</Primary></IndexTerm>
-Debugging output is in one of several ``styles.'' Take the printing
-of types, for example. In the ``user'' style, the compiler's internal
+Debugging output is in one of several “styles.” Take the printing
+of types, for example. In the “user” style, the compiler's internal
ideas about types are presented in Haskell source-level syntax,
-insofar as possible. In the ``debug'' style (which is the default for
+insofar as possible. In the “debug” style (which is the default for
debugging output), the types are printed in with
explicit foralls, and variables have their unique-id attached (so you
can check for things that look the same but aren't).
<ListItem>
<Para>
<IndexTerm><Primary>-ddump-raw-asm option</Primary></IndexTerm>
-Dump out the assembly-language stuff, before the ``mangler'' gets it.
+Dump out the assembly-language stuff, before the “mangler” gets it.
</Para>
</ListItem>
</VarListEntry>
<Para>
Before we jump in, a word about names of things. Within GHC,
variables, type constructors, etc., are identified by their
-``Uniques.'' These are of the form `letter' plus `number' (both
+“Uniques.” These are of the form `letter' plus `number' (both
loosely interpreted). The `letter' gives some idea of where the
-Unique came from; e.g., <Literal>_</Literal> means ``built-in type variable'';
-<Literal>t</Literal> means ``from the typechecker''; <Literal>s</Literal> means ``from the
-simplifier''; and so on. The `number' is printed fairly compactly in
+Unique came from; e.g., <Literal>_</Literal> means “built-in type variable”;
+<Literal>t</Literal> means “from the typechecker”; <Literal>s</Literal> means “from the
+simplifier”; and so on. The `number' is printed fairly compactly in
a `base-62' format, which everyone hates except me (WDP).
</Para>
<Para>
-Remember, everything has a ``Unique'' and it is usually printed out
+Remember, everything has a “Unique” and it is usually printed out
when debugging, in some form or another. So here we go…
</Para>
</Para>
<Para>
-(``It's just a simple functional language'' is an unregisterised
+(“It's just a simple functional language” is an unregisterised
trademark of Peyton Jones Enterprises, plc.)
</Para>
Virtually all of the Glasgow extensions serve to give you access to
the underlying facilities with which we implement Haskell. Thus, you
can get at the Raw Iron, if you are willing to write some non-standard
-code at a more primitive level. You need not be ``stuck'' on
+code at a more primitive level. You need not be “stuck” on
performance because of the implementation costs of Haskell's
-``high-level'' features—you can always code ``under'' them. In an
+“high-level” features—you can always code “under” them. In an
extreme case, you can write all your time-critical code in C, and then
just glue it together with Haskell!
</Para>
<ListItem>
<Para>
You can get right down to the raw machine types and operations;
-included in this are ``primitive arrays'' (direct access to Big Wads
+included in this are “primitive arrays” (direct access to Big Wads
of Bytes). Please see <XRef LinkEnd="glasgow-unboxed"> and following.
</Para>
</ListItem>
<Para>
Before you get too carried away working at the lowest level (e.g.,
sloshing <Literal>MutableByteArray#</Literal>s around your program), you may wish to
-check if there are system libraries that provide a ``Haskellised
-veneer'' over the features you want. See <XRef LinkEnd="ghc-prelude">.
+check if there are system libraries that provide a “Haskellised
+veneer” over the features you want. See <XRef LinkEnd="ghc-prelude">.
</Para>
<Sect1 id="glasgow-unboxed">
</Para>
<Para>
-These types correspond to the ``raw machine'' types you would use in
+These types correspond to the “raw machine” types you would use in
C: <Literal>Int#</Literal> (long int), <Literal>Double#</Literal> (double), <Literal>Addr#</Literal> (void *), etc. The
<Emphasis>primitive operations</Emphasis> (PrimOps) on these types are what you
might expect; e.g., <Literal>(+#)</Literal> is addition on <Literal>Int#</Literal>s, and is the
<Para>
Nevertheless, A numerically-intensive program using unboxed types can
-go a <Emphasis>lot</Emphasis> faster than its ``standard'' counterpart—we saw a
+go a <Emphasis>lot</Emphasis> faster than its “standard” counterpart—we saw a
threefold speedup on one example.
</Para>
<Para>
This monad underlies our implementation of arrays, mutable and
-immutable, and our implementation of I/O, including ``C calls''.
+immutable, and our implementation of I/O, including “C calls”.
</Para>
<Para>
<Term>Immutable:</Term>
<ListItem>
<Para>
-Arrays that do not change (as with ``standard'' Haskell arrays); you
+Arrays that do not change (as with “standard” Haskell arrays); you
can only read from them. Obviously, they do not need the care and
attention of the state-transformer monad.
</Para>
<Term>Mutable:</Term>
<ListItem>
<Para>
-Arrays that may be changed or ``mutated.'' All the operations on them
+Arrays that may be changed or “mutated.” All the operations on them
live within the state-transformer monad and the updates happen
<Emphasis>in-place</Emphasis>.
</Para>
</ListItem>
</VarListEntry>
<VarListEntry>
-<Term>``Static'' (in C land):</Term>
+<Term>“Static” (in C land):</Term>
<ListItem>
<Para>
A C routine may pass an <Literal>Addr#</Literal> pointer back into Haskell land. There
are then primitive operations with which you may merrily grab values
-over in C land, by indexing off the ``static'' pointer.
+over in C land, by indexing off the “static” pointer.
</Para>
</ListItem>
</VarListEntry>
<VarListEntry>
-<Term>``Stable'' pointers:</Term>
+<Term>“Stable” pointers:</Term>
<ListItem>
<Para>
If, for some reason, you wish to hand a Haskell pointer (i.e.,
<Emphasis>not</Emphasis> an unboxed value) to a C routine, you first make the
-pointer ``stable,'' so that the garbage collector won't forget that it
+pointer “stable,” so that the garbage collector won't forget that it
exists. That is, GHC provides a safe way to pass Haskell pointers to
C.
</Para>
</ListItem>
</VarListEntry>
<VarListEntry>
-<Term>``Foreign objects'':</Term>
+<Term>“Foreign objects”:</Term>
<ListItem>
<Para>
-A ``foreign object'' is a safe way to pass an external object (a
+A “foreign object” is a safe way to pass an external object (a
C-allocated pointer, say) to Haskell and have Haskell do the Right
Thing when it no longer references the object. So, for example, C
-could pass a large bitmap over to Haskell and say ``please free this
-memory when you're done with it.''
+could pass a large bitmap over to Haskell and say “please free this
+memory when you're done with it.”
</Para>
<Para>
</Para>
<Para>
-The libraries section gives more details on all these ``primitive
-array'' types and the operations on them, <XRef LinkEnd="ghc-prelude">. Some of these extensions
+The libraries section gives more details on all these “primitive
+array” types and the operations on them, <XRef LinkEnd="ghc-prelude">. Some of these extensions
are also supported by Hugs, and the supporting libraries are described
in the <ULink
URL="libs.html"
<ProgramListing>
fooH :: Char -> Int -> Double -> Word -> IO Double
-fooH c i d w = _ccall_ fooC (``stdin''::Addr) c i d w
+fooH c i d w = _ccall_ fooC (“stdin”::Addr) c i d w
</ProgramListing>
</Para>
import CString
oldGetEnv name
- = _casm_ ``%r = getenv((char *) %0);'' name >>= \ litstring ->
+ = _casm_ “%r = getenv((char *) %0);” name >>= \ litstring ->
return (
if (litstring == nullAddr) then
Left ("Fail:oldGetEnv:"++name)
<Para>
The first literal-literal argument to a <Function>_casm_</Function> is like a <Function>printf</Function>
-format: <Literal>%r</Literal> is replaced with the ``result,'' <Literal>%0</Literal>–<Literal>%n-1</Literal> are
+format: <Literal>%r</Literal> is replaced with the “result,” <Literal>%0</Literal>–<Literal>%n-1</Literal> are
replaced with the 1st–nth arguments. As you can see above, it is an
easy way to do simple C casting. Everything said about <Function>_ccall_</Function> goes
for <Function>_casm_</Function> as well.
<ProgramListing>
fooH :: Char -> Int -> Double -> Word -> IO Double
-fooH c i d w = _ccall_ fooC (``stdin''::Addr) c i d w
+fooH c i d w = _ccall_ fooC (“stdin”::Addr) c i d w
</ProgramListing>
</Para>
</Sect2>
<Sect2 id="glasgow-stablePtrs">
-<Title>Subverting automatic unboxing with ``stable pointers''
+<Title>Subverting automatic unboxing with “stable pointers”
</Title>
<Para>
</Para>
<Para>
-It is possible to subvert the unboxing process by creating a ``stable
-pointer'' to a value and passing the stable pointer instead. For
+It is possible to subvert the unboxing process by creating a “stable
+pointer” to a value and passing the stable pointer instead. For
example, to pass/return an integer lazily to C functions <Function>storeC</Function> and
<Function>fetchC</Function> might write:
</Para>
sincosd :: Double -> (Double, Double)
sincosd x = unsafePerformIO $ do
da <- newDoubleArray (0, 1)
- _casm_ ``sincosd( %0, &((double *)%1[0]), &((double *)%1[1]) );'' x da
+ _casm_ “sincosd( %0, &((double *)%1[0]), &((double *)%1[1]) );” x da
s <- readDoubleArray da 0
c <- readDoubleArray da 1
return (s, c)
((_ccall_ PostTraceHook sTDERR{-msg-}):: IO ()) >>
return expr )
where
- sTDERR = (``stderr'' :: Addr)
+ sTDERR = (“stderr” :: Addr)
</ProgramListing>
</Sect2>
<Sect2 id="ccall-gotchas">
-<Title>C-calling ``gotchas'' checklist
+<Title>C-calling “gotchas” checklist
</Title>
<Para>
<ListItem>
<Para>
-To avoid ambiguity, the type after the ``<Literal>::</Literal>'' in a result
+To avoid ambiguity, the type after the “<Literal>::</Literal>” in a result
pattern signature on a lambda or <Literal>case</Literal> must be atomic (i.e. a single
token or a parenthesised type of some sort). To see why,
consider how one would parse this:
<IndexTerm><Primary>pragma, INLINE</Primary></IndexTerm></Title>
<Para>
-GHC (with <Option>-O</Option>, as always) tries to inline (or ``unfold'')
-functions/values that are ``small enough,'' thus avoiding the call
+GHC (with <Option>-O</Option>, as always) tries to inline (or “unfold”)
+functions/values that are “small enough,” thus avoiding the call
overhead and possibly exposing other more-wonderful optimisations.
</Para>
</Para>
<Para>
-Normally, if GHC decides a function is ``too expensive'' to inline, it
+Normally, if GHC decides a function is “too expensive” to inline, it
will not do so, nor will it export that unfolding for other modules to
use.
</Para>
<Para>
The major effect of an <Literal>INLINE</Literal> pragma is to declare a function's
-``cost'' to be very low. The normal unfolding machinery will then be
+“cost” to be very low. The normal unfolding machinery will then be
very keen to inline it.
</Para>
</ProgramListing>
Notice the <Literal>INLINE</Literal>! That prevents <Literal>(:)</Literal> from being inlined when compiling
-<Literal>PrelBase</Literal>, so that an importing module will ``see'' the <Literal>(:)</Literal>, and can
+<Literal>PrelBase</Literal>, so that an importing module will “see” the <Literal>(:)</Literal>, and can
match it on the LHS of a rule. <Literal>INLINE</Literal> prevents any inlining happening
in the RHS of the <Literal>INLINE</Literal> thing. I regret the delicacy of this.
</Para>
<Sect1 id="wrong-compiler">
-<Title>When the compiler ``does the wrong thing''
+<Title>When the compiler “does the wrong thing”
</Title>
<Para>
<VariableList>
<VarListEntry>
-<Term>``Help! The compiler crashed (or `panic'd)!''</Term>
+<Term>“Help! The compiler crashed (or `panic'd)!”</Term>
<ListItem>
<Para>
These events are <Emphasis>always</Emphasis> bugs in the GHC system—please report them.
</ListItem>
</VarListEntry>
<VarListEntry>
-<Term>``The compiler ran out of heap (or stack) when compiling itself!''</Term>
+<Term>“The compiler ran out of heap (or stack) when compiling itself!”</Term>
<ListItem>
<Para>
It happens. We try to supply reasonable <Option>-H<n></Option> flags for
</ListItem>
</VarListEntry>
<VarListEntry>
-<Term>``The compiler died with a pattern-matching error.''</Term>
+<Term>“The compiler died with a pattern-matching error.”</Term>
<ListItem>
<Para>
-This is a bug just as surely as a ``panic.'' Please report it.
+This is a bug just as surely as a “panic.” Please report it.
</Para>
</ListItem>
</VarListEntry>
<VarListEntry>
-<Term>``This is a terrible error message.''</Term>
+<Term>“This is a terrible error message.”</Term>
<ListItem>
<Para>
If you think that GHC could have produced a better error message,
</ListItem>
</VarListEntry>
<VarListEntry>
-<Term>``What about these `trace' messages from GHC?''</Term>
+<Term>“What about these `trace' messages from GHC?”</Term>
<ListItem>
<Para>
Almost surely not a problem. About some specific cases…
</Para>
<Para>
-If the simplifier definitely seems to be ``looping,'' please report
+If the simplifier definitely seems to be “looping,” please report
it.
</Para>
</ListItem>
</ListItem>
</VarListEntry>
<VarListEntry>
-<Term>``What about this warning from the C compiler?''</Term>
+<Term>“What about this warning from the C compiler?”</Term>
<ListItem>
<Para>
-For example: ``…warning: `Foo' declared `static' but never defined.''
+For example: “…warning: `Foo' declared `static' but never defined.”
Unsightly, but shouldn't be a problem.
</Para>
</ListItem>
</ListItem>
</VarListEntry>
<VarListEntry>
-<Term>``I think GHC is producing incorrect code'':</Term>
+<Term>“I think GHC is producing incorrect code”:</Term>
<ListItem>
<Para>
Unlikely :-) A useful be-more-paranoid option to give to GHC is
-<Option>-dcore-lint</Option><IndexTerm><Primary>-dcore-lint option</Primary></IndexTerm>; this causes a ``lint''
+<Option>-dcore-lint</Option><IndexTerm><Primary>-dcore-lint option</Primary></IndexTerm>; this causes a “lint”
pass to check for errors (notably type errors) after each Core-to-Core
transformation pass. We run with <Option>-dcore-lint</Option> on all the time; it
costs about 5% in compile time.
</ListItem>
</VarListEntry>
<VarListEntry>
-<Term>``Why did I get a link error?''</Term>
+<Term>“Why did I get a link error?”</Term>
<ListItem>
<Para>
If the linker complains about not finding <Literal>_<something>_fast</Literal>, then
</ListItem>
</VarListEntry>
<VarListEntry>
-<Term>``What's a `consistency error'?''</Term>
+<Term>“What's a `consistency error'?”</Term>
<ListItem>
<Para>
(These are reported just after linking your program.)
</ListItem>
</VarListEntry>
<VarListEntry>
-<Term>``Is this line number right?''</Term>
+<Term>“Is this line number right?”</Term>
<ListItem>
<Para>
On this score, GHC usually does pretty well, especially
-if you ``allow'' it to be off by one or two. In the case of an
+if you “allow” it to be off by one or two. In the case of an
instance or class declaration, the line number
may only point you to the declaration, not to a specific method.
</Para>
</Sect1>
<Sect1 id="wrong-compilee">
-<Title>When your program ``does the wrong thing''
+<Title>When your program “does the wrong thing”
</Title>
<Para>
<VariableList>
<VarListEntry>
-<Term>``Help! My program crashed!''</Term>
+<Term>“Help! My program crashed!”</Term>
<ListItem>
<Para>
(e.g., a `segmentation fault' or `core dumped')
For example, if an interface is lying about the type of an imported
value then GHC may well generate duff code for the importing module.
<Emphasis>This applies to pragmas inside interfaces too!</Emphasis> If the pragma is
-lying (e.g., about the ``arity'' of a value), then duff code may result.
+lying (e.g., about the “arity” of a value), then duff code may result.
Furthermore, arities may change even if types do not.
</Para>
</ListItem>
</VarListEntry>
<VarListEntry>
-<Term>``My program entered an `absent' argument.''</Term>
+<Term>“My program entered an `absent' argument.”</Term>
<ListItem>
<Para>
This is definitely caused by a bug in GHC. Please report it.
</ListItem>
</VarListEntry>
<VarListEntry>
-<Term>``What's with this `arithmetic (or `floating') exception' ''?</Term>
+<Term>“What's with this `arithmetic (or `floating') exception' ”?</Term>
<ListItem>
<Para>
<Literal>Int</Literal>, <Literal>Float</Literal>, and <Literal>Double</Literal> arithmetic is <Emphasis>unchecked</Emphasis>.
<Para>
The name of the bug-reporting game is: facts, facts, facts.
-Don't omit them because ``Oh, they won't be interested…''
+Don't omit them because “Oh, they won't be interested…”
</Para>
<Para>
<Para>
Run the sequence of compiles/runs that caused the offending
-behaviour, capturing all the input/output in a ``script'' (a UNIX
+behaviour, capturing all the input/output in a “script” (a UNIX
command) or in an Emacs shell window. We'd prefer to see the whole
thing.
<Para>
Installing from binary distributions is easiest, and recommended!
(Why binaries? Because GHC is a Haskell compiler written in Haskell,
-so you've got to ``bootstrap'' it, somehow. We provide
+so you've got to “bootstrap” it, somehow. We provide
machine-generated C-files-from-Haskell for this purpose, but it's
really quite a pain to use them. If you must build GHC from its
sources, using a binary-distributed GHC to do so is a sensible way to
</Para>
<Para>
-Binary distributions come in ``bundles,'' one bundle per file called
+Binary distributions come in “bundles,” one bundle per file called
<Literal><bundle>-<platform>.tar.gz</Literal>. (See the building guide for the definition of a platform.) Suppose that you untar a binary-distribution bundle, thus:
</Para>
<Screen>
% cd /your/scratch/space
-% gunzip < ghc-x.xx-sun-sparc-solaris2.tar.gz | tar xvf -
-</Screen>
+% gunzip < ghc-x.xx-sun-sparc-solaris2.tar.gz | tar xvf -</Screen>
</Para>
<Screen>
% cd /your/scratch/space
% gunzip < ghc-x.xx-sun-sparc-solaris2.tar.gz | tar xvf -
-% gunzip < happy-x.xx-sun-sparc-sunos4.tar.gz | tar xvf -
-</Screen>
+% gunzip < happy-x.xx-sun-sparc-sunos4.tar.gz | tar xvf -</Screen>
</Para>
<Para>
<IndexTerm><Primary>installing in-place</Primary></IndexTerm>
<IndexTerm><Primary>in-place installation</Primary></IndexTerm>
-</Para>
-
-<Para>
You can now either start using the tools <Emphasis>in-situ</Emphasis> without going
through any installation process, just type <Literal>make in-place</Literal> to set the
tools up for this. You'll also want to add the path which <Literal>make</Literal> will
<ListItem>
<Para>
- Once done, test your ``installation'' as suggested in
+ Once done, test your “installation” as suggested in
<XRef LinkEnd="sec-GHC-test">. Be sure to use a <Literal>-v</Literal>
option, so you can see exactly what pathnames it's using.
procedure will install GHC as <Literal>ghc-x.xx</Literal> where <Literal>x.xx</Literal> is the version
number of GHC. It will also make a link (in the binary installation
directory) from <Literal>ghc</Literal> to <Literal>ghc-x.xx</Literal>. If you install multiple versions
-of GHC then the last one ``wins'', and ``<Literal>ghc</Literal>'' will invoke the last
+of GHC then the last one “wins”, and “<Literal>ghc</Literal>” will invoke the last
one installed. You can change this manually if you want. But
regardless, <Literal>ghc-x.xx</Literal> should always invoke GHC version <Literal>x.xx</Literal>.
</Para>
<Para>
<IndexTerm><Primary>bundles, binary</Primary></IndexTerm>
-There are plenty of ``non-basic'' GHC bundles. The files for them are
+There are plenty of “non-basic” GHC bundles. The files for them are
called <Literal>ghc-x.xx-<bundle>-<platform>.tar.gz</Literal>, where
the <Literal><platform></Literal> is as above, and <Literal><bundle></Literal> is one
of these:
<Term><Literal>gran</Literal>:</Term>
<ListItem>
<Para>
-The ``GranSim'' parallel-Haskell simulator
+The “GranSim” parallel-Haskell simulator
(hmm… mainly for implementors).
<IndexTerm><Primary>bundles, gransim</Primary></IndexTerm>
<IndexTerm><Primary>gransim bundles</Primary></IndexTerm>
<Term><Literal>ticky</Literal>:</Term>
<ListItem>
<Para>
-``Ticky-ticky'' profiling; very detailed
-information about ``what happened when I ran this program''—really
+“Ticky-ticky” profiling; very detailed
+information about “what happened when I ran this program”—really
for implementors.
<IndexTerm><Primary>bundles, ticky-ticky</Primary></IndexTerm>
<IndexTerm><Primary>ticky-ticky bundles</Primary></IndexTerm>
libraries, etc., are being found properly:
<Screen>
-% ghc -v -o hello Main.hs
-</Screen>
+% ghc -v -o hello Main.hs</Screen>
</Para>
<Screen>
% ./hello
-Hello, world!
-</Screen>
+Hello, world!</Screen>
</Para>
</Para>
<Para>
-For more information on how to ``drive'' GHC, either do <Literal>ghc -help</Literal> or
+For more information on how to “drive” GHC, either do <Literal>ghc -help</Literal> or
consult the User's Guide (distributed in several pre-compiled formats
with a binary distribution, or in source form in
<Literal>ghc/docs/users_guide</Literal> in a source distribution).
</ItemizedList>
<Para>
-Some environment variables are ``user variables'' and
-some are ``system variables''. I'm not sure of the difference
+Some environment variables are “user variables” and
+some are “system variables”. I'm not sure of the difference
but both are changed though the same dialogue.
</Para>
<ListItem>
<Para>
-Add the two <Filename>bin</Filename> directories to your <Constant>PATH</Constant>.
-</Para>
-</ListItem>
-
-<ListItem>
-<Para>
Copy <Filename>bash.exe</Filename> from the <Filename>bin</Filename>
directory of the cygwin tree
(<Filename>cygwin-b20/H-i586-cygwin32/bin/bash.exe</Filename>) to
<ListItem>
<Para>
-Add <Filename>C:\cygnus\cygwin-b20\H-i586-cygwin32\bin</Filename> to your <Constant>PATH</Constant>.
-<Command>bash</Command> needs this, and when it is invoked from <Filename>/bin</Filename> it can't
-find it.
+If you're an Emacs user and want to be able to run <Command>bash</Command>
+from within a shell buffer, see the <ULink URL="http://www.cs.washington.edu/homes/voelker/ntemacs.html">NT Emacs home page</ULink> for
+instructions on how to set this up.
</Para>
</ListItem>
-<ListItem>
+</ItemizedList>
+
<Para>
-Set your <Constant>SHELL</Constant> user environment variable to <Filename>c:/bin/sh</Filename>.
+The following environment variables must be set:
</Para>
-</ListItem>
-<ListItem>
<Para>
-Set your <Filename>HOME</Filename> user environment variable to point to your
-home directory. This is where, for example,
+<InformalTable>
+<TGroup cols="2">
+<ColSpec Align="Left" Colsep="0">
+<ColSpec Align="Left" Colsep="0">
+<TBody>
+
+<Row>
+<Entry><Constant>PATH</Constant></Entry>
+<Entry>System</Entry>
+<Entry><Para>
+Add <Filename>C:\cygnus\cygwin-b20\H-i586-cygwin32\bin</Filename>.
+<Command>bash</Command> needs this, and when it is invoked from <Filename>/bin</Filename> it can't
+find it. <Filename>c:/bin</Filename> and <Filename>c:/usr/local/bin</Filename> should also be added.
+</Para></Entry>
+</Row>
+
+<Row>
+<Entry><Constant>SHELL</Constant></Entry>
+<Entry>User</Entry>
+<Entry><Para>
+<Filename>c:/bin/sh</Filename>.
+</Para></Entry>
+</Row>
+
+<Row>
+<Entry><Constant>HOME</Constant></Entry>
+<Entry>User</Entry>
+<Entry><Para>
+Set to point to your home directory. This is where, for example,
<Command>bash</Command> will look for your <Filename>.bashrc</Filename>
file.
-</Para>
-</ListItem>
-
-<ListItem>
-<Para>
-Set your <Constant>MAKE_MODE</Constant> user environment variable to <Literal>UNIX</Literal>. If you don't do
+</Para></Entry>
+</Row>
+
+<Row>
+<Entry><Constant>MAKE_MODE</Constant></Entry>
+<Entry>User</Entry>
+<Entry><Para>
+Set to <Literal>UNIX</Literal>. If you don't do
this you get very weird messages when you type `<Command>make</Command>', such as:
-</Para>
-
-<Screen>
-/c: /c: No such file or directory
-</Screen>
-</ListItem>
-
-<ListItem>
-<Para>
-Set the <Constant>TMPDIR</Constant> user environment variable to
-<Filename>c:/tmp</Filename>. For some reason, Win2k invisibly sets
+</Para><Screen>
+/c: /c: No such file or directory</Screen></Entry>
+</Row>
+
+<Row>
+<Entry><Constant>TMPDIR</Constant></Entry>
+<Entry>User</Entry>
+<Entry><Para>
+Set to <Filename>c:/tmp</Filename>. For some reason, Win2k invisibly sets
this variable to point to a temporary directory in your profile, that
contains embedded spaces. If GHC sees the <Constant>TMPDIR</Constant>
variable set, it tries to use it for temporary files, but Cygwin
doesn't grok filenames with spaces, so disaster results.
-</Para>
-<Para>
+</Para><Para>
Furthermore, it seems that <Constant>TMPDIR</Constant> must be set to a directory
in the same file system in which you invoke GHC. Otherwise you get very werid messages
when you invoke GHC, such as:
<Screen>
- does not exist
- Action: openFile
- Reason: file does not exist /tmp/ghc11068.cpp
-</Screen>
+does not exist
+Action: openFile
+Reason: file does not exist /tmp/ghc11068.cpp</Screen>
We think this is due to a bug in Cygwin.
-</Para>
-</ListItem>
+</Para></Entry>
+</Row>
+</TBody>
-<ListItem>
-<Para>
-If you're an Emacs user and want to be able to run <Command>bash</Command>
-from within a shell buffer, see the <ULink URL="http://www.cs.washington.edu/homes/voelker/ntemacs.html">NT Emacs home page</ULink> for
-instructions on how to set this up.
+</TGroup>
+</InformalTable>
</Para>
-</ListItem>
-</ItemizedList>
</Sect3>
+
<Sect3><Title>Perl5</Title>
<Para>
..
bash$ ./main
Hello, world!
-bash$
-</Screen>
+bash$ </Screen>
<Para>
OK, assuming that worked, you're all set. Go forth and write useful
bash$ /ghc/ghc-4.05/bin/ghc-4.05 main.hs
<stdin>:0:25: Character literal '{-# LINE 1 "main.hs" -}' too long
<stdin>:0:25: on input: "'"
-bash$
-</Screen>
+bash$ </Screen>
<Para>
or
<Screen>
bash$ /ghc/ghc-4.05/bin/ghc-4.05 main.hs
Program too big fit into memory under NT
-bash$
-</Screen>
+bash$ </Screen>
</Question>
<Answer>
bin/ghc-4.xx -- where xx is the minor release number
bin/stat2resid
bin/hstags
-lib/mkdependHS
-</Screen>
+lib/mkdependHS</Screen>
<Para>
For each of these files, you need to edit the first line from instead
<Question>
<Para>
-<Function>System.getArgs</Function> always return the empty list, i.e. the following program always prints <Screen>"[]"</Screen>:
+<Function>System.getArgs</Function> always return the empty list, i.e. the following program always prints “<Literal>[]</Literal>”:
</Para>
<ProgramListing>
a batch compiler for the Haskell 98 language, with support for various
Glasgow-only extensions. In this document, we assume that GHC has been
installed at your site as <Literal>ghc</Literal>. A separate document,
-``Building and Installing the Glasgow Functional Programming Tools Suite'',
+“Building and Installing the Glasgow Functional Programming Tools Suite”,
describes how to install <Literal>ghc</Literal>.
</Para>
<Para>
A <Emphasis>driver</Emphasis><IndexTerm><Primary>driver program</Primary></IndexTerm>
<Literal>ghc</Literal><IndexTerm><Primary>ghc</Primary></IndexTerm>—which
-you usually think of as ``the compiler''—is a program that merely
+you usually think of as “the compiler”—is a program that merely
invokes/glues-together the other pieces of the system (listed below),
passing the right options to each, slurping in the right libraries, etc.
</Para>
<IndexTerm><Primary>C pre-processor, Haskellised</Primary></IndexTerm>
<IndexTerm><Primary>pre-processor, Haskellised C</Primary></IndexTerm>
<Literal>hscpp</Literal>,<IndexTerm><Primary>hscpp</Primary></IndexTerm> only needed by people requiring conditional
-compilation, probably for large systems. The ``Haskellised'' part
+compilation, probably for large systems. The “Haskellised” part
just means that <Literal>#line</Literal> directives in the output have been
converted into proper Haskell <Literal>{-# LINE ... -}</Literal> pragmas. You must give an explicit <Literal>-cpp</Literal> option
<IndexTerm><Primary>-cpp option</Primary></IndexTerm> for the C pre-processor to be invoked.
</Sect1>
<Sect1 id="compile-what-really-happens">
-<Title>What really happens when I ``compile'' a Haskell program?
+<Title>What really happens when I “compile” a Haskell program?
</Title>
<Para>
You invoke the Glasgow Haskell compilation system through the
driver program <Literal>ghc</Literal>.<IndexTerm><Primary>ghc</Primary></IndexTerm> For example, if you had typed a
-literate ``Hello, world!'' program into <Literal>hello.lhs</Literal>, and you then
+literate “Hello, world!” program into <Literal>hello.lhs</Literal>, and you then
invoked:
<Screen>
<ListItem>
<Para>
-The assembler (or that ubiquitous ``high-level assembler,'' a C
+The assembler (or that ubiquitous “high-level assembler,” a C
compiler), which produces an object file and passes it to
</Para>
<Para>
You have considerable control over the compilation process. You feed
-command-line arguments (call them ``options,'' for short) to the
-driver, <Literal>ghc</Literal>; the ``types'' of the input files (as encoded in
+command-line arguments (call them “options,” for short) to the
+driver, <Literal>ghc</Literal>; the “types” of the input files (as encoded in
their names' suffixes) also matter.
</Para>
</ProgramListing>
<IndexTerm><Primary>Integer type</Primary></IndexTerm>
-The primitive ops to support large <Literal>Integers</Literal> use the ``pieces'' of the
+The primitive ops to support large <Literal>Integers</Literal> use the “pieces” of the
representation, and are as follows:
</Para>
<Para>
Operations for indexing off of C pointers (<Literal>Addr#</Literal>s) to snatch values
-are listed under ``arrays''.
+are listed under “arrays”.
</Para>
</Sect2>
</Para>
<Para>
-We use the terms ``reading'' and ``writing'' to refer to accessing
+We use the terms “reading” and “writing” to refer to accessing
<Emphasis>mutable</Emphasis> arrays (see <XRef LinkEnd="sect-mutable">), and
-``indexing'' to refer to reading a value from an <Emphasis>immutable</Emphasis>
+“indexing” to refer to reading a value from an <Emphasis>immutable</Emphasis>
array.
</Para>
But the <Emphasis>only</Emphasis> effect of this parameterisation is in the type
system: all values of type <Literal>State#</Literal> are represented in the same way.
Indeed, they are all represented by nothing at all! The code
-generator ``knows'' to generate no code, and allocate no registers
+generator “knows” to generate no code, and allocate no registers
etc, for primitive states.
</Para>
<Para>
The type <Literal>GHC.RealWorld</Literal> is truly opaque: there are no values defined
-of this type, and no operations over it. It is ``primitive'' in that
+of this type, and no operations over it. It is “primitive” in that
sense - but it is <Emphasis>not unlifted!</Emphasis> Its only role in life is to be
the type which distinguishes the <Literal>IO</Literal> state transformer.
</Para>
<Para>
Mutable arrays can be allocated. Only pointer-arrays are initialised;
-arrays of non-pointers are filled in by ``user code'' rather than by
+arrays of non-pointers are filled in by “user code” rather than by
the array-allocation primitive. Reason: only the pointer case has to
worry about GC striking with a partly-initialised array.
</Para>
</Para>
<Para>
-One can take ``equality'' of mutable arrays. What is compared is the
+One can take “equality” of mutable arrays. What is compared is the
<Emphasis>name</Emphasis> or reference to the mutable array, not its contents.
</Para>
</Para>
<Para>
-Parallel Haskell is still relatively new; it is more about ``research
-fun'' than about ``speed.'' That will change.
+Parallel Haskell is still relatively new; it is more about “research
+fun” than about “speed.” That will change.
</Para>
<Para>
Again, check Simon's Web page for publications about Parallel Haskell
-(including ``GUM'', the key bits of the runtime system).
+(including “GUM”, the key bits of the runtime system).
</Para>
<Para>
<Para>
Any comments, suggestions and/or improvements you have are welcome.
-Recommended ``profiling tricks'' would be especially cool!
+Recommended “profiling tricks” would be especially cool!
</Para>
<Sect1 id="profiling-intro">
<Para>
The GHC approach to profiling is very simple: annotate the expressions
-you consider ``interesting'' with <Emphasis>cost centre</Emphasis> labels (strings);
+you consider “interesting” with <Emphasis>cost centre</Emphasis> labels (strings);
so, for example, you might have:
</Para>
<Para>
The costs of the evaluating the expressions bound to <VarName>output1</VarName>,
-<VarName>output2</VarName> and <VarName>output3</VarName> will be attributed to the ``cost
-centres'' <VarName>Pass1</VarName>, <VarName>Pass2</VarName> and <VarName>Pass3</VarName>, respectively.
+<VarName>output2</VarName> and <VarName>output3</VarName> will be attributed to the “cost
+centres” <VarName>Pass1</VarName>, <VarName>Pass2</VarName> and <VarName>Pass3</VarName>, respectively.
</Para>
<Para>
<Para>
You can put in cost-centres via <Function>_scc_</Function> constructs by hand, as in the
example above. Perfectly cool. That's probably what you
-<Emphasis>would</Emphasis> do if your program divided into obvious ``passes'' or
-``phases'', or whatever.
+<Emphasis>would</Emphasis> do if your program divided into obvious “passes” or
+“phases”, or whatever.
</Para>
<Para>
<Para>
To use profiling, you must <Emphasis>compile</Emphasis> and <Emphasis>run</Emphasis> with special
-options. (We usually forget the ``run'' magic!—Do as we say, not as
+options. (We usually forget the “run” magic!—Do as we say, not as
we do…) Details follow.
</Para>
<Para>
<IndexTerm><Primary>-caf-all option</Primary></IndexTerm>
The costs of all CAFs in a module are usually attributed to one
-``big'' CAF cost-centre. With this option, all CAFs get their own cost-centre.
-An ``if all else fails'' option…
+“big” CAF cost-centre. With this option, all CAFs get their own cost-centre.
+An “if all else fails” option…
</Para>
</ListItem>
</VarListEntry>
<Para>
When you run your profiled program with the <Option>-p</Option> RTS option <IndexTerm><Primary>-p
-RTS option</Primary></IndexTerm>, you get the following information about your ``cost
-centres'':
+RTS option</Primary></IndexTerm>, you get the following information about your “cost
+centres”:
</Para>
<Para>
<ListItem>
<Para>
How many times this cost-centre was entered; think
-of it as ``I got to the <Function>_scc_</Function> construct this many times…''
+of it as “I got to the <Function>_scc_</Function> construct this many times…”
</Para>
</ListItem>
</VarListEntry>
<Term><Literal>%time</Literal>:</Term>
<ListItem>
<Para>
-What part of the time was spent in this cost-centre (see also ``ticks,''
+What part of the time was spent in this cost-centre (see also “ticks,”
below).
</Para>
</ListItem>
<ListItem>
<Para>
What part of the memory allocation was done in this cost-centre
-(see also ``bytes,'' below).
+(see also “bytes,” below).
</Para>
</ListItem>
</VarListEntry>
<Term><Literal>inner</Literal>:</Term>
<ListItem>
<Para>
-How many times this cost-centre ``passed control'' to an inner
+How many times this cost-centre “passed control” to an inner
cost-centre; for example, <Literal>scc=4</Literal> plus <Literal>subscc=8</Literal> means
-``This <Literal>_scc_</Literal> was entered four times, but went out to
-other <Literal>_scc_s</Literal> eight times.''
+“This <Literal>_scc_</Literal> was entered four times, but went out to
+other <Literal>_scc_s</Literal> eight times.”
</Para>
</ListItem>
</VarListEntry>
<Term><Literal>ticks</Literal>:</Term>
<ListItem>
<Para>
-The raw number of time ``ticks'' which were
+The raw number of time “ticks” which were
attributed to this cost-centre; from this, we get the <Literal>%time</Literal>
figure mentioned above.
</Para>
<IndexTerm><Primary>closures, profiling</Primary></IndexTerm>
How many heap objects were allocated; these objects may be of varying
size. If you divide the number of bytes (mentioned below) by this
-number of ``closures'', then you will get the average object size.
+number of “closures”, then you will get the average object size.
(Not too interesting, but still…)
</Para>
</ListItem>
</Sect1>
<Sect1 id="ticky-ticky">
-<Title>Using ``ticky-ticky'' profiling (for implementors)
+<Title>Using “ticky-ticky” profiling (for implementors)
</Title>
<Para>
It is possible to compile Glasgow Haskell programs so that they will
count lots and lots of interesting things, e.g., number of updates,
number of data constructors entered, etc., etc. We call this
-``ticky-ticky'' profiling,<IndexTerm><Primary>ticky-ticky profiling</Primary></IndexTerm>
+“ticky-ticky” profiling,<IndexTerm><Primary>ticky-ticky profiling</Primary></IndexTerm>
<IndexTerm><Primary>profiling, ticky-ticky</Primary></IndexTerm> because that's the sound a Sun4 makes
when it is running up all those counters (<Emphasis>slowly</Emphasis>).
</Para>
<Para>
Ticky-ticky profiling is mainly intended for implementors; it is quite
-separate from the main ``cost-centre'' profiling system, intended for
+separate from the main “cost-centre” profiling system, intended for
all users everywhere.
</Para>
<Para>
To be able to use ticky-ticky profiling, you will need to have built
appropriate libraries and things when you made the system. See
-``Customising what libraries to build,'' in the installation guide.
+“Customising what libraries to build,” in the installation guide.
</Para>
<Para>
<Para>
These RTS options might be used (a) to avoid a GHC bug, (b) to see
-``what's really happening'', or (c) because you feel like it. Not
+“what's really happening”, or (c) because you feel like it. Not
recommended for everyday use!
</Para>
<Para>
Oddly enough, people really do use this option! Our pal in Durham
-(England), Paul Callaghan, writes: ``Some people here use it for a
+(England), Paul Callaghan, writes: “Some people here use it for a
variety of purposes—honestly!—e.g., confirmation that the
code/machine is doing something, infinite loop detection, gauging cost
of recently added code. Certain people can even tell what stage [the
program] is in by the beep pattern. But the major use is for annoying
-others in the same office…''
+others in the same office…”
</Para>
</ListItem>
</VarListEntry>
<Para>
<IndexTerm><Primary>-r <file> RTS option</Primary></IndexTerm>
<IndexTerm><Primary>ticky ticky profiling</Primary></IndexTerm>
-Produce ``ticky-ticky'' statistics at the end of the program run.
+Produce “ticky-ticky” statistics at the end of the program run.
The <Filename><file></Filename> business works just like on the <Option>-S</Option> RTS option (above).
</Para>
<Para>
-``Ticky-ticky'' statistics are counts of various program actions
+“Ticky-ticky” statistics are counts of various program actions
(updates, enters, etc.) The program must have been compiled using
-<Option>-ticky</Option><IndexTerm><Primary>-ticky option</Primary></IndexTerm> (a.k.a. ``ticky-ticky profiling''),
+<Option>-ticky</Option><IndexTerm><Primary>-ticky option</Primary></IndexTerm> (a.k.a. “ticky-ticky profiling”),
and, for it to be really useful, linked with suitable system
libraries. Not a trivial undertaking: consult the installation guide
-on how to set things up for easy ``ticky-ticky'' profiling. For more
+on how to set things up for easy “ticky-ticky” profiling. For more
information, see <XRef LinkEnd="ticky-ticky">.
</Para>
</ListItem>
<ListItem>
<Para>
<IndexTerm><Primary>-Z RTS option</Primary></IndexTerm>
-Turn <Emphasis>off</Emphasis> ``update-frame squeezing'' at garbage-collection
+Turn <Emphasis>off</Emphasis> “update-frame squeezing” at garbage-collection
time. (There's no particularly good reason to turn it off, except to
ensure the accuracy of certain data collected regarding thunk entry
counts.)
</Sect2>
<Sect2 id="rts-hooks">
-<Title>``Hooks'' to change RTS behaviour
+<Title>“Hooks” to change RTS behaviour
</Title>
<Para>
<Para>
GHC lets you exercise rudimentary control over the RTS settings for
-any given program, by compiling in a ``hook'' that is called by the
+any given program, by compiling in a “hook” that is called by the
run-time system. The RTS contains stub definitions for all these
hooks, but by writing your own version and linking it on the GHC
command line, you can override the defaults.
<Para>
You can also change the messages printed when the runtime system
-``blows up,'' e.g., on stack overflow. The hooks for these are as
+“blows up,” e.g., on stack overflow. The hooks for these are as
follows:
</Para>
</Para>
<Para>
-For example, here is the ``hooks'' code used by GHC itself:
+For example, here is the “hooks” code used by GHC itself:
<ProgramListing>
#include <stdio.h>
</Title>
<Para>
-Please advise us of other ``helpful hints'' that should go here!
+Please advise us of other “helpful hints” that should go here!
</Para>
<Sect1 id="sooner">
<Term>Don't use too much memory!</Term>
<ListItem>
<Para>
-As soon as GHC plus its ``fellow citizens'' (other processes on your
+As soon as GHC plus its “fellow citizens” (other processes on your
machine) start using more than the <Emphasis>real memory</Emphasis> on your
-machine, and the machine starts ``thrashing,'' <Emphasis>the party is
+machine, and the machine starts “thrashing,” <Emphasis>the party is
over</Emphasis>. Compile times will be worse than terrible! Use something
like the csh-builtin <Command>time</Command> command to get a report on how many page
faults you're getting.
<Para>
Please report any overly-slow GHC-compiled programs. The current
-definition of ``overly-slow'' is ``the HBC-compiled version ran
-faster''…
+definition of “overly-slow” is “the HBC-compiled version ran
+faster”…
</Para>
<Para>
</ListItem>
</VarListEntry>
<VarListEntry>
-<Term>``But how do I know where overloading is creeping in?'':</Term>
+<Term>“But how do I know where overloading is creeping in?”:</Term>
<ListItem>
<Para>
A low-tech way: grep (search) your interface files for overloaded
</Para>
<Para>
-(If you don't know what a ``strict function'' is, please consult a
+(If you don't know what a “strict function” is, please consult a
functional-programming textbook. A sentence or two of
explanation here probably would not do much good.)
</Para>
</ListItem>
</VarListEntry>
<VarListEntry>
-<Term>``How do I find out a function's strictness?''</Term>
+<Term>“How do I find out a function's strictness?”</Term>
<ListItem>
<Para>
Don't guess—look it up.
Look for your function in the interface file, then for the third field
in the pragma; it should say <Literal>_S_ <string></Literal>. The <Literal><string></Literal>
gives the strictness of the function's arguments. <Function>L</Function> is lazy
-(bad), <Function>S</Function> and <Function>E</Function> are strict (good), <Function>P</Function> is ``primitive'' (good),
+(bad), <Function>S</Function> and <Function>E</Function> are strict (good), <Function>P</Function> is “primitive” (good),
<Function>U(...)</Function> is strict and
-``unpackable'' (very good), and <Function>A</Function> is absent (very good).
+“unpackable” (very good), and <Function>A</Function> is absent (very good).
</Para>
<Para>
-For an ``unpackable'' <Function>U(...)</Function> argument, the info inside
+For an “unpackable” <Function>U(...)</Function> argument, the info inside
tells the strictness of its components. So, if the argument is a
-pair, and it says <Function>U(AU(LSS))</Function>, that means ``the first component of the
+pair, and it says <Function>U(AU(LSS))</Function>, that means “the first component of the
pair isn't used; the second component is itself unpackable, with three
-components (lazy in the first, strict in the second \& third).''
+components (lazy in the first, strict in the second \& third).”
</Para>
<Para>
<ListItem>
<Para>
When you are <Emphasis>really</Emphasis> desperate for speed, and you want to get
-right down to the ``raw bits.'' Please see <XRef LinkEnd="glasgow-unboxed"> for some information about using unboxed
+right down to the “raw bits.” Please see <XRef LinkEnd="glasgow-unboxed"> for some information about using unboxed
types.
</Para>
</ListItem>
</Para>
<Para>
-Decrease the ``go-for-it'' threshold for unfolding smallish
+Decrease the “go-for-it” threshold for unfolding smallish
expressions. Give a
<Option>-funfolding-use-threshold0</Option><IndexTerm><Primary>-funfolding-use-threshold0
-option</Primary></IndexTerm> option for the extreme case. (``Only unfoldings with
-zero cost should proceed.'') Warning: except in certain specialiised
+option</Primary></IndexTerm> option for the extreme case. (“Only unfoldings with
+zero cost should proceed.”) Warning: except in certain specialiised
cases (like Happy parsers) this is likely to actually
<Emphasis>increase</Emphasis> the size of your program, because unfolding
generally enables extra simplifying optimisations to be performed.
</Para>
<Para>
-``I think I have a space leak…'' Re-run your program with
+“I think I have a space leak…” Re-run your program with
<Option>+RTS -Sstderr</Option>,<IndexTerm><Primary>-Sstderr RTS option</Primary></IndexTerm> and remove all doubt!
(You'll see the heap usage get bigger and bigger…) [Hmmm…this
might be even easier with the <Option>-F2s</Option><IndexTerm><Primary>-F2s RTS option</Primary></IndexTerm> RTS
</Para>
<Para>
-File names with ``meaningful'' suffixes (e.g., <Filename>.lhs</Filename> or <Filename>.o</Filename>)
-cause the ``right thing'' to happen to those files.
+File names with “meaningful” suffixes (e.g., <Filename>.lhs</Filename> or <Filename>.o</Filename>)
+cause the “right thing” to happen to those files.
</Para>
<Para>
<ListItem>
<Para>
<IndexTerm><Primary>lhs suffix</Primary></IndexTerm>
-A ``literate Haskell'' module.
+A “literate Haskell” module.
</Para>
</ListItem>
</VarListEntry>
<Row>
<Entry>Phase of the compilation system</Entry>
-<Entry>Suffix saying ``start here''</Entry>
-<Entry>Flag saying ``stop after''</Entry>
+<Entry>Suffix saying “start here”</Entry>
+<Entry>Flag saying “stop after”</Entry>
<Entry>(suffix of) output file</Entry>
</Row>
</Para>
<Para>
-Note: this ``feature'' can be counterintuitive:
+Note: this “feature” can be counterintuitive:
<Command>ghc -C -o foo.o foo.hs</Command> will put the intermediate C code in the
file <Filename>foo.o</Filename>, name notwithstanding!
</Para>
normally put in the same directory as their corresponding input file
came from. You may specify that they be put in another directory
using the <Option>-odir <dir></Option><IndexTerm><Primary>-odir <dir> option</Primary></IndexTerm> (the
-``Oh, dear'' option). For example:
+“Oh, dear” option). For example:
</Para>
<Para>
generally likely to indicate bugs in your program. These are:
<Option>-fwarn-overlpapping-patterns</Option>, <Option>-fwarn-duplicate-exports</Option>, and
<Option>-fwarn-missing-methods</Option>. The following flags are simple ways to
-select standard ``packages'' of warnings:
+select standard “packages” of warnings:
</Para>
<Para>
<ListItem>
<Para>
<IndexTerm><Primary>-i<dirs> option</Primary></IndexTerm>This flag
-prepends a colon-separated list of <Filename>dirs</Filename> to the ``import
-directories'' list.
+prepends a colon-separated list of <Filename>dirs</Filename> to the “import
+directories” list.
See also <XRef LinkEnd="recomp"> for the significance of using
relative and absolute pathnames in the <Option>-i</Option> list.
</Para>
<Term><Option>-i</Option></Term>
<ListItem>
<Para>
-resets the ``import directories'' list back to nothing.
+resets the “import directories” list back to nothing.
</Para>
</ListItem>
</VarListEntry>
</Para>
<Para>
-The <Filename>.hi</Filename> files from GHC contain ``usage'' information which changes
+The <Filename>.hi</Filename> files from GHC contain “usage” information which changes
often and uninterestingly. If you really want to see these changes
reported, you need to use the
<Option>-hi-diffs-with-usages</Option><IndexTerm><Primary>-hi-diffs-with-usages option</Primary></IndexTerm>
numbers on the things it needs this time with the version numbers on
the things it needed last time (gleaned from the interface file of the
module being compiled); if they are all the same it stops compiling
-rather early in the process saying ``Compilation IS NOT required''.
+rather early in the process saying “Compilation IS NOT required”.
What a beautiful sight!
</Para>
<Para>
-GHC <Emphasis>only</Emphasis> keeps detailed dependency information for ``user'' modules,
-not for ``library'' modules. It distinguishes the two by a hack: a module
+GHC <Emphasis>only</Emphasis> keeps detailed dependency information for “user” modules,
+not for “library” modules. It distinguishes the two by a hack: a module
whose <Filename>.hi</Filename> file has an absolute path name is considered a library module,
while a relative path name indicates a user module. So if you have a
multi-directory application, use <Emphasis>relative</Emphasis> path names in your
</Para>
<Para>
-A path is considered ``absolute'' if it starts with ``<Filename>/</Filename>'', or
-``<Filename>A:/</Filename>'', or ``<Filename>A:\</Filename>'' (or ``<Filename>B:/</Filename>'', ``<Filename>B:\</Filename>'' etc).
+A path is considered “absolute” if it starts with “<Filename>/</Filename>”, or
+“<Filename>A:/</Filename>”, or “<Filename>A:\</Filename>” (or “<Filename>B:/</Filename>”, “<Filename>B:\</Filename>” etc).
</Para>
<Para>
<Para>
You may have to type <Command>make</Command> more than once for the dependencies
to have full effect. However, a <Command>make</Command> run that does nothing
-<Emphasis>does</Emphasis> mean ``everything's up-to-date.''
+<Emphasis>does</Emphasis> mean “everything's up-to-date.”
</Para>
</ListItem>
<Para>
This scheme will work with mutually-recursive modules but,
-again, it may take multiple iterations to ``settle.''
+again, it may take multiple iterations to “settle.”
</Para>
</ListItem>
</Para>
<Para>
-The number ``1'' after ``__interface A'' gives the version number of module A;
-it is incremented whenever anything in A's interface file changes. The ``404'' is
+The number “1” after “__interface A” gives the version number of module A;
+it is incremented whenever anything in A's interface file changes. The “404” is
the version number of the interface file <Emphasis>syntax</Emphasis>; we change it when
we change the syntax of interface files so that you get a better error message when
you try to read an old-format file with a new-format compiler.
</Para>
<Para>
-The number ``1'' at the beginning of a declaration is the <Emphasis>version
+The number “1” at the beginning of a declaration is the <Emphasis>version
number</Emphasis> of that declaration: for the purposes of <Filename>.hi-boot</Filename> files
these can all be set to 1. All names must be fully qualified with the
<Emphasis>original</Emphasis> module that an object comes from: for example, the
</Para>
<Para>
-The <Option>-O*</Option> options specify convenient ``packages'' of optimisation
+The <Option>-O*</Option> options specify convenient “packages” of optimisation
flags; the <Option>-f*</Option> options described later on specify
<Emphasis>individual</Emphasis> optimisations to be turned on/off; the <Option>-m*</Option>
options specify <Emphasis>machine-specific</Emphasis> optimisations to be turned
</Para>
<Sect2 id="optimise-pkgs">
-<Title><Option>-O*</Option>: convenient ``packages'' of optimisation flags.
+<Title><Option>-O*</Option>: convenient “packages” of optimisation flags.
</Title>
<Para>
<Para>
There are <Emphasis>many</Emphasis> options that affect the quality of code
produced by GHC. Most people only have a general goal, something like
-``Compile quickly'' or ``Make my program run like greased lightning.''
-The following ``packages'' of optimisations (or lack thereof) should
+“Compile quickly” or “Make my program run like greased lightning.”
+The following “packages” of optimisations (or lack thereof) should
suffice.
</Para>
<Para>
-Once you choose a <Option>-O*</Option> ``package,'' stick with it—don't chop and
+Once you choose a <Option>-O*</Option> “package,” stick with it—don't chop and
change. Modules' interfaces <Emphasis>will</Emphasis> change with a shift to a new
<Option>-O*</Option> option, and you may have to recompile a large chunk of all
importing modules before your program can again be run
<ListItem>
<Para>
<IndexTerm><Primary>-O* not specified</Primary></IndexTerm>
-This is taken to mean: ``Please compile quickly; I'm not over-bothered
-about compiled-code quality.'' So, for example: <Command>ghc -c Foo.hs</Command>
+This is taken to mean: “Please compile quickly; I'm not over-bothered
+about compiled-code quality.” So, for example: <Command>ghc -c Foo.hs</Command>
</Para>
</ListItem>
</VarListEntry>
<IndexTerm><Primary>-O option</Primary></IndexTerm>
<IndexTerm><Primary>-O1 option</Primary></IndexTerm>
<IndexTerm><Primary>optimise normally</Primary></IndexTerm>
-Means: ``Generate good-quality code without taking too long about it.''
+Means: “Generate good-quality code without taking too long about it.”
Thus, for example: <Command>ghc -c -O Main.lhs</Command>
</Para>
</ListItem>
<Para>
<IndexTerm><Primary>-O2 option</Primary></IndexTerm>
<IndexTerm><Primary>optimise aggressively</Primary></IndexTerm>
-Means: ``Apply every non-dangerous optimisation, even if it means
-significantly longer compile times.''
+Means: “Apply every non-dangerous optimisation, even if it means
+significantly longer compile times.”
</Para>
<Para>
-The avoided ``dangerous'' optimisations are those that can make
+The avoided “dangerous” optimisations are those that can make
runtime or space <Emphasis>worse</Emphasis> if you're unlucky. They are
normally turned on or off individually.
</Para>
</Para>
<Para>
-This option will make GHC ``forget'' any <Option>-O</Option>ish options it has seen so
+This option will make GHC “forget” any <Option>-O</Option>ish options it has seen so
far. Sometimes useful; for example: <Command>make all EXTRA_HC_OPTS=-Onot</Command>.
</Para>
</ListItem>
</Para>
<Para>
-The easiest way to see what <Option>-O</Option> (etc.) ``really mean'' is to run with
+The easiest way to see what <Option>-O</Option> (etc.) “really mean” is to run with
<Option>-v</Option>, then stand back in amazement. Alternatively, just look at the
<Literal>HsC_minus<blah></Literal> lists in the GHC driver script.
</Para>
</Para>
<Para>
-Here are some ``dangerous'' optimisations you <Emphasis>might</Emphasis> want to try:
+Here are some “dangerous” optimisations you <Emphasis>might</Emphasis> want to try:
<VariableList>
<VarListEntry>
<IndexTerm><Primary>unfolding, controlling</Primary></IndexTerm>
(Default: 30) By raising or lowering this number, you can raise or
lower the amount of pragmatic junk that gets spewed into interface
-files. (An unfolding has a ``size'' that reflects the cost in terms
-of ``code bloat'' of expanding that unfolding in another module. A
+files. (An unfolding has a “size” that reflects the cost in terms
+of “code bloat” of expanding that unfolding in another module. A
bigger function would be assigned a bigger cost.)
</Para>
</ListItem>
<Para>
OK, folks, these magic numbers `30', `8', and '2' are mildly
-arbitrary; they are of the ``seem to be OK'' variety. The `8' is the
+arbitrary; they are of the “seem to be OK” variety. The `8' is the
more critical one; it's what determines how eager GHC is about
expanding unfoldings.
</Para>
<Para>
This option causes all constructor fields which are marked strict
-(i.e. ``!'') to be unboxed or unpacked if possible. For example:
+(i.e. “!”) to be unboxed or unpacked if possible. For example:
</Para>
<Para>
<ListItem>
<Para>
(iX86 machines)<IndexTerm><Primary>-monly-N-regs option (iX86 only)</Primary></IndexTerm>
-GHC tries to ``steal'' four registers from GCC, for performance
+GHC tries to “steal” four registers from GCC, for performance
reasons; it almost always works. However, when GCC is compiling some
modules with four stolen registers, it will crash, probably saying:
</Para>
<Para>
-A small word of warning: <Option>-cpp</Option> is not friendly to ``string
-gaps''.<IndexTerm><Primary>-cpp vs string gaps</Primary></IndexTerm><IndexTerm><Primary>string gaps vs
+A small word of warning: <Option>-cpp</Option> is not friendly to “string
+gaps”.<IndexTerm><Primary>-cpp vs string gaps</Primary></IndexTerm><IndexTerm><Primary>string gaps vs
-cpp</Primary></IndexTerm>. In other words, strings such as the following:
</Para>
<Row>
<Entry>
<Option>-dgcc-lint</Option> </Entry>
-<Entry> (hack) short for ``make GCC very paranoid''</Entry>
+<Entry> (hack) short for “make GCC very paranoid”</Entry>
</Row>
</TBody>
</Para>
<Para>
-If you are using a Haskell ``system library'' (e.g., the POSIX
+If you are using a Haskell “system library” (e.g., the POSIX
library), just use the <Option>-syslib posix</Option> option, and the correct code
should be linked in.
</Para>
<IndexTerm><Primary>consistency checking of executables</Primary></IndexTerm>
By default, immediately after linking an executable, GHC verifies that
the pieces that went into it were compiled with compatible flags; a
-``consistency check''.
+“consistency check”.
(This is to avoid mysterious failures caused by non-meshing of
incompatibly-compiled programs; e.g., if one <Filename>.o</Filename> file was compiled
for a parallel machine and the others weren't.) You may turn off this
</Para>
<Para>
-To run your parallel program, once PVM is going, just invoke it ``as
-normal''. The main extra RTS option is <Option>-N<n></Option>, to say how many
-PVM ``processors'' your program to run on. (For more details of
+To run your parallel program, once PVM is going, just invoke it “as
+normal”. The main extra RTS option is <Option>-N<n></Option>, to say how many
+PVM “processors” your program to run on. (For more details of
all relevant RTS options, please see <XRef LinkEnd="parallel-rts-opts">.)
</Para>
</Para>
<Para>
-Creating and/or controlling your ``parallel machine'' is a purely-PVM
+Creating and/or controlling your “parallel machine” is a purely-PVM
business; nothing specific to Parallel Haskell.
</Para>
<Para>
You use the <Command>pvm</Command><IndexTerm><Primary>pvm command</Primary></IndexTerm> command to start PVM on your
machine. You can then do various things to control/monitor your
-``parallel machine;'' the most useful being:
+“parallel machine;” the most useful being:
</Para>
<Para>
<Row>
<Entry><Command>halt</Command></Entry>
-<Entry>kill off this ``parallel machine'' & exit</Entry>
+<Entry>kill off this “parallel machine” & exit</Entry>
</Row>
<Row>
<Para>
With Parallel Haskell programs, we usually don't care about the
-results—only with ``how parallel'' it was! We want pretty pictures.
+results—only with “how parallel” it was! We want pretty pictures.
</Para>
<Para>
<Title>Other useful info about running parallel programs</Title>
<Para>
-The ``garbage-collection statistics'' RTS options can be useful for
+The “garbage-collection statistics” RTS options can be useful for
seeing what parallel programs are doing. If you do either
<Option>+RTS -Sstderr</Option><IndexTerm><Primary>-Sstderr RTS option</Primary></IndexTerm> or <Option>+RTS -sstderr</Option>, then
you'll get mutator, garbage-collection, etc., times on standard
</Para>
<Para>
-Rather than scratch your head, saying ``Now where did we define
-`foo'?'', you just do (in Emacs) <Literal>M-. foo RET</Literal>, and You're There!
+Rather than scratch your head, saying “Now where did we define
+`foo'?”, you just do (in Emacs) <Literal>M-. foo RET</Literal>, and You're There!
Some people go wild over this stuff…
</Para>
</Sect1>
<Sect1 id="happy">
-<Title>``Yacc for Haskell'': <Command>happy</Command>
+<Title>“Yacc for Haskell”: <Command>happy</Command>
</Title>
<Para>
<Para>
This section lists Glasgow Haskell infelicities in its implementation
-of Haskell 98. See also the ``when things go wrong'' section
+of Haskell 98. See also the “when things go wrong” section
(<XRef LinkEnd="wrong">)
for information about crashes, space leaks, and other undesirable
phenomena.
<Term>Very long <Literal>String</Literal> constants:</Term>
<ListItem>
<Para>
-May not go through. If you add a ``string gap'' every
+May not go through. If you add a “string gap” every
few thousand characters, then the strings can be as long
as you like.
</Para>
<Term>Very long literal lists:</Term>
<ListItem>
<Para>
-These may tickle a ``yacc stack overflow'' error in the parser.
+These may tickle a “yacc stack overflow” error in the parser.
(It depends on the Yacc used to build your parser.)
</Para>
</ListItem>