content: -- Generated by re2hs
  {-# LANGUAGE RecordWildCards #-}
  #1 "haskell/submatch/01_stags_fill.re"
  -- re2hs $INPUT -o $OUTPUT
  {-# OPTIONS_GHC -Wno-unused-record-wildcards #-}
  {-# LANGUAGE OverloadedStrings #-}
  
  import Control.Monad
  import Data.ByteString as BS
  import GHC.IO.Handle
  import System.Directory
  import System.IO
  
  chunk_size :: Int
  chunk_size = 4096
  
  data State = State {
      _file :: !Handle,
      _yyinput :: !BS.ByteString,
      _yycursor :: !Int,
      _yymarker :: !Int,
      _yylimit :: !Int,
      _token :: !Int,
      -- Final tag bindings available in semantic action.
      
  #27 "haskell/submatch/01_stags_fill.hs"
  
  _1 :: !Int,
  _2 :: !Int,
  _3 :: !Int,
  _4 :: !Int,
  _5 :: !Int,
  #22 "haskell/submatch/01_stags_fill.re"
  
      -- Intermediate tag bindings used by the lexer (must be autogenerated).
      
  #38 "haskell/submatch/01_stags_fill.hs"
  
  _yyt1 :: !Int,
  _yyt2 :: !Int,
  _yyt3 :: !Int,
  _yyt4 :: !Int,
  #24 "haskell/submatch/01_stags_fill.re"
  
      _eof :: !Bool
  }
  
  data SemVer = SemVer {
      major :: !Int,
      minor :: !Int,
      patch :: !Int
  } deriving (Eq, Show)
  
  s2n :: BS.ByteString -> Int -> Int -> Int
  s2n s i j = f i 0 where
      f k n = if k >= j then n else f (k + 1) (n * 10 + (fromIntegral (BS.index s k) - 48))
  
  
  #60 "haskell/submatch/01_stags_fill.hs"
  yy0 :: State -> [SemVer] -> IO [SemVer]
  yy0 State{..} _vers = do
      yych <- return $ BS.index _yyinput _yycursor
      case yych of
          _c | 0x30 <= _c && _c <= 0x39 -> do
              let _yyt1 = _yycursor
              _yycursor <- return $ _yycursor + 1
              yy3 State{..} _vers
          _c | True -> do
              if _yycursor >= _yylimit then do
                  (State{..}, yyfill) <- fill State{..}
                  if yyfill then yy0 State{..} _vers
                  else yy11 State{..} _vers
              else do
                  _yycursor <- return $ _yycursor + 1
                  yy1 State{..} _vers
  
  yy1 :: State -> [SemVer] -> IO [SemVer]
  yy1 State{..} _vers = do
      yy2 State{..} _vers
  
  yy2 :: State -> [SemVer] -> IO [SemVer]
  yy2 State{..} _vers = do
  #57 "haskell/submatch/01_stags_fill.re"
      error "lexer failed"
  #86 "haskell/submatch/01_stags_fill.hs"
  
  yy3 :: State -> [SemVer] -> IO [SemVer]
  yy3 State{..} _vers = do
      let _yymarker = _yycursor
      yych <- return $ BS.index _yyinput _yycursor
      case yych of
          _c | 0x2E == _c -> do
              _yycursor <- return $ _yycursor + 1
              yy4 State{..} _vers
          _c | 0x30 <= _c && _c <= 0x39 -> do
              _yycursor <- return $ _yycursor + 1
              yy6 State{..} _vers
          _c | True -> do
              if _yycursor >= _yylimit then do
                  (State{..}, yyfill) <- fill State{..}
                  if yyfill then yy3 State{..} _vers
                  else yy2 State{..} _vers
              else do
                  yy2 State{..} _vers
  
  yy4 :: State -> [SemVer] -> IO [SemVer]
  yy4 State{..} _vers = do
      yych <- return $ BS.index _yyinput _yycursor
      case yych of
          _c | 0x30 <= _c && _c <= 0x39 -> do
              let _yyt2 = _yycursor
              _yycursor <- return $ _yycursor + 1
              yy7 State{..} _vers
          _c | True -> do
              if _yycursor >= _yylimit then do
                  (State{..}, yyfill) <- fill State{..}
                  if yyfill then yy4 State{..} _vers
                  else yy5 State{..} _vers
              else do
                  yy5 State{..} _vers
  
  yy5 :: State -> [SemVer] -> IO [SemVer]
  yy5 State{..} _vers = do
      let _yycursor = _yymarker
      yy2 State{..} _vers
  
  yy6 :: State -> [SemVer] -> IO [SemVer]
  yy6 State{..} _vers = do
      yych <- return $ BS.index _yyinput _yycursor
      case yych of
          _c | 0x2E == _c -> do
              _yycursor <- return $ _yycursor + 1
              yy4 State{..} _vers
          _c | 0x30 <= _c && _c <= 0x39 -> do
              _yycursor <- return $ _yycursor + 1
              yy6 State{..} _vers
          _c | True -> do
              if _yycursor >= _yylimit then do
                  (State{..}, yyfill) <- fill State{..}
                  if yyfill then yy6 State{..} _vers
                  else yy5 State{..} _vers
              else do
                  yy5 State{..} _vers
  
  yy7 :: State -> [SemVer] -> IO [SemVer]
  yy7 State{..} _vers = do
      yych <- return $ BS.index _yyinput _yycursor
      case yych of
          _c | 0x0A == _c -> do
              let _yyt3 = _yycursor
              let _yyt4 = (-1)
              _yycursor <- return $ _yycursor + 1
              yy8 State{..} _vers
          _c | 0x2E == _c -> do
              let _yyt3 = _yycursor
              _yycursor <- return $ _yycursor + 1
              yy9 State{..} _vers
          _c | 0x30 <= _c && _c <= 0x39 -> do
              _yycursor <- return $ _yycursor + 1
              yy7 State{..} _vers
          _c | True -> do
              if _yycursor >= _yylimit then do
                  (State{..}, yyfill) <- fill State{..}
                  if yyfill then yy7 State{..} _vers
                  else yy5 State{..} _vers
              else do
                  yy5 State{..} _vers
  
  yy8 :: State -> [SemVer] -> IO [SemVer]
  yy8 State{..} _vers = do
      let _1 = _yyt1
      let _3 = _yyt2
      let _4 = _yyt3
      let _5 = _yyt4
      let _2 = _yyt2
      _2 <- return $ if _2 == (-1) then (-1) else _2 - 1
  #48 "haskell/submatch/01_stags_fill.re"
      let ver = SemVer {
          major = s2n _yyinput _1 _2,
          minor = s2n _yyinput _3 _4,
          patch = if _5 == (-1) then 0 else s2n _yyinput _5 (_yycursor - 1)
      }
      lexer State{..} (ver: _vers)
  #185 "haskell/submatch/01_stags_fill.hs"
  
  yy9 :: State -> [SemVer] -> IO [SemVer]
  yy9 State{..} _vers = do
      yych <- return $ BS.index _yyinput _yycursor
      case yych of
          _c | 0x30 <= _c && _c <= 0x39 -> do
              let _yyt4 = _yycursor
              _yycursor <- return $ _yycursor + 1
              yy10 State{..} _vers
          _c | True -> do
              if _yycursor >= _yylimit then do
                  (State{..}, yyfill) <- fill State{..}
                  if yyfill then yy9 State{..} _vers
                  else yy5 State{..} _vers
              else do
                  yy5 State{..} _vers
  
  yy10 :: State -> [SemVer] -> IO [SemVer]
  yy10 State{..} _vers = do
      yych <- return $ BS.index _yyinput _yycursor
      case yych of
          _c | 0x0A == _c -> do
              _yycursor <- return $ _yycursor + 1
              yy8 State{..} _vers
          _c | 0x30 <= _c && _c <= 0x39 -> do
              _yycursor <- return $ _yycursor + 1
              yy10 State{..} _vers
          _c | True -> do
              if _yycursor >= _yylimit then do
                  (State{..}, yyfill) <- fill State{..}
                  if yyfill then yy10 State{..} _vers
                  else yy5 State{..} _vers
              else do
                  yy5 State{..} _vers
  
  yy11 :: State -> [SemVer] -> IO [SemVer]
  yy11 State{..} _vers = do
  #56 "haskell/submatch/01_stags_fill.re"
      return _vers
  #225 "haskell/submatch/01_stags_fill.hs"
  
  lexer :: State -> [SemVer] -> IO [SemVer]
  lexer State{..} _vers = do
      yy0 State{..} _vers
  
  #58 "haskell/submatch/01_stags_fill.re"
  
  
  fill :: State -> IO (State, Bool)
  fill State{..} = do
      case _eof of
          True -> return (State{..}, False)
          False -> do
              -- Discard everything up to the current token, cut off terminating null,
              -- read new chunk from file and reappend terminating null at the end.
              chunk <- BS.hGet _file chunk_size
              return (State{
                  _yyinput = BS.concat [(BS.init . BS.drop _token) _yyinput, chunk, "\0"],
                  _yycursor = _yycursor - _token,
                  _yymarker = _yymarker - _token,
                  _yylimit = _yylimit - _token + BS.length chunk, -- exclude terminating null
                  _token = 0,
                  _eof = BS.null chunk, -- end of file?
                  ..}, True)
  
  main :: IO ()
  main = do
      let fname = "input"
  
      -- Prepare input file.
      BS.writeFile fname $ BS.concat ["1.22.333\n" | _ <- [1..chunk_size]]
      let expect = [SemVer {major = 1, minor = 22, patch = 333} | _ <- [1..chunk_size]]
  
      -- Run lexer on the prepared file.
      fh <- openFile fname ReadMode
      let st = State {
          _file = fh,
          _yyinput = BS.singleton 0,
          _yycursor = 0,
          _yymarker = 0,
          _yylimit = 0,
          _token = 0,
          
  #269 "haskell/submatch/01_stags_fill.hs"
  
  _1 = (-1),
  _2 = (-1),
  _3 = (-1),
  _4 = (-1),
  _5 = (-1),
  #94 "haskell/submatch/01_stags_fill.re"
  
          
  #279 "haskell/submatch/01_stags_fill.hs"
  
  _yyt1 = (-1),
  _yyt2 = (-1),
  _yyt3 = (-1),
  _yyt4 = (-1),
  #95 "haskell/submatch/01_stags_fill.re"
  
          _eof = False
      }
      result <- lexer st []
      hClose fh
  
      -- Cleanup.
      removeFile fname
  
      -- Check result.
      when (result /= expect) $ error $ "expected " ++ show expect ++ ", got " ++ show result
      return ()
  