Haskell CPP macros

Posted on September 13, 2014

Listing these here mostly because whenever I need to use them I seem to be unable to find them and have to dig for them in previous code I wrote.

Checking for minimal package versions

This relies on macros generated by Cabal. Example:

#if MIN_VERSION_process(1,2,0)
    -- something
#else
    -- something else
#endif

Checking GHC version

One option is to check the version of base

#if MIN_VERSION_base(4,7,0)

or of Template Haskell

#if MIN_VERSION_template_haskell(2,9,0)

It is however also possible to check the version of GHC directly:

#if __GLASGOW_HASKELL__ >= 706

Checking host platform

To check the host platform you can use one of these macros:

#if defined(mingw32_HOST_OS)
#if defined(cygwin32_HOST_OS) 
#if defined(darwin_HOST_OS)
#if defined(aix_HOST_OS)

Custom macros

You can add flags to your Cabal file to introduce custom CPP flags:

Flag dev
  Description:   Turn on development settings.
  Default:       False

library
  exposed-modules: ...

  if flag(dev)
    cpp-options: -DDEVELOPMENT

which you can then use as normal:

#if DEVELOPMENT

Similarly, you can use your package Cabal file to set flags based on current architecture, package versions, etc. For example, if you need a more fine-grained check for the GHC version (__GLASGOW_HASKELL__ gives major and minor version number but not patch level) you can add

library
  exposed-modules: ...

  if impl(ghc == 7.6.1)
    cpp-options: -DGHC_761