diff --git a/egison.cabal b/egison.cabal
--- a/egison.cabal
+++ b/egison.cabal
@@ -1,5 +1,5 @@
 Name:                egison
-Version:             3.2.12
+Version:             3.2.13
 Synopsis:            Programming language with non-linear pattern-matching against unfree data types
 Description:         An interpreter for Egison, the programming langugage that realized non-linear pattern-matching with unfree data types.
                      With Egison, you can represent pattern-matching with unfree data types intuitively,
diff --git a/hs-src/Interpreter/egisoni.hs b/hs-src/Interpreter/egisoni.hs
--- a/hs-src/Interpreter/egisoni.hs
+++ b/hs-src/Interpreter/egisoni.hs
@@ -10,6 +10,7 @@
 import Control.Applicative ((<$>), (<*>))
 import Control.Monad.Error
 
+import Data.List
 import Data.Sequence (Seq, ViewL(..), ViewR(..), (><))
 import qualified Data.Sequence as Sq
 
@@ -127,7 +128,7 @@
   where
     settings :: MonadIO m => FilePath -> Settings m
     settings home = do
-      setComplete noCompletion $ defaultSettings { historyFile = Just (home </> ".egison_history") }
+      setComplete completeParen $ defaultSettings { historyFile = Just (home </> ".egison_history") }
     
     loop :: Env -> String -> String -> InputT IO ()
     loop env prompt' rest = do
@@ -164,3 +165,73 @@
               loop env prompt ""
             Right env' ->
               loop env' prompt ""
+
+completeParen :: Monad m => CompletionFunc m
+completeParen arg@((')':_), _) = completeParen' arg
+completeParen arg@(('>':_), _) = completeParen' arg
+completeParen arg@((']':_), _) = completeParen' arg
+completeParen arg@(('}':_), _) = completeParen' arg
+completeParen arg@(('(':_), _) = (completeWord Nothing " \t<>[]{}$," completeAfterOpenParen) arg
+completeParen arg@(('<':_), _) = (completeWord Nothing " \t()[]{}$," completeAfterOpenCons) arg
+completeParen arg@((' ':_), _) = (completeWord Nothing "" completeNothing) arg
+completeParen arg@([], _) = (completeWord Nothing "" completeNothing) arg
+completeParen arg@(_, _) = (completeWord Nothing " \t[]{}$," completeEgisonKeyword) arg
+
+completeAfterOpenParen :: Monad m => String -> m [Completion]
+completeAfterOpenParen str = return $ map (\kwd -> Completion kwd kwd False) $ filter (isPrefixOf str) egisonKeywordsAfterOpenParen
+
+completeAfterOpenCons :: Monad m => String -> m [Completion]
+completeAfterOpenCons str = return $ map (\kwd -> Completion kwd kwd False) $ filter (isPrefixOf str) egisonKeywordsAfterOpenCons
+
+completeNothing :: Monad m => String -> m [Completion]
+completeNothing _ = return []
+
+completeEgisonKeyword :: Monad m => String -> m [Completion]
+completeEgisonKeyword str = return $ map (\kwd -> Completion kwd kwd False) $ filter (isPrefixOf str) egisonKeywords
+
+egisonKeywordsAfterOpenParen = map ((:) '(') $ ["define", "let", "letrec", "do", "lambda", "match-lambda", "match", "match-all", "pattern-function", "matcher", "algebraic-data-matcher", "if", "loop", "io"]
+                            ++ ["id", "or", "and", "not", "char", "eq?/m", "compose", "compose3", "list", "map", "between", "repeat1", "repeat", "filter", "separate", "concat", "foldr", "foldl", "map2", "zip", "empty?", "member?", "member?/m", "include?", "include?/m", "any", "all", "length", "count", "count/m", "car", "cdr", "rac", "rdc", "nth", "take", "drop", "while", "reverse", "multiset", "add", "add/m", "delete-first", "delete-first/m", "delete", "delete/m", "difference", "difference/m", "union", "union/m", "intersect", "intersect/m", "set", "unique", "unique/m", "simple-select", "print", "print-to-port", "each", "pure-rand", "fib", "fact", "divisor?", "gcd", "primes", "find-factor", "prime-factorization", "p-f", "pfs", "pfs-n", "min", "max", "min-and-max", "power", "mod", "float", "ordering", "qsort", "intersperse", "intercalate", "split", "split/m"]
+egisonKeywordsAfterOpenCons = map ((:) '<') ["nil", "cons", "join", "snoc", "nioj"]
+egisonKeywordsInNeutral = ["something"]
+                       ++ ["bool", "string", "integer", "nat", "nats", "nats0"]
+egisonKeywords = egisonKeywordsAfterOpenParen ++ egisonKeywordsAfterOpenCons ++ egisonKeywordsInNeutral
+
+completeParen' :: Monad m => CompletionFunc m
+completeParen' (lstr, _) = case (closeParen lstr) of
+                             Nothing -> return (lstr, [])
+                             Just paren -> return (lstr, [(Completion paren paren False)])
+
+closeParen :: String -> Maybe String
+closeParen str = closeParen' 0 $ removeCharAndStringLiteral str
+
+removeCharAndStringLiteral :: String -> String
+removeCharAndStringLiteral [] = []
+removeCharAndStringLiteral ('"':'\\':str) = '"':'\\':(removeCharAndStringLiteral str)
+removeCharAndStringLiteral ('"':str) = removeCharAndStringLiteral' str
+removeCharAndStringLiteral ('\'':'\\':str) = '\'':'\\':(removeCharAndStringLiteral str)
+removeCharAndStringLiteral ('\'':str) = removeCharAndStringLiteral' str
+removeCharAndStringLiteral (c:str) = c:(removeCharAndStringLiteral str)
+
+removeCharAndStringLiteral' :: String -> String
+removeCharAndStringLiteral' [] = []
+removeCharAndStringLiteral' ('"':'\\':str) = removeCharAndStringLiteral' str
+removeCharAndStringLiteral' ('"':str) = removeCharAndStringLiteral str
+removeCharAndStringLiteral' ('\'':'\\':str) = removeCharAndStringLiteral' str
+removeCharAndStringLiteral' ('\'':str) = removeCharAndStringLiteral str
+removeCharAndStringLiteral' (_:str) = removeCharAndStringLiteral' str
+
+closeParen' :: Integer -> String -> Maybe String
+closeParen' _ [] = Nothing
+closeParen' 0 ('(':_) = Just ")"
+closeParen' 0 ('<':_) = Just ">"
+closeParen' 0 ('[':_) = Just "]"
+closeParen' 0 ('{':_) = Just "}"
+closeParen' n ('(':str) = closeParen' (n - 1) str
+closeParen' n ('<':str) = closeParen' (n - 1) str
+closeParen' n ('[':str) = closeParen' (n - 1) str
+closeParen' n ('{':str) = closeParen' (n - 1) str
+closeParen' n (')':str) = closeParen' (n + 1) str
+closeParen' n ('>':str) = closeParen' (n + 1) str
+closeParen' n (']':str) = closeParen' (n + 1) str
+closeParen' n ('}':str) = closeParen' (n + 1) str
+closeParen' n (_:str) = closeParen' n str
diff --git a/hs-src/Language/Egison/Parser.hs b/hs-src/Language/Egison/Parser.hs
--- a/hs-src/Language/Egison/Parser.hs
+++ b/hs-src/Language/Egison/Parser.hs
@@ -60,12 +60,16 @@
   doesExist <- liftIO $ doesFileExist file
   unless doesExist $ throwError $ strMsg ("file does not exist: " ++ file)
   input <- liftIO $ readFile file
-  exprs <- readTopExprs input
+  exprs <- readTopExprs $ shebang input
   concat <$> mapM  recursiveLoad exprs
  where
   recursiveLoad (Load file) = loadLibraryFile file
   recursiveLoad (LoadFile file) = loadFile file
   recursiveLoad expr = return [expr]
+  shebang :: String -> String
+  shebang ('#':'!':cs) = ';':'#':'!':cs
+  shebang cs = cs
+
 
 loadLibraryFile :: FilePath -> EgisonM [EgisonTopExpr]
 loadLibraryFile file = liftIO (getDataFileName file) >>= loadFile
diff --git a/hs-src/Language/Egison/Primitives.hs b/hs-src/Language/Egison/Primitives.hs
--- a/hs-src/Language/Egison/Primitives.hs
+++ b/hs-src/Language/Egison/Primitives.hs
@@ -420,21 +420,23 @@
                , ("write-char", writeChar)
                , ("write-string", writeString)
                , ("write", writeToStdout)
-               , ("eof?", isEOFStdin)
-               , ("flush", flushStdout)
                , ("read-char-from-port", readCharFromPort)
                , ("read-line-from-port", readLineFromPort)
 --             , ("read-from-port", readFromPort)
                , ("write-char-to-port", writeCharToPort)
                , ("write-string-to-port", writeStringToPort)
                , ("write-to-port", writeToPort)
+                 
+               , ("eof?", isEOFStdin)
+               , ("flush", flushStdout)
                , ("eof-port?", isEOFPort)
                , ("flush-port", flushPort)
-
                , ("read-file", readFile')
                  
-               , ("rand", randRange) ]
---             , ("get-lib-dir-name", getLibDirName) ]
+               , ("rand", randRange)
+                 
+--             , ("get-lib-dir-name", getLibDirName)
+               ]
 
 makeIO :: EgisonM EgisonValue -> EgisonValue
 makeIO m = IOFunc $ liftM (Value . Tuple . (World :) . (:[])) m
