minishell's specification - 42tokyo-minishell/42_minishell GitHub Wiki

builtin command

cd (PR#294,PR#190)

  • option あり
    • error
  • option なし
    • 引数 1 個以上
      • error
    • 引数 1 個
      • 無効な directory : error
      • 有効な directory : 移動する
        • - : OLDPWD に移動
  • -- : signify the end of the options
  • /, //, ///, ////..
  • permissionがない
  • currentが削除
  • CDPATH (PR#216, PR#218)
    • CDPATH が環境変数にあれば検索しにいく
    • なければ current を検索する
  • 未対応
    • ~ : HOME だが /etc/passwd に探しに行ってる(のは起動時だけ)。するならHOME展開。cd ~ + 何かで bash がセグフォする…
    • PWD を set or unset した場合
      • An absolute pathname of the current working directory. If an application sets or unsets the value of PWD, the behavior of pwd is unspecified.
      • POSIX-PWD
        ですが、bash に合わせた
    • sh: 0: のエラー文は理由が不明だったので出力していない。

echo (PR #59)

  • option なし, 引数ありなし
  • option あり, 引数ありなし
    • -n : -n, -nnn, -n -n -n
  • 未対応
    • error 系(対応予定)
    • $- : bash の option を表示するが、未対応。

env (PR #151)

  • 引数なし : stdout environ key=value\n (value が NULL なら表示しない)
  • 引数あり : error (PR #276)
    • invalid option (bash とパターンは同じ、error message は異なる)
    • invalid argument (bash と異なる)
  • -- : signify the end of the options
  • 未対応
    • option ではない引数がある時の挙動は要件外
    • exit status 126,127

exit (PR #77)

  • 引数なし
  • 引数あり : 個数や引数の種類によっては error
  • 未対応
    • non-interactive mode 時の prompt,exit 出力 (対応検討)
  • 検討中
    • -- : signify the end of the options (やる)

export (PR #155)

  • 引数なし : sort key, stdout environ key=value\n (する)
  • 引数あり : key=value -> set, key+=value -> join
  • option
    • 全てのoptionがinvalid
  • -- : signify the end of the options
  • 未対応
    • -a -> invalid option
  • 検討中
    • \ を付与して表示 → PDFに解釈しないとあるのでしなさそう
    • sort 高速化

pwd (PR#168)

  • 引数なし : cwd を stdout に表示
  • 引数あり
    • not option : cwd を stdout に表示
    • valid option : cwd を stdout に表示
    • invalid option : error
  • dir の権限がない時
    • linux : 正常終了(0)
    • macOS
      • pwdを保持している場合 : 正常終了(0)
      • pwdを保持していない場合 : error(1)
  • cwd が削除された時
    • pwdを保持している場合 : 正常終了(0)
    • pwdを保持していない場合 : error(1)
  • -- : signify the end of the options
  • 検討中
    • symbolic link (cd と一緒に?)

unset

  • 引数なし
  • 引数あり : error (a valid & an invalid option)
  • -- : signify the end of the options
  • 未対応
    • a NAME is read-only

declare(隠しcommand... Issue #186, #191)

  • option なし
  • option
    • -p : 属性付きで shell 変数と環境変数を一覧表示
      • -- : shell variables
      • -x : environment variables
    • -x : env属性を付与
    • +x : env属性を削除

環境変数

  • PWD
    • getcwd() 成功 : PWD=pwd_path を env に set
    • getcwd() 失敗 : env から key=PWD を削除
  • OLDPWD
    • OLDPWD が env にある
      • EACCES (directory のアクセス権限がない) 以外のエラー
        • env から OLDPWD を削除
    • OLDPWD が env にない
      • env に OLDPWD を set
  • 未対応
    • $_ : shell変数(declare -p | grep _=で見ると属性:--)のため
    • readonly などのx以外の属性

tokenize

  • | : pipe
  • < : redirect-in
  • << : redirect-heredoc
  • > : redirect-out
  • >> : redirect-out-append
  • " ", ' ' : quote
    • 閉じてない : error
  • &&, || : and, or
  • ( ) : sub shell としての parenthesis
    • whitespace が 1個以上間にある : subshell
    • 閉じてない : error
  • |, <, >, &
    • 3個以上 : 有効な 2個以上の op の後に連続して op が来ているので parse error
  • 未対応
    • &
      • 1個 : background 起動の & の役目はない、ただの文字列
    • ()
      • a=("a", "b", "c") のような配列宣言用の括弧
      • (( )) : 算術演算としての2重括弧の役目はない、whitespace のない連続した括弧なので error

parse (Issue#199)

expansion

  • $word
  • $?
  • $+有効なkey : keyを環境変数から探して置換する
  • $+NULL : $ という1文字
  • $ + _ : $_に変換 ($+無効なkey;$+++などと同様)
  • quote で囲まれてる時の挙動、前後と結合してる時の挙動。
  • word splitting
    • quote されてなかったら word split する
  • wildcard (*)
    • current working directory の directory-name, file-name の中から pattern matching するものを ascii 順に sort して出力
    • sort 順はロケールの設定の違いによるもので、42VM の ubuntu の bash に合わせてはいない。ascii順。
    • * は 0 byte 以上の任意の文字に置き換わる
    • 通常 : 隠しファイル以外が検索対象
    • .* : 隠しファイルのみ検索対象
  • 未対応
    • $$ : getpid() が使えないので
    • $ + word以外
    • $'string' : ANSI-C Quoting
    • $"string" : Locale-Specific Translation
    • word splitting
      • export, (declare) : key=value の kye だけ quote されてなかったら word split する。key が展開されたものかそうでないかで挙動が変わる。 (余裕があったら対応)

pipe (PR #48)

  • 複数コマンドの独立実行
  • 先頭と末尾の | : syntax error

redirect

  • <: in
  • << : heredoc
  • > : out
  • >> : append
  • 同プロセス内に複数ある時は 1 番右(最後)の fd がそのプロセスの in_fd, out_fd になる
  • 未対応
    • 1>in2&>in などの n>word

heredoc << (PR#202, PR#244)

  • parse error がなかったらコマンド実行前に heredoc だけ実行
  • 未対応
    • bash は ||, &&( ) の時で parse error を出すタイミングが違くて、parse error でも heredoc だけ実行したりする。

subshell ()

  • 環境変数を引き継いで子プロセスで実行
  • ( ( ) ) space 空けで subshell のネスト
  • 唯の()のネストはskipした( (echo a) ) -> (echo a)
  • こちらで設定したネストの個数 (再帰の深さ) の上限を超えると SYNTAX ERROR で終了。(bash は 4998 くらい)

search PATH

  • 環境変数 PATH の value を : 区切りで検索しに行く
  • permission がない
    • 1 周目全部見て hit しなければ 2 周目?最初のエラーが出る

mallocエラー

  • ft_abort() が呼ばれる。簡易的に exit(134) : 128+SIGABRT
  • 検討中
    • SIGABRT を送りたいが getpid() 使用禁止なので、linux のみ対応として /proc/self/stat を使って無理矢理作るかどうか。

./minishell

  • -i : forced_interactive mode で起動
  • -t