blogPHPでWEB+DBシステムの開発をやっています。3分28秒CakePHPのセキュリティホール(まだの方はご対応を!)から、unserialize()が話題になっています。このセキュリティホールは、外部から送信された値をチェックせずにunserialize()したことが引き金になっており、安全でない値をunserialize()することの危険性が指摘されています。下記エントリでは、コードを交えてunserialize()から__destruct()が実行される過程が解説されています。blog念のための補足なのですが、unserialize()から__destruct()が呼ばれるわけではありません。下記コードは、PHP5.3.3で実行しています。unserialize()から実行される関数unserialize()から実行される関数(メソッド)は以下です。__autoload、spl_autoload*などのオートローダーデシリアライズするインスタンスのクラス定義を探す時に実行される可能性があります。上記オートローダー実行してもデシリアライズするインスタンスのクラス定義が存在しない場合に実行されます。ini_set()等で設定していなければ実行されません。__wakeupデシリアライズしたインスタンスに__wakeupメソッドが定義されていれば実行されます。unserialize()から間接的に実行される関数デシリアライズしたインスタンスの操作によって、結果実行される可能性があるのは以下です。__destruct()デシリアライズしたインスタンスの参照が0になったタイミングで実行されます。通常必ず実行されます。__invoke()などのマジックメソッドデシリアライズしたインスタンスへの操作によって実行される可能性があります。この中で実行されそうなのは__toString()です。unserialize()した値が文字列だと想定して以下のようなコードを書いていると__toString()が実行されます。endunserialize()で__destruct()が実行される?上記でも触れたように__destruct()は、unserialize()で呼ばれるわけではなく、デシリアライズしたインスタンスの参照が0になるタイミングで実行されます。これは通常のクラスインスタンスと同じ挙動です。下記コードを実行してみるとその挙動が確認できます。end"の後ただ以下のようにunserialize()の戻り値を変数に格納しない場合は、デシリアライズしたインスタンスへの参照がありませんので、即時に__destruct()が実行されます。protected/privateな変数もデシリアライズ可能ちなみにunserialize()では、protected/privateなインスタンス変数もデシリアライズ可能です。インスタンス変数をprotected/privateにしたところで、unserialize()で汚染される可能性があることには変わりありません。"private"}でも結果としては実行されるunserialize()が__destruct()を直接実行するわけではないですが、デシリアライズしたインスタンスはどこかで破棄されるので、結果として__destruct()が実行されることには変わりありません。やみくもに「unserialize()が__destruct()を実行する」と考えると問題を見誤る可能性があるのでご注意を。2分9秒すでにご存知の方も多いと思うのですが、CakePHPに深刻なセキュリティホールが見つかりました。SecurityComponentの実装に問題があり、結果、外部から任意のコードを実行させることができるという深刻な内容です。セキュリティホールの概要や攻撃手順については以下のエントリが詳しいですので、ご一読を。焦がすなお、今回の問題はSecurityComponentを利用していない場合は発生しません。SecurityComponentを利用している場合は、以下のいずれかの方法で早急に対策してください。1.3.6にアップグレードする。この脆弱性を受けて修正バージョンが出ています。以下に修正差分があるので、このコードをSecurityComponentに適用してください。必要以上に複雑な実装となっていて内容が掴みづらいという印象です。こと自分に必要なシンプルなものを自作してしまうのもひとつの方法です。(私も社内で開発したものを使っています。)まずは確認をCakePHPを使っている方は、まずはSecurityComponentを利用しているか確認を。使っているかどうかは以下のコマンドでも探せます。"'Security'"まだ実際のサイトでの攻撃例は聞かないですが、今後発生する可能性があります。会社の名刺にTwitterアカウント入れてますか?1×1の名刺をリニューアルしようともろもろ検討中です。Twitterアカウントを入れようかなと思って、他社がどうしているのかを手元の名刺で調べてみました。手持ちの名刺を全部見ると大変なんで、ぱっと取り出せた626枚の会社名刺で見てます。ちなみに取り出した名刺の束には個人名刺も150枚ほど混ざってたので、800枚近くありました。夜中に何をやってんだか。626枚の会社(法人)名刺626枚の会社名刺の中でTwitterアカウントが入っていたのは、9件でした。1%強と思ったより少なかったですね。会社をIT系とそれ以外に分けると、やはり9枚は全てIT系企業でした。IT系企業:359枚(Twitterアカウント:9枚)一般企業:267枚(Twitterアカウント:0枚)9件は全てここ一年以内で頂いた名刺Twitterアカウントが入っていた会社名刺は全てここ一年以内に頂いた名刺ばかりでした。名刺の中には数年前に頂いたものもあるので、もしかしたら今現在の名刺にはTwitterアカウントが入っているかもしれませんね。懐かしい名刺もちらほらなんだか色々な名刺を見ているとその当時のことがよみがえってきて懐かしいですね。IT系では転職されている方も多いので、前職の名刺や前々職や前々前職の名刺が出てきたり:Dまた、同じ会社でも現在とは名刺が変わったりして、時の流れを感じます。1×1の新名刺にTwitterのアカウントを入れると、数年経ってTwitterが廃れると意味ないなーと思いつつ、どうせいずれ名刺は変えるものなので、時代を反映するものとして入れて見ようと思います。新名刺は、乞うご期待。スプレッドシートに表データをコピペする方法です。比べると多少操作性や機能は劣りますが、どこからでも共有できるというのはそれを補って余りあります。そんな便利なスプレッドシートなのですが、コピーしたCSVを表形式でスプレッドシートに貼る機能がありません。CSVをファイルに書き出してインポートすれば良いのですが、今画面上に表示しているCSVをそのままコピペしたい時ってありませんか。以下のようなCSVをコピペしてスプレッドシートに貼り付けると、1行が1つのセルに文字列として格納されてしまいます。RS250RWばっちりいけます。貼り付けはショートカットキーでこれ不思議なのですが、マウスの右クリックから「貼り付け」を選択するとセルに値が入りません。psqlの検索結果をスプレッドシートに貼り付けそもそもなんでこれをやりたかったかというと、psqlで検索した結果をスプレッドシートに貼り付けたかったから。psqlで検索結果をTSVにするのは以下。RS250RWあとはこの結果をコピーして、スプレッドシートに貼り付けるだけ。5分45秒ApacheでX-Sendfileが利用できるmod_xsendfileをPHPと連携して使ってみました。PHPで認証してから、許可したユーザのみにファイルを出力する、という処理を実装する場合、ファイルはdocument_root外に配置しておいて、readfile()やfpassthru()でファイルを出力するという手法を良く使います。この方法でも問題無い場合が多いのですが、容量の大きいファイルを出力する際は思ったようなスピードが出ない時があります。そのような時はmod_xsendfileを使って、ファイル出力の部分をApacheに任せてしまう方法が有効です。0.12を対象としています。インストール環境はRHEL、CentOSを想定しています。mod_xsendfileのインストールmod_xsendfileはApache2/2.2で動作するモジュールです。インストールにあたって、apxsコマンドが必要となるので、もしインストールしていない場合はyum等でインストールします。httpd-devel次にmod_xsendfileをダウンロードします。mod_xsendfileは、mod_xsendfile.cという1ファイルだけなので、それをダウンロードしてインストールします。ブラウザからダウンロードする際は問題無いのですが、wgetでダウンロードしようとすると証明書エラーが発生します。–no-check-certificateオプションを付けるとこのエラーを避けることができます。https://tn123.org/mod_xsendfile/mod_xsendfile.capxsでmod_xsendfileをインストールします。mod_xsendfile.cインストールと共にhttpd.confにLoadModuleが追加されます。/usr/lib/httpd/modules/mod_xsendfile.somod_xsendfileを設定するmod_xsendfileを利用するために設定を行います。httpd.confでXSendFilePathを指定するまず、XSendFilePathで出力を許可するパスを指定します。mod_xsenfileではdocument_root外のファイルを出力することができるので、誤って意図しないファイルの出力を避けるために出力対象のパスを指定する必要があります。出力するファイルは「/path/to/images」以下にあるなら以下のように指定します。/path/to/imagesXSendFilePathは、VirtualHostやDirecortyディレクティブでも指定が可能です。Directoryディレクティブでは実行するPHPファイルのパスを指定できます。CakePHPで指定するなら以下のようになります。(出力ファイルがapp/data以下にあるとします。/path/to/app/dataXSendFileをonにする次にXSendFileをonに設定します。これによりX-Sendfileが有効となります。/etc/httpd/conf*な設定ファイルでも記載できるのですが、アプリ側ファイルの方が都合が良いので、.htaccessに設定を書いておきます。onこれで設定は完了です。あとはPHPから出力するファイルを指定します。XSendFileAllowAboveは削除なおmod_xsendfile0.9ではXSendFileAllowAboveという設定項目があったのですが、これは0.10で削除されたようです。記載しているとエラーになるのでご注意を。PHPから出力するファイルを指定mod_xsendfileと使って、PHPからファイルを出力するにはX-Sendfileヘッダで出力ファイルパスを指定します。下記のようにreadfile()を記載していた箇所(下から2行目)を、X-Sendfileを出力するheader()に書き換えます。これでmod_xsendfileからファイルが出力されます。気になったことX-Sendfileヘッダは外部に出力される?X-Sendfileヘッダには出力ファイルのパスを指定するので、外部に出力されるのはあまり好ましいことではありません。mod_xsendfileの処理が有効になっていれば、このヘッダは除去され外部には出力されないようになっています。0バイトのファイルが出力されるX-Sendfileヘッダで指定したファイルパスが、XSendFilePathで指定したパスにマッチしないと0バイトになるようです。必要であれば、XSendFilePathにファイルパスを追加しましょう。404が発生するX-Sendfileヘッダで指定したファイルが存在しない場合は404になります。PHP以外でも使える?X-Sendfileヘッダをレスポンスヘッダに出力できれば良いので、PHP以外でも利用できるようです。Apacheで使えるX-Sendfile数年前にこんなエントリも書いたりしていたのですが、たしか当時はApacheでの実装は無かったと思います。なんとなくそのままのイメージでいたので、Lighttpd(nginxにも似た機能があったような。X-Accel-Redirectかな。)いいなあと思ってたら、実は結構前からApacheでもできるようになったんですね。この認証ロジックはPHP、出力はmod_xsendfileと、それぞれ得意な分野に分けるのは、Unixっぽくて好きです。2分10秒appengine関連でTogetterから議論が巻き起こってますね。最近すっかりappengineをご無沙汰だった自分としては、一連のtweetやblogを読んだおかげですっかり熱が戻ってきました。議論の発端になったのは以下のTogetter。議論を見ていて感じるところがあったので、ざざっと。さんの主張自体は自分はそれほど違和感無かった。表現がキツイ箇所があったのが琴線に触れてしまったのかな。議論から有用なtweetやblogエントリが生まれてきた。これはとても参考になった。さんが気の毒に感じた。さんがこれまでされてきた活動(Python4PHPer)は素晴らしいと思う(自分もイベントは気になってた)し、これからも続けられると良いのでは。night」な方も多かったけど、自分がイベントに参加した時はアットホームな雰囲気でとても楽しかったです。技術的な内容ゼロの自分のLTも笑顔で聞いてくれたし。別にこわいひとたちでは無い(と思う)。ようは、表現が少し過激だったり、ちょっとした言葉の行き違いが原因かと。自分も感情的になるとついつい余計なことを書いてしまうから気をつけないと。飲み屋で同じ話すれば「おまえなにいうてんねん」というノリで軽い議論になるだけで、こんなややこしい話にはならなかったでしょうね。オンラインのコミュニケーションは難しい。どちらかがどちらかのイベントに参加して懇親会とかで話せば、わだかりも解けると思うんだけどなー。さんが辛い思いをされているのは、とても悲しいことなので、気にせずに頑張って下さい。appengineを追いかけてる時に作ろうと思って放置していたものとかあるから、またやりだそうかな。