ゆる〜く、shコマンド自作してみた 〜Cはいつも側に〜

Created: 2025/04/25

ChatGPTとお喋りしていたときに、「zsh」って何?っていう話題になりました。
確かに、普段なんとなく使ってるし考えたこともなかったので調べて、自分でshコマンド作った話です。が、別に凝ったコマンド作ったわけではないですw

zshとは?

zshとは、shの拡張版です。
となると、shって何?になります。
shは、ターミナルと通じて、os とユーザーを繋げるインターフェースです。
正直、あんまりピンときてません。インターフェースという言葉はよく聞くけど、なんか分かりづらくないですか?(in my poinion)

この記事がわかりやすかったです↓
https://curtaincall.weblike.jp/portfolio-unix/shell

僕の解釈としては、こんな感じです。

  1. ターミナルを起動する。と同時にshも起動して、ユーザーのコマンドを受け付ける状態になる。
  2. ユーザーがコマンドを入力。(例:mkdir, cd, ls ...)
  3. shはコマンドを受け取り、osにユーザーの命令を伝える。
  4. osが命令を実行

こんな流れで理解していいます。
この一連の流れを一言でインターフェースとして機能していると言えるのか?

これが、ざっくりとしたshの概要ですね。
zshは、このshの強化版、拡張版みたいな感じです。
サイヤ人でいう、スーパーサイヤ人3ですな。
詳細はこちら↓
zshの意味、使い方について学ぶ。

shコマンドを作ろう〜

ここから、実際にコマンドを作っていきます。
shコマンドにも2種類ほどあります。

  1. ビルドインコマンド
  2. 外部コマンド

ざっくりこの2つがあります。
ここの説明は一旦飛ばして、今回は外部コマンド作ってみます🙏🏻
参考↓
ビルドインコマンドについて
外部コマンドについて

外部コマンド一覧

僕は、macOSです。
ターミナルでルート直下のディレクトリを見ると

Terminal
1
2
3
➜  ~ ls ../../
Applications cores        etc          Library      private      System       Users        var
bin          dev          home         opt          sbin         tmp          usr          Volumes

binというディレクトリがあります。
ここに、コマンドの実行ファイルがあります。

見てみると

Terminal
1
2
3
➜  ~ ls ../../bin
[         cat       cp        dash      dd        echo      expr      kill      launchctl ln        mkdir     pax       pwd       rm        sh        stty      tcsh      unlink    zsh
bash      chmod     csh       date      df        ed        hostname  ksh       link      ls        mv        ps        realpath  rmdir     sleep     sync      test      wait4path

cat, echo, mkdirとか見たことあるやつがいますね。
じゃあ、catでcatの中身見てみましょう!
そしたら、中身が全然何書いてあるかわからんでした。

そして、調べたら、単純にCのプログラムをコンパイルしたバイナリファイルでした。
binってbinaryのbinですね。なるほど、そりゃ読めない訳か...
読めるのはフォン・ノイマンぐらいか...笑

ちなみに、コンパイル前のソースコードはGithubで公開されてます!
よかったら↓
https://github.com/wertarbyte/coreutils/tree/master/src

そして、自分でC書いてコンパイルしたファイル入れれば自作できるのか!
と思いやってみます。

ここまで長かった...🙇‍♂️

Cを書く

かなり適当ですが...

hello.c
1
2
3
4
5
6
#include <stdio.h>

int main(){
  printf("hello 自作コマンド\n");
  return 0;
}

これをコンパイルしたバイナリファイルを./bin/に移動したら動くはずです!

1
2
➜  Desktop mv hello ../../../bin
mv: fastcopy: open() failed (to): ../../../bin/hello: Operation not permitted
移動できない!!
なんてこった、基本的にmacOSのセキュリティ上この./binの中身はいじれない仕様だそうです。(確かに、ここ変更できたらまずいか...)
しかし、ChatGPTに相談してみたら、./usr/local/bin/ここに入れて、パスをとうせばいけるらしい!

早速

1
➜  Desktop sudo mv hello ../../../usr/local/bin
sudoが必要でした。

パスの確認

1
2
➜  Desktop echo $PATH
...:/usr/local/bin...
元々通ってました。

自作コマンド実行

1
2
➜  Desktop hello
hello 自作コマンド
お〜!できた
結構感動しました。
個人的に「C言語いつ使うんだよ」と思ってましたが、Cはいつも側に...ごめん

まとめ

自作コマンドでC言語のありがたみを実感でき、いい機会になりました。
shとかも、全然気にしていなかったので、調べると面白い
改めて、プログラミングおもろいな

便利な自作コマンド作ってみたいけど、いつになるかな...笑

最後までありがとうございました!