<para>The flag <option>-fglasgow-exts</option>
<indexterm><primary><option>-fglasgow-exts</option></primary></indexterm>
is equivalent to enabling the following extensions:
- <option>-XPrintExplicitForalls</option>,
- <option>-XForeignFunctionInterface</option>,
- <option>-XUnliftedFFITypes</option>,
- <option>-XGADTs</option>,
- <option>-XImplicitParams</option>,
- <option>-XScopedTypeVariables</option>,
- <option>-XUnboxedTuples</option>,
- <option>-XTypeSynonymInstances</option>,
- <option>-XStandaloneDeriving</option>,
- <option>-XDeriveDataTypeable</option>,
- <option>-XFlexibleContexts</option>,
- <option>-XFlexibleInstances</option>,
- <option>-XConstrainedClassMethods</option>,
- <option>-XMultiParamTypeClasses</option>,
- <option>-XFunctionalDependencies</option>,
- <option>-XMagicHash</option>,
- <option>-XPolymorphicComponents</option>,
- <option>-XExistentialQuantification</option>,
- <option>-XUnicodeSyntax</option>,
- <option>-XPostfixOperators</option>,
- <option>-XPatternGuards</option>,
- <option>-XLiberalTypeSynonyms</option>,
- <option>-XExplicitForAll</option>,
- <option>-XRankNTypes</option>,
- <option>-XImpredicativeTypes</option>,
- <option>-XTypeOperators</option>,
- <option>-XDoRec</option>,
- <option>-XParallelListComp</option>,
- <option>-XEmptyDataDecls</option>,
- <option>-XKindSignatures</option>,
- <option>-XGeneralizedNewtypeDeriving</option>,
- <option>-XTypeFamilies</option>.
+ &what_glasgow_exts_does;
Enabling these options is the <emphasis>only</emphasis>
effect of <option>-fglasgow-exts</option>.
We are trying to move away from this portmanteau flag,
<para>All these primitive data types and operations are exported by the
library <literal>GHC.Prim</literal>, for which there is
-<ulink url="../libraries/ghc-prim/GHC-Prim.html">detailed online documentation</ulink>.
+<ulink url="&libraryGhcPrimLocation;/GHC-Prim.html">detailed online documentation</ulink>.
(This documentation is generated from the file <filename>compiler/prelude/primops.txt.pp</filename>.)
</para>
<para>
<entry>LEFTWARDS ARROW</entry>
</row>
</tbody>
- <tbody>
- <row>
- <entry>..</entry>
- <entry>…</entry>
- <entry>0x22EF</entry>
- <entry>MIDLINE HORIZONTAL ELLIPSIS</entry>
- </row>
- </tbody>
<tbody>
<row>
(y -> x) = e2 } in x
</programlisting>
-(We may lift this
-restriction in the future; the only cost is that type checking patterns
-would get a little more complicated.)
-
+(For some amplification on this design choice see
+<ulink url="http://hackage.haskell.org/trac/ghc/ticket/4061">Trac #4061</ulink>.)
</para>
</listitem>
<!-- ===================== Recursive do-notation =================== -->
-<sect2 id="mdo-notation">
+<sect2 id="recursive-do-notation">
<title>The recursive do-notation
</title>
As you can guess <literal>justOnes</literal> will evaluate to <literal>Just [-1,-1,-1,...</literal>.
</para>
<para>
-The background and motivation for recusrive do-notation is described in
+The background and motivation for recursive do-notation is described in
<ulink url="http://sites.google.com/site/leventerkok/">A recursive do for Haskell</ulink>,
by Levent Erkok, John Launchbury,
Haskell Workshop 2002, pages: 29-37. Pittsburgh, Pennsylvania.
</para>
</sect3>
-<sect3> <title> Mdo-notation (deprecated) </title>
+<sect3 id="mdo-notation"> <title> Mdo-notation (deprecated) </title>
<para> GHC used to support the flag <option>-XRecursiveDo</option>,
which enabled the keyword <literal>mdo</literal>, precisely as described in
For example, in a <literal>let</literal>, it applies in the right-hand
sides of other <literal>let</literal>-bindings and the body of the
<literal>let</literal>C. Or, in recursive <literal>do</literal>
-expressions (<xref linkend="mdo-notation"/>), the local fixity
+expressions (<xref linkend="recursive-do-notation"/>), the local fixity
declarations of a <literal>let</literal> statement scope over other
statements in the group, just as the bound name does.
</para>
Nevertheless, they can be useful when defining "phantom types".</para>
</sect2>
+<sect2 id="datatype-contexts">
+<title>Data type contexts</title>
+
+<para>Haskell allows datatypes to be given contexts, e.g.</para>
+
+<programlisting>
+data Eq a => Set a = NilSet | ConsSet a (Set a)
+</programlisting>
+
+<para>give constructors with types:</para>
+
+<programlisting>
+NilSet :: Set a
+ConsSet :: Eq a => a -> Set a -> Set a
+</programlisting>
+
+<para>In GHC this feature is an extension called
+<literal>DatatypeContexts</literal>, and on by default.</para>
+</sect2>
+
<sect2 id="infix-tycons">
<title>Infix type constructors, classes, and type variables</title>
</para>
<para>A list of all supported language extensions can be obtained by invoking
- <literal>ghc --supported-languages</literal> (see <xref linkend="modes"/>).</para>
+ <literal>ghc --supported-extensions</literal> (see <xref linkend="modes"/>).</para>
<para>Any extension from the <literal>Extension</literal> type defined in
<ulink
- url="../libraries/Cabal/Language-Haskell-Extension.html"><literal>Language.Haskell.Extension</literal></ulink>
+ url="&libraryCabalLocation;/Language-Haskell-Extension.html"><literal>Language.Haskell.Extension</literal></ulink>
may be used. GHC will report an error if any of the requested extensions are not supported.</para>
</sect2>
function "<literal>f</literal>" has a number of other effects:
<itemizedlist>
<listitem><para>
-No functions are inlined into <literal>f</literal>. Otherwise
-GHC might inline a big function into <literal>f</literal>'s right hand side,
-making <literal>f</literal> big; and then inline <literal>f</literal> blindly.
+While GHC is keen to inline the function, it does not do so
+blindly. For example, if you write
+<programlisting>
+map key_function xs
+</programlisting>
+there really isn't any point in inlining <literal>key_function</literal> to get
+<programlisting>
+map (\x -> <replaceable>body</replaceable>) xs
+</programlisting>
+In general, GHC only inlines the function if there is some reason (no matter
+how slight) to supose that it is useful to do so.
</para></listitem>
+
<listitem><para>
-The float-in, float-out, and common-sub-expression transformations are not
-applied to the body of <literal>f</literal>.
+Moreover, GHC will only inline the function if it is <emphasis>fully applied</emphasis>,
+where "fully applied"
+means applied to as many arguments as appear (syntactically)
+on the LHS of the function
+definition. For example:
+<programlisting>
+comp1 :: (b -> c) -> (a -> b) -> a -> c
+{-# INLINE comp1 #-}
+comp1 f g = \x -> f (g x)
+
+comp2 :: (b -> c) -> (a -> b) -> a -> c
+{-# INLINE comp2 #-}
+comp2 f g x = f (g x)
+</programlisting>
+The two functions <literal>comp1</literal> and <literal>comp2</literal> have the
+same semantics, but <literal>comp1</literal> will be inlined when applied
+to <emphasis>two</emphasis> arguments, while <literal>comp2</literal> requires
+<emphasis>three</emphasis>. This might make a big difference if you say
+<programlisting>
+map (not `comp1` not) xs
+</programlisting>
+which will optimise better than the corresponding use of `comp2`.
+</para></listitem>
+
+<listitem><para>
+It is useful for GHC to optimise the definition of an
+INLINE function <literal>f</literal> just like any other non-INLINE function,
+in case the non-inlined version of <literal>f</literal> is
+ultimately called. But we don't want to inline
+the <emphasis>optimised</emphasis> version
+of <literal>f</literal>;
+a major reason for INLINE pragmas is to expose functions
+in <literal>f</literal>'s RHS that have
+rewrite rules, and it's no good if those functions have been optimised
+away.
+</para>
+<para>
+So <emphasis>GHC guarantees to inline precisely the code that you wrote</emphasis>, no more
+and no less. It does this by capturing a copy of the definition of the function to use
+for inlining (we call this the "inline-RHS"), which it leaves untouched,
+while optimising the ordinarly RHS as usual. For externally-visible functions
+the inline-RHS (not the optimised RHS) is recorded in the interface file.
</para></listitem>
<listitem><para>
An INLINE function is not worker/wrappered by strictness analysis.
It's going to be inlined wholesale instead.
</para></listitem>
</itemizedlist>
-All of these effects are aimed at ensuring that what gets inlined is
-exactly what you asked for, no more and no less.
</para>
<para>GHC ensures that inlining cannot go on forever: every mutually-recursive
group is cut by one or more <emphasis>loop breakers</emphasis> that is never inlined
{-# INLINE returnUs #-}
</programlisting>
- <para>See also the <literal>NOINLINE</literal> pragma (<xref
- linkend="noinline-pragma"/>).</para>
+ <para>See also the <literal>NOINLINE</literal> (<xref linkend="inlinable-pragma"/>)
+ and <literal>INLINABLE</literal> (<xref linkend="noinline-pragma"/>)
+ pragmas.</para>
<para>Note: the HBC compiler doesn't like <literal>INLINE</literal> pragmas,
so if you want your code to be HBC-compatible you'll have to surround
</sect3>
+ <sect3 id="inlinable-pragma">
+ <title>INLINABLE pragma</title>
+
+<para>An INLINABLE pragma works very like an INLINE pragma, except that:
+<itemizedlist>
+<listitem><para>
+INLINE says "please inline me", but INLINABLE says "feel free to inline me; use your
+discretion". In other words the choice is left to GHC, which uses the same
+rules as for pragma-free functions. Unlike INLINE, That decision is made at
+the <emphasis>call site</emphasis>, and
+will therefore be affected by the inlining threshold, optimisation level etc.
+</para></listitem>
+<listitem><para>
+Like INLINE, the INLINABLE pragma retains a copy of the original RHS for
+inlining purposes, and persists it in the interface file, regardless of
+the size of the RHS.
+</para></listitem>
+<listitem><para>
+If you use the special function <literal>inline</literal> (<xref linkend="special-ids"/>)
+to force inlining at a
+call site, you will get a copy of the the original RHS.
+Indeed, if you intend to use <literal>inline f</literal> it
+is a good idea to mark the definition of <literal>f</literal> INLINABLE,
+so that GHC guarantees to expose an unfolding regardless of how big it is.
+</para></listitem>
+</itemizedlist>
+</para>
+
+ </sect3>
+
<sect3 id="noinline-pragma">
<title>NOINLINE pragma</title>
directly in the <function>T</function> constructor. The
unpacker can see through newtypes, too.</para>
- <para>If a field cannot be unpacked, you will not get a warning,
- so it might be an idea to check the generated code with
- <option>-ddump-simpl</option>.</para>
-
<para>See also the <option>-funbox-strict-fields</option> flag,
which essentially has the effect of adding
<literal>{-# UNPACK #-}</literal> to every strict
<title>Special built-in functions</title>
<para>GHC has a few built-in functions with special behaviour. These
are now described in the module <ulink
-url="../libraries/ghc-prim/GHC-Prim.html"><literal>GHC.Prim</literal></ulink>
-in the library documentation.</para>
+url="&libraryGhcPrimLocation;/GHC-Prim.html"><literal>GHC.Prim</literal></ulink>
+in the library documentation.
+In particular:
+<itemizedlist>
+<listitem><para>
+<ulink url="&libraryGhcPrimLocation;/GHC-Prim.html#v%3Ainline"><literal>inline</literal></ulink>
+allows control over inlining on a per-call-site basis.
+</para></listitem>
+<listitem><para>
+<ulink url="&libraryGhcPrimLocation;/GHC-Prim.html#v%3Alazy"><literal>lazy</literal></ulink>
+restrains the strictness analyser.
+</para></listitem>
+<listitem><para>
+<ulink url="&libraryGhcPrimLocation;/GHC-Prim.html#v%3AunsafeCoerce%23"><literal>lazy</literal></ulink>
+allows you to fool the type checker.
+</para></listitem>
+</itemizedlist>
+</para>
</sect1>
<!-- Emacs stuff:
;;; Local Variables: ***
- ;;; mode: xml ***
;;; sgml-parent-document: ("users_guide.xml" "book" "chapter" "sect1") ***
;;; ispell-local-dictionary: "british" ***
;;; End: ***