2010/02/10

ディスプレイカードの温度表示

ディスプレイカードの温度上昇が原因と思われる 表示不正が稀に発生するので、 ディスプレイカードの温度を取得して表示してみた。
取得した温度は普段利用しているデスクトップ環境で常時表示している GKrellM (1) のセンサー表示部分に多少無理やり表示してしまう事にする。
GKrellM (1) は mbmon (1) をデーモンとして起動しておくと mbmon (1) から取得した3種類の温度を表示できるので、 mbmon (1) を改造して3番目の温度を ディスプレイカードの温度に変更してしまうというのが 「多少無理やり」な方法だ。

ディスプレイカードに nVidia の GeForce を使用しているので、 温度は nvidia-settings (1) の --query オプションを利用すると取得できる。 まずは mbmon (1) のソースを改造し nvidia-settings (1) を popen (3) で呼び出してみると 確にディスプレイカードの温度は取得できるのだが、 温度取得のたびに nvidia-settings (1) コマンドが起動されるので システムリソースに負荷がかかり過ぎてしまう。
そこで nvidia-settings (1) のソースに付属している サンプルプログラムを調べてみると、 割と簡単にディスプレイカードの温度を取得できる事が判ったので mbmon (1) から直接ディスプレイカードの温度を取得する。

まずは、必要となる NVCtrl.hNVCtrlLib.hlibXNVCtrl.a の3ファイルを準備するために、 nvidia-settings をコンパイルする。
ports/x11/nvidia-settingsmake (1) を実行すると、 ports/x11/nvidia-settings/work/nvidia-settings-1.0/src/libXNVCtrl に上記3ファイルが作成される。

次に mbmon (1) を修正してプログラムをインストールする。
ports/sysutils/mbmon ディレクトリで make configure まで実行した後で以下のパッチを適用し、 上記3ファイルを prts/sysutils/mbmon/work/xmbmon205にコピーして make (1)すると ディスプレイカードの温度を取得できる mbmon (1) ができる。
この mbmon (1) をデーモンとして起動すると GKrellM (1) のセンサー表示部分の 温度表示の 3番目にディスプレイカードの温度が表示できる。

Image: gkrellm.jpg

diff -rcN xmbmon205.orig/Makefile xmbmon205/Makefile
*** xmbmon205.orig/Makefile   2010-02-10 15:42:38.000000000 +0900
--- xmbmon205/Makefile        2010-02-10 15:45:16.000000000 +0900
***************
*** 25,30 ****
--- 25,34 ----
  LIBS= -lm 
  LIBSX=$(LIBS)  -L/usr/X11R6/lib -lXt  -lSM -lICE -lX11 
  
+ INCLUDES+= -I. -I/usr/X11R6/include
+ LIBS+= -L. -lXNVCtrl -L/usr/X11R6/lib -lXext -lX11
+ DEFS+= -DNVHACK
+ 
  #CC=/compat/linux/usr/bin/gcc
  CC=cc
  CFLAGS+=$(INCLUDES) $(DEFS)
diff -rcN xmbmon205.orig/mbmon.c xmbmon205/mbmon.c
*** xmbmon205.orig/mbmon.c    2010-02-10 15:31:52.000000000 +0900
--- xmbmon205/mbmon.c         2010-02-10 15:17:02.000000000 +0900
***************
*** 36,41 ****
--- 36,47 ----
  #  include <sys/sysctl.h>
  #endif
  
+ #ifdef    NVHACK
+ #include <X11/Xlib.h>
+ #include "NVCtrl.h"
+ #include "NVCtrlLib.h"
+ #endif
+ 
  #include "mbmon.h"
  
  static const char *MyName = "mbmon";
***************
*** 510,515 ****
--- 516,536 ----
  
      getTemp(&temp1, &temp2, &temp3);
  
+ #ifdef    NVHACK
+     {
+ 
+         Display    *dpy;
+         int        temp;
+ 
+         if((dpy = XOpenDisplay(NULL))){
+             if(XNVCTRLQueryAttribute(dpy, 0, 0, NV_CTRL_GPU_CORE_TEMPERATURE, &temp))
+                 temp3 = temp;
+             XCloseDisplay(dpy);
+         }
+         
+     }
+ #endif
+ 
  /* get fan speeds */
  
      getFanSp(&rot1, &rot2, &rot3);

2010/01/14

MyJVN チェッカーサービス

JVN - Japan Vulnerability Notes - が セキュリティ設定チェッカ、バージョンチェッカのサービスを実施している。

これらのサービスは Microsoft Windows 専用のサービスなのだが、 Windows の機能である USB メモリ自動実行機能の設定の確認や、 インストールされている Adobe Reader や Flash Player などの バージョンをチェックしてくれる。
最近は GENO/Gumblar と呼ばれているマルウェアなど 悪意のあるソフトウェアによる Web サイトの改ざんなどが話題になっているが、 そういった悪意のソフトウェアによる被害を防ぐための一つの足がかりとして こういったツールも積極的に利用すると良いだろう。

2009/10/16

php からのディスクアクセス

php だという時点で既にアレなんだが…

php からディレクトリにある全ファイルの一覧を取得する処理のパフォーマンスを exec()popen()opendir() を利用した処理で比較してみる。

方法は単純にテスト用のディレクトリに 500 ファイルを用意して、 それぞれの関数を使用してファイル名一覧を取得する処理を 10 回実行した場合の処理速度を計測する。

exec("ls -1") 0.774762
popen("ls -1") 0.865914
opendir() 0.136642

外部 shell を実行しないので opendir() が早いだろうとは予想していたが、 これほど差が出るとは思わなかった。
パフォーマンスを優先する場合は勿論だが、 余計なプロセスを生成しないので opendir() が地球に優しい様だ。

  1<?
  2
  3    $func = array("byexec", "bypopen", "byopendir");
  4
  5    for($i=0; $i<3; $i++){
  6        $dist = array();
  7        $start[$i] = gett();
  8        for($j=0; $j<100; $j++)
  9            $dist[$j] = $func[$i]("/tmp/test");
 10        $end[$i] = gett();
 11
 12        printf("%-10s:%f\n", $func[$i], $end[$i] - $start[$i]);
 13    }
 14
 15    function    byexec($dir)
 16    {
 17
 18        exec("ls -1 $dir", $output);
 19
 20        return($output);
 21
 22    }
 23
 24    function    bypopen($dir)
 25    {
 26
 27        if(($fp = popen("ls -1 $dir", "r"))){
 28            while($buf = fgets($fp))
 29                $output[] = trim($buf);
 30            pclose($fp);
 31
 32        }
 33
 34        return($output);
 35
 36    }
 37
 38    function    byopendir($dir)
 39    {
 40
 41        if($dir = dir($dir)){
 42            while($file = $dir->read())
 43                $outout[] = trim($file);
 44            $dir->close();
 45        }
 46
 47    }
 48
 49    function    gett()
 50    {
 51
 52        $t = gettimeofday();
 53        return((float)($t['sec'] + $t['usec'] / 1000000.0));
 54
 55    }
 56
 57?>
    

ついでにシェルの glob なパターン指定を利用して 指定した文字列にマッチするファイル名の一覧取得を行う場合のテストもしてみた。

20090219000 から 20090219499 までの500個のファイルの中から、 200902192?? にマッチするファイル名の一覧取得で時間を計測してみる。

exec("ls -1 200902192??") 0.883770
popen("ls -1 200902192??") 0.902392
opendir()→preg_match("/200902192../") 0.188792
glob("/200902192../") 0.203928

exec()popen() が遅いのは相変わらずだが、 preg_match()の呼出しが意外に早かったのが驚き。
正規表現のマッチ処理って基本的に相当時間がかかる筈なんだが…
glob() はファイルシステムに自分でアクセスしてる様なので早い。
複雑なパターン指定が必要ならpreg_match()の方が柔軟だが、 シェルに渡せる程度のパターン指定なら glob() を利用するのが 可読性やメンテナンス性と性能が両立できて良いのかも?

2009/08/20

Namazu

Namazu はオープンソースの全文検索システムで、 メイリングリストの検索やサイト内検索用のツールとして 様々な Web Site で利用されている。
2004年12月に公表されたその Namazu のセキュリティ・ホールである 「Namazu におけるクロスサイト・スクリプティングの脆弱性」の 対策を適用していないサイトが 非常に多く見受けられるそうだ。

もう4年半も前の脆弱性を対策せずに放置しているのは、 今の世の中では単なるサイト管理の怠慢では済まされない問題だと思う。
なぜなら、これらの脆弱性が悪用された場合に ユーザのブラウザ上で任意のスクリプトが実行されてしまう事で、 最悪な場合フィッシング詐欺などの踏み台に使われてしまう可能性があるから。
管理者はもっと責任をもってサイトの管理を行うべきじゃないのか?

2009/07/03

ファイルのオーバーライド

通常のパイプ動作するフィルタコマンドでは 元ファイルを直接オーバライドできない。
例えば sort (1) の -o オプションの様に 元ファイルのオーバライド指定ができる (この動作をスポンジ動作というらしい)もの以外での処理について。

一番簡単で誰でも思いつくのが一時ファイルを利用するやりかた。

$ command < foo.dat > foo.new 
$ mv foo.new foo.dat
この方法だと command の実行中に割込が発生したりすると 一時ファイルが残ってしまい美しくない。

$ cat foo.dat | ( sleep 1; command > foo.dat)
この方法だと sleep (1) の時間がうっとおしく、 データ量や command の速度などによって失敗する場合もありうる。

$ (rm foo.dat; command > foo.dat) < foo.dat
若干判りづらいのだがこれで確実に成功する。
先行する rm (1) は必須である。 rm (1) がない場合は外側のシェルが '<' により O_RDONLYopen (2) するファイルと 内側のシェルが '>' により O_RDONLY|O_TRUNCopen (2) するファイルの inode が等しいので OS は同一ファイルと見做し、 command の標準入力は O_TRUC により truncate されたファイルとなってしまう。
対して rm (1) がある場合は外側のシェルが O_RDONLYopen (2) するファイルと 内側のシェルが O_RDONLY|O_TRUNCopen (2) するファイルの inode が異なるので O_TRUNC による truncate は影響を受けない。

2009/06/18

SIGPIPE

  1#!/bin/sh
  2    :
  3if ${any_command} | grep -q "${word}"
  4then
  5    :
    

linux 上で実行しているこの様なシェルスクリプトの ${any_commnand} がたまに異常終了している事がある。
気になって調べてみると SIGPIPE を受信してエラー終了している様だ。
grep (1) のマニュアルを調べてみると

Exit immediately with zero status if any match is found, even if an error was detected.

man grep



と明記してあるので grep (1) が先に終了してしまったので、 ${any_command} に SIGPIPE が送信されているらしい。

スクリプト中で grep -q は割と多用すると思うが、 こんな落とし穴もあるので気をつけなくては。
そもそも grep (1) なんてよく使うコマンドだから かえってマニュアルを熟読しないだろうし、 だからこの様な BUG が潜む原因にもなっていると思う。
というか実は常識的な話だったりする?

2009/05/18

The myth of unix security

Kaspersky 社のブログ によると、 FreeBSD や Linux をターゲットとしたマルウェアが発見されたとの事です。

It’s often argued that *nix systems are secure, and there are’t any viruses or malware for such systems. This hasn’t been true for a long time, as two recently detected malicious programs prove.

Kaspersky 社の Blog より



超適当に翻訳してみると、 『多くの場合、unix システムはセキュリティを確保しているので、 ウィルスやマルウェアはありえないと主張されていた。 これらの事は既に真実ではない事が最近検出された2種類の悪意あるプログラム により証明されている。』 みたいな事が言われている。
今回は通常の perl スクリプトと FreeBSD や Linux 上で実行可能な 暗号化された perl スクリプトの 2 種類のマルウェアが発見されたらしく、 それぞれ迷惑メイルを送信する「ボット」や、 セキュリティソフト風の怪しいソフトウェアを販売するための 詐欺サイトを宣伝・販売するウェブサイトを構築してしまうらしい。

Windows に比較すれば FreeBSD や Linux の方が多少は安全ではあるが、 それはあくまでも相対的な比較においての安全であり 絶対的に安全という訳ではない。 そんな事はちょっと考えてみれば常識だろって位の事だと思うのだが、 一部では「Linux だから安全っ」みたいな事を妄信している人がいる様だ。
自分だけが被害に遭うだけならそれでも全然構わないのだが、 マルウェアに侵入を許してしまうと迷惑メイルの発信源になったり、 他のコンピュータへの攻撃の足掛かりになったりする事で、 他人にも迷惑を及ぼす危険性があるので是非とも心を改めて欲しい。
まぁ、人に迷惑をかけるなって事ですね。
コンピュータである以上「絶対に安全」なんてあり得ない事なので、 ちゃんとセキュリティ情報などには気を配り、 万全の対策をしなくてはならないのはもはや常識の範疇だと思う。

2009/04/09

POSIX.2 標準仕様のシェルによる変数展開

シェルスクリプトを作成する際に シェル変数に値を代入したり参照したりする事は頻繁に発生するが、 シェル変数の展開にも便利な使い方がある。
basename (1) や dirname (1) と同様な動作が シェルの組込みとして利用できるので資源の節約にもつながり、 上手に利用すると可読性の高いスクリプトが作成できる。

機能一覧

${parameter:-word} デフォルト値への置換
${parameter:=word} デフォルト値の代入
${parameter:?[word]} 値の検査とエラー
${parameter:+word} 代替値の使用
${#parameter} 文字列長の取得
${parameter%word} 最短後置パターンの削除
${parameter%%word} 最長後置パターンの削除
${parameter#word} 最短前置パターンの削除
${parameter##word} 最長前置パターンの削除

デフォルト値への置換

  • ${parameter:-word}
  • ${parameter} が NULL の場合 word に置換される。

    $ echo ${foo}
    
    $ echo ${foo:-FOO}
    FOO
    $ echo ${foo}
    
    $ foo=BAR
    $ echo ${foo:-FOO}
    BAR
    

デフォルト値の代入

  • ${parameter:=word}
  • ${parameter} が NULL の場合 word に置換され、 かつ parameter に代入される。

    $ echo ${foo}
    
    $ echo ${foo:=FOO}
    FOO
    $ echo ${foo}
    FOO
    $ echo ${foo:=BAR}
    FOO
    

値の検査とエラー

  • ${parameter:?[word]}
  • ${parameter} が NULL の場合 word が指定されていればその値を、 指定されていない場合はデフォルトの値を表示し、 非対話実行されているシェルをエラー終了させる。

    $ echo ${foo}
    
    $ echo ${foo:?value not set}
    value not set
    

代替値の使用

  • ${parameter:+word}
  • ${parameter} が NULL 以外の場合 word に置換される

    $ echo ${foo:+FOO}
    
    $ echo ${foo}
    
    $ foo=BAR
    $ echo ${foo}
    BAR
    $ echo ${foo:+FOO}
    FOO
    

文字列長の取得

  • ${#parameter}
  • ${parameter} の文字列としての長さに置換される

    $ echo ${foo}
    
    $ echo ${#foo}
    0
    $ foo=FOO
    $ echo ${foo}
    FOO
    $ echo ${#foo}
    3
    

最短後置パターンの削除

  • ${parameter%word}
  • ${parameter} の右から word で示されるパターンの最短部分を削除する

    $ foo=/foo/bar/baz
    $ echo ${foo%/*}
    /foo/bar
    $ foo=foo.c
    $ echo ${foo%.*}
    foo
    $ foo=foo
    $ echo ${foo%.*}
    foo
    

最長後置パターンの削除

  • ${parameter%%word}
  • ${parameter} の右から word で示されるパターンの最長部分を削除する

    $ foo=foo.example.com
    $ echo ${foo%%.*}
    foo
    $ foo=http://www.example.com:8888/
    $ echo ${foo%%:*}
    http
    $ foo=foo
    $ echo ${foo%%.*}
    foo
    

最短前置パターンの削除

  • ${parameter#word}
  • ${parameter} の左から word で示されるパターンの最短部分を削除する

    $ foo=foo.c
    $ echo ${foo#*.}
    c
    $ foo=foo.example.com
    $ echo ${foo#*.}
    example.com
    $ foo=foo
    $ echo ${foo#*.}
    foo
    

最長前置パターンの削除

  • ${parameter##word}
  • ${parameter} の左から word で示されるパターンの最長部分を削除する

    $ foo=foo.example.com
    $ echo ${foo##*.}
    com
    $ foo=/foo/bar/baz
    $ echo ${foo##*/}
    baz
    $ foo=foo
    $ echo ${foo##*.}
    foo
    

2009/03/31

Dual Head + KVM Switch + Synergy その3

ATEN の CS-1734A を入手したのでデスクトップ環境を変更してみた。

メインの生活環境となる FreeBSD マシンはビデオカードに nVidia の GeForce 7300 を使用しているので、 Dual Head を活用して画面を VGA と DVI に出力している。
VGA 出力は CS-1734A 経由で正面の BENQ 24 インチメインディスプレイに繋がり、

  • 生活環境としての FreeBSD
  • あまり使う機会は少ないが何となく必要な Windows Xp Professional
  • 使いやすさと美しさが最高な Mac OS X 10.5 Leopard
  • 検証や Linux 独自の作業に必要な ubuntu
の4台を接続し切替ながら使用している。

DVI 出力は メインディスプレイの右隣に設置してある 19 インチのサブディスプレイに直接接続しており、 常時 FreeBSD の画面を表示している。
コンソール使用時は双方に同じ内容が出力されているが、 X Window を起動するとそれぞれ独立した別のスクリーンとして動作できるので、 メインディスプレイに FreeBSD の画面以外が表示されている場合でも サブディスプレイには FreeBSD の画面が表示されていて便利である。
勿論キーボードとマウスはそれぞれのスクリーンを透過的にアクセスできるので、 メインディスプレイにも FreeBSD の X Window が表示されている場合、 マウスカーソルはメインディスプレイの右側からサブディスプレイの左側にかけて 連続して移動する。

CS-1734A 経由で接続されているメインキーボード/マウス以外に、 FreeBSD マシンには BlueTooth 経由でサブキーボード/マウスも接続されているので、 メインディスプレイに FreeBSD が表示されていない (メインのキーボード/マウスが他の OS で利用されている)場合でも、 サブキーボード/マウスを利用してサブディスプレイ上に表示されている FreeBSD を操作する事が可能である。

更にサブディスプレイ上に表示されている X Window のスクリーンでは synergy サーバが動作しており、 Windows Xp、Mac OS X、ubuntu がそれぞれ synergy クライアントとなっているので 各 OS 上でのコピー & ペーストが可能になっている。
ちなみにサブディスプレイ側でマウスカーソルを画面上部に移動すると Mac OS X、 画面下部に移動すると Windows Xp、画面右に移動すると ubuntu に キーボードとマウスの対話権が移動する。
例えばメインディスプレイに Mac OS X が表示されている場合、 メインキーボード/マウスを操作するとメインディスプレイ上で Mac OS X の操作ができ、 サブキーボード/マウスを操作するとサブディスプレイ上で FreeBSD の操作ができるのだが、 サブディスプレイ上でサブマウスのカーソルを画面上部に移動すると、 メインディスプレイ上の Mac OS X の操作を synergy 経由のサブキーボード/マウスでできてしまう。

文章で説明するのが困難な程複雑な仕組みになってしまった気がする。


複雑な仕組みになってしまったのでたまに混乱してしまう…

2009/03/30

ATEN CS-1734A + Logicool V450 Nano

職場で利用しているマウスが 10 年以上前に購入した有線マウスなので、 ワイヤレスで快適な環境を目指し Logicool の V450 Nano を購入した。
本日届いたので早速 CS-1734A の CONSOLE ポートに接続してみると… マウスカーソルが縦方向にしか移動しない。
それぞれの OS が動作するハードウェアの USB ポートに V450 Nano の レシーバを直接差し込むと当然ながら正常に動作しており、 CS-1734A につながっている FreBSD、Windows Xp、Leopard、Linux の 全てで同じ動作なので OS の問題ではなく KVM Switch の問題らしい。
USB マウスは CS-1734A(というか KVM Switch)との相性があるんですね…がっかり。

とりあえず CONSOLE ポートではなく裏面の USB HUB に接続したら動作した。
裏面の USB HUB は前面のスイッチを短くタッチした場合は ディスプレイと連動しないので前面のスイッチを長押するか ホットキーで切替える必要がある。
普段からホットキーのみで切替ているので良しとするか

追記

ディスプレイの切替のたびに USB マウスの挿抜が検出されてしまい、 FreeBSD は USB デバイスのエラーが発生してしまった。
なので当面は V450 Nano は使用できない。


Copyright © 2008-2020 Mitzyuki IMAIZUMI. All rights reserved.