{-# LINE 1 "Data/Text/ICU/Regex/Internal.hsc" #-}
{-# LANGUAGE BangPatterns, DeriveDataTypeable, EmptyDataDecls,
ForeignFunctionInterface, MagicHash, RecordWildCards,
ScopedTypeVariables #-}
module Data.Text.ICU.Regex.Internal
(
MatchOption(..)
, Regex(..)
, URegularExpression
, regex
, uregex_clone
, uregex_close
, uregex_end
, uregex_find
, uregex_findNext
, uregex_getText
, uregex_group
, uregex_groupCount
, uregex_pattern
, uregex_setUText
, uregex_start
) where
import Control.Monad (when)
import Data.IORef (IORef, newIORef)
import Data.Int (Int32)
import Data.Text (Text)
import Data.Text.ICU.Internal (UBool, UChar, UTextPtr, UText, useAsUCharPtr, withUTextPtr, emptyUTextPtr, newICUPtr)
import Data.Text.ICU.Error (isRegexError)
import Data.Text.ICU.Error.Internal (UParseError, UErrorCode,
handleError, handleParseError)
import Data.Typeable (Typeable)
import Data.Word (Word32)
import Foreign.ForeignPtr (ForeignPtr)
import Foreign.Ptr (FunPtr, Ptr)
data MatchOption
= CaseInsensitive
| Comments
| DotAll
| Literal
| Multiline
| HaskellLines
| UnicodeWord
| ErrorOnUnknownEscapes
| WorkLimit Int
| StackLimit Int
deriving (Eq, Show, Typeable)
data Regex = Regex {
reRe :: ForeignPtr URegularExpression
, reText :: IORef UTextPtr
}
regex :: [MatchOption] -> Text -> IO Regex
regex opts pat = useAsUCharPtr pat $ \pptr plen ->
newICUPtr Regex uregex_close (do
ptr <- handleParseError isRegexError $
uregex_open pptr (fromIntegral plen) flags
withUTextPtr hayfp $ \hayPtr -> handleError $
uregex_setUText ptr hayPtr
when (workLimit > -1) .
handleError $ uregex_setTimeLimit ptr (fromIntegral workLimit)
when (stackLimit > -1) .
handleError $ uregex_setStackLimit ptr (fromIntegral stackLimit)
return ptr)
<*> newIORef hayfp
where (flags,workLimit,stackLimit) = toURegexpOpts opts
hayfp = emptyUTextPtr
data URegularExpression
type URegexpFlag = Word32
toURegexpOpts :: [MatchOption] -> (URegexpFlag,Int,Int)
toURegexpOpts = foldl go (0,-1,-1)
where
go (!flag,work,stack) opt = (flag+flag',work',stack')
where
flag' = case opt of
CaseInsensitive -> 2
{-# LINE 167 "Data/Text/ICU/Regex/Internal.hsc" #-}
Comments -> 4
{-# LINE 168 "Data/Text/ICU/Regex/Internal.hsc" #-}
DotAll -> 32
{-# LINE 169 "Data/Text/ICU/Regex/Internal.hsc" #-}
Literal -> 16
{-# LINE 170 "Data/Text/ICU/Regex/Internal.hsc" #-}
Multiline -> 8
{-# LINE 171 "Data/Text/ICU/Regex/Internal.hsc" #-}
HaskellLines -> 1
{-# LINE 172 "Data/Text/ICU/Regex/Internal.hsc" #-}
UnicodeWord -> 256
{-# LINE 173 "Data/Text/ICU/Regex/Internal.hsc" #-}
ErrorOnUnknownEscapes -> 512
{-# LINE 174 "Data/Text/ICU/Regex/Internal.hsc" #-}
_ -> 0
work' = case opt of
WorkLimit limit -> limit
_ -> work
stack' = case opt of
StackLimit limit -> limit
_ -> stack
foreign import ccall unsafe "hs_text_icu.h __hs_uregex_open" uregex_open
:: Ptr UChar -> Int32 -> Word32 -> Ptr UParseError -> Ptr UErrorCode
-> IO (Ptr URegularExpression)
foreign import ccall unsafe "hs_text_icu.h &__hs_uregex_close" uregex_close
:: FunPtr (Ptr URegularExpression -> IO ())
foreign import ccall unsafe "hs_text_icu.h __hs_uregex_clone" uregex_clone
:: Ptr URegularExpression -> Ptr UErrorCode
-> IO (Ptr URegularExpression)
foreign import ccall unsafe "hs_text_icu.h __hs_uregex_pattern" uregex_pattern
:: Ptr URegularExpression -> Ptr Int32 -> Ptr UErrorCode
-> IO (Ptr UChar)
foreign import ccall unsafe "hs_text_icu.h __hs_uregex_setUText" uregex_setUText
:: Ptr URegularExpression -> Ptr UText -> Ptr UErrorCode -> IO ()
foreign import ccall unsafe "hs_text_icu.h __hs_uregex_getText" uregex_getText
:: Ptr URegularExpression -> Ptr Int32 -> Ptr UErrorCode -> IO (Ptr UChar)
foreign import ccall unsafe "hs_text_icu.h __hs_uregex_find" uregex_find
:: Ptr URegularExpression -> Int32 -> Ptr UErrorCode -> IO UBool
foreign import ccall unsafe "hs_text_icu.h __hs_uregex_findNext" uregex_findNext
:: Ptr URegularExpression -> Ptr UErrorCode -> IO UBool
foreign import ccall unsafe "hs_text_icu.h __hs_uregex_start" uregex_start
:: Ptr URegularExpression -> Int32 -> Ptr UErrorCode -> IO Int32
foreign import ccall unsafe "hs_text_icu.h __hs_uregex_end" uregex_end
:: Ptr URegularExpression -> Int32 -> Ptr UErrorCode -> IO Int32
foreign import ccall unsafe "hs_text_icu.h __hs_uregex_groupCount" uregex_groupCount
:: Ptr URegularExpression -> Ptr UErrorCode -> IO Int32
foreign import ccall unsafe "hs_text_icu.h __hs_uregex_group" uregex_group
:: Ptr URegularExpression -> Int32 -> Ptr UChar -> Int32 -> Ptr UErrorCode
-> IO Int32
foreign import ccall unsafe "hs_text_icu.h __hs_uregex_setTimeLimit" uregex_setTimeLimit
:: Ptr URegularExpression -> Int32 -> Ptr UErrorCode -> IO ()
foreign import ccall unsafe "hs_text_icu.h __hs_uregex_setStackLimit" uregex_setStackLimit
:: Ptr URegularExpression -> Int32 -> Ptr UErrorCode -> IO ()