共用のサーバなどでsudo権限がない状態でapt-get, yum, brewなどでパッケージをインストールしたいと思った時にpermission deniedで怒られたことは誰しもあると思います。
その時に自分のローカルの環境にインストールする際にいつもやり方を忘れてしまうので、流れをざっとまとめてみました。
ちなみにdockerを使って各イメージの用途に合わせて必要なパッケージをインストールすれば良い、という話もありますが、tmuxやscreenなどホスト側にインストールしたい場合もあると思うので知っておいて損はないはずです。
手順
- 共有ライブラリのソースをダウンロード
- 共有ライブラリをコンパイル、ローカルのフォルダにインストール
- パッケージのソースをダウンロード
- パッケージをコンパイル、ローカルのフォルダにインストール
- インストールしたローカルのフォルダにパスを通す
以下でtmuxをローカルにインストールする方法を例に説明していきます。
ちなみにインストール方法は以下のページを参考にさせていただきました。
https://qiita.com/kentarosasaki/items/f6769109a251fcc96208
共有ライブラリのソースをダウンロード
共有ライブラリとは以下のサイトの言葉を引用すると、
https://www.weblio.jp/content/%E5%85%B1%E6%9C%89%E3%83%A9%E3%82%A4%E3%83%96%E3%83%A9%E3%83%AA
共有ライブラリとは、複数のプログラムが共通して利用する汎用性の高いプログラムの部品の集まりのことである。
です。通常、tmuxなどのパッケージには必要なライブラリが同梱されているのですが、汎用的なライブラリ(共有ライブラリ)についてはパッケージには含まれていません。tmuxでは「libevent(tmux-1.2以降で必要)」と「ncurses」が必要な共有ライブラリで且つubuntuやcentOSなどの環境でデフォルトで入っていないライブラリです。そのため、パッケージのインストール前にこれらの共有ライブラリをダウンロード&インストールしておく必要があります。
ソースのダウンロードをする前にソースファイルを置くディレクトリを作りましょう。
mkdir -p ~/tools/src
次にlibeventをダウンロードします。
ちなみに、libeventはファイルディスクリプタに特定のイベントが生じた際にcallback関数を実行するイベント通知プログラムです。例えば、実行中のスクリプトが標準エラー出力に出力を開始した、などの特定のイベントが起きたことを瞬時に検知してそれをトリガーに別の処理を実行する、といった場合にイベント検知(通知)に使えます。
wget https://github.com/libevent/libevent/releases/download/release-2.1.8-stable/libevent-2.1.8-stable.tar.gz -P ~/tools/src
cd ~/tools/src
tar zxf libevent-2.1.8-stable.tar.gz
次にncursesをダウンロードします。ncursesはキー入力や画面表示など、端末のテキストユーザインタフェース(TUI)を作る際に使うライブラリです。
wget -nc ftp://ftp.invisible-island.net/ncurses/ncurses-6.1.tar.gz -P ~/tools/src
cd ~/tools/src
tar zxf ncurses-6.1.tar.gz
ちなみに、もはやwgetすらない場合はブラウザからftpサイトやgithubのサイトにアクセスしてダウンロードし、インストールしたい環境にscpなどで移してインストールすればOKです。本ページと同じ方法でwget自体もインストールできます。
また、ソースのリンクが消滅している場合もブラウザでソースのリンクを探してみましょう。
例えば、ncursesならgoogleで検索すると下記のリンクが出てきて、ソースのリンクが貼ってあることがわかるかと思います。
https://www.gnu.org/software/ncurses/
共有ライブラリをコンパイル、ローカルのフォルダにインストール
ここからは共有ライブラリのインストールです。
まずはインストールする前に、インストールするサーバやlaptopのOSや必要なライブラリが存在するかどうかをチェックしてMakefileを作成するconfigureスクリプトを実行します。
cd ~/tools/src/libevent-2.1.8-stable
./configure --prefix=${HOME}/tools
Makefileはソースコードをコンパイルする(つまりC言語などの人間が読める形のファイルを機械語に変換する)処理が記述されたファイルです。このMakefileにはconfigureファイルで指定されたパッケージのインストール先が記述されていますが、configureを実行する際に特に指定をしない基本的には「/usr/local」が指定されることになります。ところが/usr以下はsudo権限がないと書き込みができないため、このままだとインストール時にエラーが起きます。そこでconfigure実行時に--prefixをつけることでパッケージのインストール先をローカルの書き込み権限のあるフォルダに指定します。
prefixを指定するのではなくMakefileそのものを編集してインストール先を変更することもできます。
実行すると下記のように環境を確認して、config.statusにまとめ、Makefileなどのファイルを作成していることが確認できます。
checking for struct sockaddr_storage.__ss_family... no
checking for struct so_linger... no
checking for socklen_t... yes
checking whether our compiler supports __func__... yes
checking for the pthreads library -lpthreads... no
checking whether pthreads work without any flags... yes
checking for joinable pthread attribute... PTHREAD_CREATE_JOINABLE
checking if more special flags are required for pthreads... -D_THREAD_SAFE
checking size of pthread_t... 8
checking for library containing ERR_remove_thread_state... -lcrypto
checking that generated files are newer than configure... done
configure: creating ./config.status
config.status: creating libevent.pc
config.status: creating libevent_openssl.pc
config.status: creating libevent_pthreads.pc
config.status: creating libevent_core.pc
config.status: creating libevent_extra.pc
config.status: creating Makefile
config.status: creating config.h
config.status: creating evconfig-private.h
config.status: evconfig-private.h is unchanged
config.status: executing depfiles commands
config.status: executing libtool commands
Makefileには下記のような記載がありました。
prefix = /Users/danshari-ni/tools
私の環境では${HOME}=/Users/danshari-ni なので、configureのオプション--prefixで指定した値がMakefileにハードコードされていることがわかります。
次にmakeコマンドを使ってコンパイルを行います。
make
次にmake installを実行し、makeコマンドで生成されたバイナリファイルなどを--prefixで指定したディレクトリにコピーします。
make install
インストールが終わると~/tools配下にlib, bin, includeといったコンパイル済みのライブラリのファイルを格納するディレクトリが作成され、libevent関連のバイナリファイルが配置されています。
ちなみに、Mac OSXではmake実行時に下記のようなエラーが出てくるかもしれません。
bufferevent_openssl.c:66:10: fatal error: 'openssl/bio.h' file not found
その場合はconfigure実行時に下記を実行してください。
./configure --prefix=${HOME}/tools LDFLAGS="-L/usr/local/opt/openssl/lib" CFLAGS="-I/usr/local/opt/openssl/include"
同様にしてncursesもインストールします。
cd ~/tools/src/ncurses-6.1
./configure --prefix=${HOME}/tools
make
make install
パッケージのソースをダウンロード
共有ライブラリの時と同様にwgetを使ってtmuxのソースファイルをダウンロードします
wget https://github.com/tmux/tmux/releases/download/2.6/tmux-2.6.tar.gz -P ~/tools/src
cd ~/tools/src
tar zxf tmux-2.6.tar.gz
パッケージをコンパイル、ローカルのフォルダにインストール
configureを実行します。
cd ~/tools/src/tmux-2.6
./configure --prefix=${HOME}/tools LDFLAGS="-L${HOME}/tools/lib" CFLAGS="-I${HOME}/tools/include"
LDFLAGSはMakefileで記述するライブラリの場所で、今回インストールしたlibeventとncursesは~/tools/libに配置されているので、ここを指定します。
CFLAGSはMakefileで記述するインクルードファイルの場所で、今回インストールしたlibeventとncursesのインクルードファイルは~/tools/includeに配置されているので、ここを指定します。
ソースファイルをコンパイルしてインストールします。
make
make install
ちなみに私の環境では
curses.h not found
のようなエラーが出たので、~/tools/includeを見るとncursesという名のディレクトリが作成されていて、この中にcurses.hが入っていました。これらのファイルを~/tools/include/にmvで移動するとインストール時にエラーが出なくなりました。
インストールしたローカルのフォルダにパスを通す
最後にパッケージと共有ライブラリのパスを通します。~/.bash_profileに下記を追記してください。
export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:${HOME}/tools/lib # libeventなどの共有ライブラリへのパスを通す
export PATH=$PATH:/home/nakamura/tools/bin #ローカルにインストールしたパッケージへパスを通す
以上でsudo権限がない状態でローカルにパッケージや依存ライブラリをインストールできました。