+ <h3>Representing Binding Forms</h3>
+ <p>
+ Care needs to be taken when constructing TH representations of Haskell
+ terms that include binding forms, such as lambda abstractions or let
+ bindings. To avoid name clashes, fresh names need to be generated for
+ all defined identifiers. This is achieved via the routine
+ <code>DsMeta.mkGenSym</code>, which, given a <code>Name</code>, produces
+ a <code>Name</code> / <code>Id</code> pair (of type
+ <code>GenSymBind</code>) that associates the given <code>Name</code>
+ with a Core identifier that at runtime will be bound to a string that
+ contains the fresh name. Notice the two-level nature of this
+ arrangement. It is necessary, as the Core code that constructs the
+ Haskell term representation may be executed multiple types at runtime
+ and it must be ensured that different names are generated in each run.
+ </p>
+ <p>
+ Such fresh bindings need to be entered into the meta environment (of
+ type <a
+ href="http://cvs.haskell.org/cgi-bin/cvsweb.cgi/fptools/ghc/compiler/deSugar/DsMonad.lhs"><code>DsMonad</code></a><code>.DsMetaEnv</code>),
+ which is part of the state (of type <code>DsMonad.DsEnv</code>)
+ maintained in the desugarer monad (of type <code>DsMonad.DsM</code>).
+ This is done using the function <code>DsMeta.addBinds</code>, which
+ extends the current environment by a list of <code>GenSymBind</code>s
+ and executes a subcomputation in this extended environment. Names can
+ be looked up in the meta environment by way of the functions
+ <code>DsMeta.lookupOcc</code> and <code>DsMeta.lookupBinder</code>; more
+ details about the difference between these two functions can be found in
+ the next subsection.
+ </p>
+ <p>
+ NB: <code>DsMeta</code> uses <code>mkGenSym</code> only when
+ representing terms that may be embedded into a context where names can
+ be shadowed. For example, a lambda abstraction embedded into an
+ expression can potentially shadow names defined in the context it is
+ being embedded into. In contrast, this can never be the case for
+ top-level declarations, such as data type declarations; hence, the type
+ variables that a parametric data type declaration abstracts over are not
+ being gensym'ed. As a result, variables in defining positions are
+ handled differently depending on the syntactic construct in which they
+ appear.
+ </p>
+