halide-haskell-0.0.1.0: src/Language/Halide.hs
-- |
-- Module : Language.Halide
-- Copyright : (c) Tom Westerhout, 2023
--
-- This package provides Haskell bindings that allow to write Halide embedded in Haskell without C++.
--
-- This module contains the reference documentation for Halide. If you're new, the best way to learn Halide is to have a look at the [tutorials](https://github.com/twesterhout/halide-haskell/tree/master/tutorials).
module Language.Halide
( -- * Scalar expressions
-- | The basic building block of Halide pipelines is 'Expr'. @Expr a@ represents a scalar expression of
-- type @a@, where @a@ must be an instance of 'IsHalideType'.
Expr (..)
, Var
, RVar
, VarOrRVar
, IsHalideType
-- ** Creating
, mkExpr
, mkVar
, mkRVar
, undef
, cast
, bool
-- ** Inspecting
, toIntImm
, printed
, evaluate
-- ** Comparisons
-- | We can't use 'Eq' and 'Ord' instances here, because we want the comparison to happen
-- when the pipeline is run rather than when it's built. Hence, we define lifted version of
-- various comparison operators. Note, that infix versions of the these functions have the
-- same precedence as the normal comparison operators.
, eq
, neq
, lt
, lte
, gt
, gte
-- * Functions
, Func (..)
, FuncTy (..)
, Stage (..)
-- ** Creating
, define
, update
, (!)
-- ** Inspecting
, getArgs
, hasUpdateDefinitions
, getUpdateStage
-- * Buffers
-- | In the C interface of Halide, buffers are described by the C struct
-- [@halide_buffer_t@](https://halide-lang.org/docs/structhalide__buffer__t.html). On the Haskell side,
-- we have 'HalideBuffer'.
, HalideBuffer (..)
-- | To easily test out your pipeline, there are helper functions to create 'HalideBuffer's without
-- worrying about the low-level representation.
, allocaCpuBuffer
-- | Buffers can also be converted to lists to easily print them for debugging.
, IsListPeek (..)
-- | For production usage however, you don't want to work with lists. Instead, you probably want Halide
-- to work with your existing array data types. For this, we define 'IsHalideBuffer' typeclass that
-- teaches Halide how to convert your data into a 'HalideBuffer'. Depending on how you implement the
-- instance, this can be very efficient, because it need not involve any memory copying.
, IsHalideBuffer (..)
, withHalideBuffer
-- | There are also helper functions to simplify writing instances of 'IsHalideBuffer'.
, bufferFromPtrShapeStrides
, bufferFromPtrShape
-- * Running the pipelines
-- | There are a few ways how one can run a Halide pipeline.
--
-- The simplest way to build a t'Func' and then call 'realize' to evaluate it over a rectangular domain.
, realize
, asBufferParam
-- | The drawback of calling 'realize' all the time is that it's impossible to pass parameters to pipelines.
-- We can define pipelines that operate on buffers using 'asBufferParam', but we have to recompile the
-- pipeline for every new buffer.
--
-- A better way to handle pipeline parameters is to define a /Haskell/ function that accepts t'Expr's
-- and t'Func's as arguments and returns a 'Func'. We can then pass this function to 'compile'
-- (or 'compileForTarget'), and it compile it into a /Haskell/ function that can now be invoked with
-- normal scalars instead of t'Expr's and @Ptr 'HalideBuffer'@s instead of 'Func's.
, compile
-- ** Parameters
-- | Similar to how we can specify the name of a variable in 'mkVar' (or 'mkRVar') or function in 'define',
-- one can also specify the name of a pipeline parameter. This is achieved by using the @ViewPatterns@
-- extension together with the 'scalar' and 'buffer' helper functions.
, buffer
, scalar
-- | Another common thing to do with the parameters is to explicitly specify their shapes. For this, we expose the 'Dimension' type:
, Dimension (..)
, dim
, setMin
, setExtent
, setStride
, setEstimate
-- ** Targets
, Target (..)
, hostTarget
, gpuTarget
, compileForTarget
, DeviceAPI (..)
, TargetFeature (..)
, setFeature
, hasGpuFeature
, hostSupportsTargetDevice
-- * Scheduling
, Schedulable (..)
, TailStrategy (..)
, LoopLevel (..)
, LoopLevelTy (..)
, LoopAlignStrategy (..)
, computeRoot
, getStage
, getLoopLevel
, getLoopLevelAtStage
, asUsed
, asUsedBy
, copyToDevice
, copyToHost
, storeAt
, computeAt
, estimate
, bound
-- * Debugging / Tracing
-- | For debugging, it's often useful to observe the value of an expression when it's evaluated. If you
-- have a complex expression that does not depend on any buffers or indices, you can 'evaluate' it.
-- | However, often an expression is only used within a definition of a pipeline, and it's impossible to
-- call 'evaluate' on it. In such cases, it can be wrapped with 'printed' to indicate to Halide that the
-- value of the expression should be dumped to screen when it's computed.
, prettyLoopNest
, compileToLoweredStmt
, StmtOutputFormat (..)
, TraceEvent (..)
, TraceEventCode (..)
, TraceLoadStoreContents (..)
, setCustomTrace
, traceStores
, traceLoads
, collectIterationOrder
-- * Type helpers
, IsTuple (..)
, ToTuple
, FromTuple
, IndexTuple
, Length
, All
-- * Internal
, compileToCallable
, testCUDA
, testOpenCL
, SomeLoopLevel (..)
, RawHalideBuffer (..)
, HalideDimension (..)
, HalideDeviceInterface
, rowMajorStrides
, colMajorStrides
, isDeviceDirty
, isHostDirty
, bufferCopyToHost
, module Language.Halide.Schedule
, IsFuncBuilder
, ReturnsFunc
, FunctionArguments
, FunctionReturn
, Curry (..)
, UnCurry (..)
, Lowered
-- ** inline-c helpers
, importHalide
, CxxExpr
, CxxVar
, CxxRVar
, CxxParameter
, CxxFunc
, CxxImageParam
, CxxStage
, CxxDimension
, CxxTarget
, CxxLoopLevel
-- * Convenience re-exports
, Int32
, Ptr
, KnownNat
)
where
import Foreign.Ptr (Ptr)
import GHC.TypeLits (KnownNat)
import Language.Halide.Buffer
import Language.Halide.Context
import Language.Halide.Dimension
import Language.Halide.Expr
import Language.Halide.Func
import Language.Halide.Kernel
import Language.Halide.LoopLevel
import Language.Halide.Schedule
import Language.Halide.Target
import Language.Halide.Trace
import Language.Halide.Type