The GHC Commentary - The Basics

The directory fptools/ghc/compiler/basicTypes/ contains modules that define some of the essential types definition for the compiler - such as, identifiers, variables, modules, and unique names. Some of those are discussed in the following. See elsewhere for more detailed information on:

Elementary Types

Ids

An Id (defined in Id.lhs essentially records information about value and data constructor identifiers -- to be precise, in the case of data constructors, two Ids are used to represent the worker and wrapper functions for the data constructor, respectively. The information maintained in the Id abstraction includes among other items strictness, occurrence, specialisation, and unfolding information.

Due to the way Ids are used for data constructors, all Ids are represented as variables, which contain a varInfo field of abstract type IdInfo.IdInfo. This is where the information about Ids is really stored. The following is a (currently, partial) list of the various items in an IdInfo:

Occurence information
The OccInfo data type is defined in the module BasicTypes.lhs. Apart from the trivial NoOccInfo, it distinguishes between variables that do not occur at all (IAmDead), occur just once (OneOcc), or a loop breakers (IAmALoopBreaker).

Sets, Finite Maps, and Environments

Sets of variables, or more generally names, which are needed throughout the compiler, are provided by the modules VarSet.lhs and NameSet.lhs, respectively. Moreover, frequently maps from variables (or names) to other data is needed. For example, a substitution is represented by a finite map from variable names to expressions. Jobs like this are solved by means of variable and name environments implemented by the modules VarEnv.lhs and NameEnv.lhs.

The Module VarSet

The Module VarSet provides the types VarSet, IdSet, and TyVarSet, which are synonyms in the current implementation, as Var, Id, and TyVar are synonyms. The module provides all the operations that one would expect including the creating of sets from individual variables and lists of variables, union and intersection operations, element checks, deletion, filter, fold, and map functions.

The implementation is based on UniqSets, which in turn are simply UniqFMs (i.e., finite maps with uniques as keys) that map each unique to the variable that it represents.

The Module NameSet

The Module NameSet provides the same functionality as VarSet only for Names. As for the difference between Names and Vars, a Var is built from a Name plus additional information (mostly importantly type information).

The Module VarEnv

The module VarEnv provides the types VarEnv, IdEnv, and TyVarEnv, which are again synonyms. The provided base functionality is similar to VarSet with the main difference that a type VarEnv T associates a value of type T with each variable in the environment, thus effectively implementing a finite map from variables to values of type T.

The implementation of VarEnv is also by UniqFM, which entails the slightly surprising implication that it is not possible to retrieve the domain of a variable environment. In other words, there is no function corresponding to VarSet.varSetElems :: VarSet -> [Var] in VarEnv. This is because the UniqFM used to implement VarEnv stores only the unique corresponding to a variable in the environment, but not the entire variable (and there is no mapping from uniques to variables).

In addition to plain variable environments, the module also contains special substitution environments - the type SubstEnv - that associates variables with a special purpose type SubstResult.

The Module NameEnv

The type NameEnv.NameEnv is like VarEnv only for Names.


Last modified: Tue Jan 8 18:29:52 EST 2002