「Linux」カテゴリーアーカイブ

スワップ領域の作成

# dd if=/dev/zero of=/swapfile bs=1M count=2048
2048+0 レコード入力
2048+0 レコード出力
2147483648 バイト (2.1 GB) コピーされました、 22.799 秒、 94.2 MB/秒
# mkswap /swapfile
スワップ空間バージョン1を設定します、サイズ = 2097148 KiB
ラベルはありません, UUID=xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx
# swapon /swapfile
swapon: /swapfile: 安全でない権限 0644 を持ちます。 0600 がお勧めです。
# chmod 600 /swapfile

/etc/fstab

/swapfile none swap defaults 0 0

確認

# swapon -s
Filename				Type		Size	Used	Priority
/swapfile                              	file	2097148	0	-1

CentOS6にsclのdevtoolsetをインストール

CentOS6でnodejs(v6.9.1)をビルドしようとしたら、makeでエラーになった。
gccとg++の4.8以降が必要だが、CentOS6のgccは4.4.7だからだ。

node-v6.9.1/BUILDING.md

Prerequisites:

* `gcc` and `g++` 4.8 or newer, or
* `clang` and `clang++` 3.4 or newer
* Python 2.6 or 2.7
* GNU Make 3.81 or newer

そこで、sclでgccとg++の4.8以降をインストールしてビルドすることにした。

$ sudo yum install centos-release-scl
$ sudo yum install scl-utils
$ sudo yum install devtoolset-4-gcc devtoolset-4-gcc-c++ devtoolset-4-binutils
$ scl enable devtoolset-4 bash
$ gcc --version
gcc (GCC) 5.2.1 20150902 (Red Hat 5.2.1-2)
Copyright (C) 2015 Free Software Foundation, Inc.
This is free software; see the source for copying conditions.  There is NO
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.

devtoolset-3、devtoolset-4がある。devtoolset-4にしてみた。
devtoolset-4で全部インストールすると大量なので、nodejsのビルドに必要なgcc、g++とbinutilsのみインストールした。

$ scl enable < コレクション1> [< コレクション2> ...] bash

で、インストールしたコレクションが利用できる環境がセットされたbashが起動する。

CentOS 6.7のyum updateでエラー `http://mirror.centos.org/centos/6/SCL/x86_64/repodata/repomd.xml: [Errno 14] PYCURL ERROR 22 - "The requested URL returned error: 404 Not Found"`

CentOS release 6.7 (Final)

yum updateで以下のエラー

http://mirror.centos.org/centos/6/SCL/x86_64/repodata/repomd.xml: [Errno 14] PYCURL ERROR 22 - "The requested URL returned error: 404 Not Found"
他のミラーを試します。
エラー: Cannot retrieve repository metadata (repomd.xml) for repository: scl. Please verify its path and try again

解決方法

$ sudo yum remove centos-release-SCL
$ sudo yum update # CentOS-6.8にアップデート
$ sudo yum install centos-release-scl
$ sudo yum update

情報源: 0010925: Yum update fails on a 404 returned from http://mirror.centos.org/centos/6/SCL/x86_64/repodata/repomd.xml - CentOS Bug Tracker

CentOS7でpassenger-configやpassenger-statusがエラーになる

CentOS7でpassenger-configやpassenger-statusがエラーになる。

CentOS Linux release 7.2.1511 (Core)
Apache/2.4.6 (CentOS)
Phusion Passenger 5.0.23 (passenger-install-apache2-moduleでインストール)

$ passenger-config restart-app
*** ERROR: Phusion Passenger doesn't seem to be running. If you are sure that it
is running, then the causes of this problem could be one of:

 1. You customized the instance registry directory using Apache's
    PassengerInstanceRegistryDir option, Nginx's
    passenger_instance_registry_dir option, or Phusion Passenger Standalone's
    --instance-registry-dir command line argument. If so, please set the
    environment variable PASSENGER_INSTANCE_REGISTRY_DIR to that directory
    and run this command again.
 2. The instance directory has been removed by an operating system background
    service. Please set a different instance registry directory using Apache's
    PassengerInstanceRegistryDir option, Nginx's passenger_instance_registry_dir
    option, or Phusion Passenger Standalone's --instance-registry-dir command
    line argument.

原因

Passengerのinstance registry directory(Apacheの場合はPassengerInstanceRegistryDir、Nginxの場合はpassenger_instance_registry_dir)が見つからないのが原因。
instance registry directoryを明示的に指定していない場合のデフォルトは/tmpなので、instance registry directoryは/tmp下に作成されるが、SystemdのPrivateTmpオプションがhttpdで有効になっている(デフォルト)ため、httpd専用の/tmp(実際には/tmp/systemd-private-XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX-httpd.service-XXXXXX/tmp)に作成される。このディレクトリが、別プロセスであるpassenger-configやpassenger-statusには見つけられないのだ。

SystemdのPrivateTmpによって発生する問題なので、RHEL7でも同様だろう。

解決方法1: PassengerInstanceRegistryDirを明示的に指定する

PrivateTmpは有効にしたままで対処する方法。
Passengerのinstance registry directoryがhttpd専用の/tmpに作成されないように、明示的に指定する。

(Apacheの場合)
/etc/httpd/conf/httpd.conf

PassengerInstanceRegistryDir /var/run/passenger-instreg

/var/run(=/run)に置くファイル、ディレクトリは、再起動すると削除されてしまうので、tmpfiles.dに設定が必要。
詳細は、man 5 tmpfiles.d を参照。

/etc/tmpfiles.d/passenger.conf

D /var/run/passenger-instreg 0755 root root

passenger-status、passenger-configを実行するユーザにPASSENGER_INSTANCE_REGISTRY_DIRの設定が必要。

~/.bash_profile

export PASSENGER_INSTANCE_REGISTRY_DIR=/var/run/passenger-instreg

capistrano-passengerを使用している場合は、デプロイ後のpassenger-config restart-appでPASSENGER_INSTANCE_REGISTRY_DIRの指定が必要なので、該当するステージのデプロイレシピに以下を追加する。

set :default_env, {
  ...(略)..,
  "PASSENGER_INSTANCE_REGISTRY_DIR" => "/var/run/passenger-instreg"
}

以上を設定したら、システムを再起動する。

解決方法2: httpd.serviceのPrivateTmpを無効にする

httpdのPrivateTmpを無効にしてしまう方法。
/usr/lib/systemd/system/httpd.service を /etc/systemd/system にコピーすると、/etc/systemd/system に置いたファイルが優先される。コピーしたhttpd.serviceのPrivateTmpをfalseに変更する。

/etc/systemd/system/httpd.service

...(略)
PrivateTmp=false
...(略)

変更後、

$ sudo systemctl daemon-reload
$ sudo systemctl restart httpd.service

情報源: CentOS 7 で Phusion Passenger の passenger-status を実行するとエラーとなる - Qiita
お前らもさっさとハマって泣くべきCentOS7の落とし穴4つ - Qiita
Handle systemd PrivateTmp #1475
Systemd入門(5) - PrivateTmpの実装を見る - めもめも

ソースをビルドするために必要なパッケージをインストールする

Ubuntu, Debian

apt-get build-dep <package>

エラーになる場合

$ sudo apt-get build-dep ruby
パッケージリストを読み込んでいます... 完了
E: sources.list に 'ソース' URI を指定する必要があります

/etc/apt/sources.list で dep-srcを有効にする必要がある。
debを有効にしているURLは、対応するdeb-srcのコメントを外して有効にする。

deb http://jp.archive.ubuntu.com/ubuntu xenial main restricted
deb-src http://jp.archive.ubuntu.com/ubuntu xenial main restricted
...

CentOS, RHEL

yum-builddep <package>

Ubuntuでコアダンプが出力できないことがある

Ubuntu(14.04 LTS)で、コアダンプが出力できない場合があるという現象が発生した。
できる場合もある。プログラムによる。

以下のように、ulimitは問題ない。

$ ulimit -c unlimited
$ ulimit -a
core file size          (blocks, -c) unlimited
data seg size           (kbytes, -d) unlimited
scheduling priority             (-e) 0
file size               (blocks, -f) unlimited
pending signals                 (-i) 15739
max locked memory       (kbytes, -l) 64
max memory size         (kbytes, -m) unlimited
open files                      (-n) 1024
pipe size            (512 bytes, -p) 8
POSIX message queues     (bytes, -q) 819200
real-time priority              (-r) 0
stack size              (kbytes, -s) 8192
cpu time               (seconds, -t) unlimited
max user processes              (-u) 15739
virtual memory          (kbytes, -v) unlimited
file locks                      (-x) unlimited

コアダンプの出力先を確認。

$ sudo sysctl -a | grep core_pattern
kernel.core_pattern = |/usr/share/apport/apport %p %s %c %P

Ubuntu(14.04 LTS)では、デフォルトでcore_patternがapportを使用するように設定されていた。

コアダンプが出力されるケースでは、カレントディレクトリにcoreというファイルが出力される。
コアダンプが出力されないケースでは、apportでエラーが発生していた。

/var/log/apport.log

ERROR: apport (pid 3480) Tue May 12 18:48:31 2015: called for pid 3479, signal 6, core limit 18446744073709551615
ERROR: apport (pid 3480) Tue May 12 18:48:31 2015: ignoring implausibly big core limit, treating as unlimited
ERROR: ERROR: apport (pid 3480) Tue May 12 18:48:31 2015: Unhandled exception:
Traceback (most recent call last):
  File "/usr/share/apport/apport", line 357, in <module>
    (info['ExecutablePath'], info['ProcCmdline']))
  File "/usr/share/apport/apport", line 99, in error_log
    apport.error('apport (pid %s) %s: %s', os.getpid(), time.asctime(), msg)
  File "/usr/lib/python3/dist-packages/apport/__init__.py", line 44, in error
    sys.stderr.write(msg % args)
UnicodeEncodeError: 'ascii' codec can't encode character '\ufffd' in position 143: ordinal not in range(128)
ERROR: apport (pid 3480) Tue May 12 18:48:31 2015: pid: 3480, uid: 0, gid: 0, euid: 0, egid: 0
ERROR: apport (pid 3480) Tue May 12 18:48:31 2015: environment: environ({})

apportでエラーになっているから、コアダンプが出力されないのだ。
pythonのエラーのようだがよく分からないので、core_patternにapportを使用しないよう設定することにした。

# echo 'core.%e.%p' > /proc/sys/kernel/core_pattern
$ ulimit -c unlimited
$ cat segfault.c
#include <stdio.h>

int main(void)
{
  char *s = "hello, world!";
  *s = 'H';

  return 0;
}
$ gcc -Wall -g -o segfault segfault.c
$ ./segfault 
Segmentation fault (コアダンプ)
$ ls
core.segfault.3423  segfault  segfault.c

echoで変更した設定は、システム再起動後には無効になってしまう。
変更を永続化するためには、/etc/sysctl.confに設定する。

情報源: E.4. sysctl コマンドの使用

/etc/sysctl.conf

kernel.core_pattern = core.%e.%p

しかし、なぜかシステムを再起動すると、apportを使用するように設定が戻ってしまっている。
システム起動時のapport起動で、設定を上書きしているらしい。
情報源: 12.04 - How to permanently edit the core_pattern file? - Ask Ubuntu
これを止めさせるには、apportを無効にして再起動する。

/etc/default/apport

# set this to 0 to disable apport, or to 1 to enable it
# you can temporarily override this with
# sudo service apport start force_start=1
#enabled=1
enabled=0

コマンドの終了コードが128を超える場合はシグナルで終了した場合

コマンドの終了コードが128を超える場合はシグナルで終了した場合。

$ man bash
The return value of a simple command is its exit status, or 128+n if the command is terminated by signal n.
$ some_command
$ echo $?
139

例えば上記のように終了コードが139なら、139=128+11なので、シグナル11で終了したということになる。
man signalとかで見ると、シグナル11はSIGSEGVで、セグメンテーション違反だということが分かる。