FedoraやCentOS 6/7、RHEL 6/7のinitramfsを展開する

FedoraCentOS 6/7、RHEL 6/7のinitramfsでは、先頭にEarly CPIO image(CPUのmicrocodeなどが入っている)がつくようになり、本体の起動RAMディスクイメージ(圧縮cpio image)はその後に来ます。

本体を展開するには、先頭部分を飛ばす必要があるため、dracutが提供している skipcpio というユーティリティを通してから展開します。

mkdir img
cd img
/usr/lib/dracut/skipcpio /boot/initramfs-XXX.img | gunzip -c | cpio -i -d

なお中のファイルリストが見たいだけなら

lsinitrd /boot/initramfs-XXX.img

でOK。ちなみにlsinitrdの中身はskipcpioなどを使ったshell scriptです。

HTTPS接続がCan't verify SSL peersというエラーになるときは

久しぶりにMacでとあるPerlスクリプトを実行したら OAuth::Lite::Consumer が特にエラーも出さずに失敗してしまった。


いろいろ試しているうちに、下記のようなスクリプトを実行すると

% perl -MLWP::UserAgent -e 'print LWP::UserAgent->new()->get("https://www.google.com/")->as_string'

500 Can't verify SSL peers without knowing which Certificate Authorities to trust
Content-Type: text/plain
Client-Date: Wed, 06 May 2015 04:47:19 GMT
Client-Warning: Internal response

Can't verify SSL peers without knowing which Certificate Authorities to trust

This problem can be fixed by either setting the PERL_LWP_SSL_CA_FILE
envirionment variable or by installing the Mozilla::CA module.

To disable verification of SSL peers set the PERL_LWP_SSL_VERIFY_HOSTNAME
envirionment variable to 0.  If you do this you can't be sure that you
communicate with the expected peer.

とか言われた。これは信頼出来るCAを見つけられなくてSSL接続先を検証できなかったため(そのまんま)。


OAuth::Lite::Consumer も接続先がHTTPSだったため、内部的にこのエラーで接続ができずに(タチの悪いことに無言で)失敗していた。


Macの場合、CAはKeychainで管理されているので、PERL_LWP_SSL_CA_FILE を設定するといった方法は使えない。ホスト認証を止める(PERL_LWP_SSL_VERIFY_HOSTNAME=0にする)のはいやなので、上記メッセージの通り

% sudo cpan install Mozilla::CA

Mozilla::CAを導入すれば、Mozillaが提供するCA Bundleを勝手に取得してくれ解決する。

MouseCapeでIBeamカーソルを見やすくする

Mac OS X 10.9くらいから、Iビームのマウスポインタが暗い背景で非常に見にくくなってしまいました。ターミナル等で背景色を黒っぽい色にしていると、テキストを選択しようとした時などにマウスポインタがどこにあるかわからず、非常に不便です。


MouseCapeというマウスポインタをカスタマイズすることができるソフトを使うことで、Iビームの周囲に白いハイライトを足すことで、見易さを改善できました。


作成したcape(カスタマイズされたカーソル集)はGitHubにあります。使い方はcapeファイルをダウンロードしてImportし、取り込まれた「Enhanced IBeam」をダブルクリックして適用するだけです。


https://github.com/NeoCat/enhanced-ibeam


他にもさまざまなcapeが公開されているので、自分好みに置き換えてみるのも楽しいかもしれません。
capeを右クリックしてEditを選び、ポインタの種類を選択してアイコンをFinderにoptionドラッグすると、pngファイルを取り出せます。pngファイルを別のcapeのアイコンにドロップすれば、特定のポインタだけを入れ替えることもできます。

Xcodeでは別の対処が必要

XcodeはOSとは別にカーソルを持っているようで、Mousecapeでは置換されないようです。下記を使えば同様の対処が可能です。

https://github.com/egold/better-xcode-ibeam-cursor

「リツイート直後のツイートを探す」twicliプラグイン

Twitterで、自分のツイートがリツイートされた後、感想などが直後にツイートされることがあります。しかし、特にリプライ先の指定がされているわけでもないので、フォローしていないユーザーがどんな反応をしたかは自分にはわからないことが多いですよね。


そんなとき、@jz5さんの「リツイート直後のツイートを表示するやつ」を使うと、そういった反応を集めてくれ、なかなか便利です。


このサービスとほぼ同様のことをするtwicliプラグイン tweets_after_rt.js をつくってみました。


このプラグインは現在デフォルトで追加されています。反応を知りたいツイートの▼メニューから、「リツイート直後のツイートを探す」を選ぶと、ポップアップで反応を集めてきて表示します。該当するものがない場合は何も起きません(わかりにくい)。

*1


なお、1回あたり最大20回ほどユーザタイムライン取得のAPIを発行するので、利用しすぎるとAPIの利用制限に引っかかります*2

仕組み

対象ツイートに対する最新のリツイート情報20件を取得し、そこに含まれていた全ユーザーのツイートを取得します。その際、IDの範囲指定を対象ツイートの時点〜その10分後までにすることで、そのRTに対する反応だと思われるものをピックアップしています。


なお、取得するツイートを10分後までに限定する方法として、APIのmax_id(取得する上限ID)指定を利用しています。TwitterのツイートID (全63bit) の生成に使われているsnowflakeは、

時刻(ms単位) 41bit サーバID 10bit サーバごとのシーケンス番号 12bit

という構成になっています。→参考 http://www.slideshare.net/moaikids/20130901-snowflake *3 したがって、対象ツイートからだいたい10分後(600,000ms後)までにするためには、

max_id = target_tweet_id + 600000 * (1<<22);

のようにmax_idを計算すれば良いことになります。*4

*1:関係ないけどちゃんとネタだと理解されてるのか心配な反応がある

*2:ユーザタイムライン取得の制限は15分間で150回なので、15分間に少なくとも7回まで使える計算になります(対象ツイートのRTが少なければもっと使えます)。

*3:これによってサーバ間でロックをとったりすることなく重複しないIDが作れるわけですね。

*4:直接シフトするのではでなく1 << 22を掛け算しているのは、JavaScriptでシフト演算は32bit整数に対してしか行えないためです。掛け算なら浮動小数点に変換して計算されます。浮動小数点であるため、必然的に多少の誤差が出ますが、上位41bit分の範囲指定に使うくらいであれば問題ないでしょう。

Google AppEngine (Python) からファイルアップロード

Google AppEngineで外部サイトにHTTPリクエストを発行する際に使う urlfetch は、post関数を持っていません。通常のテキストデータの送信であれば、POSTメソッドの発行自体は method=urlfetch.POST を fetch() の引数に渡すことで可能です。しかし、ファイルアップロードを行いたいなどの用途でmultipart requestを行いたい場合、適切にリクエストをエンコードしてあげる必要があります。


このエンコードのために簡単に利用できる小さなPython Packageとして、poster.encode が利用できます。


AppEngineで使うためには https://pypi.python.org/pypi/poster/ から poster-0.8.1.tar.gz をダウンロードして展開し、中の poster-0.8.1/poster を、アプリケーションのトップ階層にコピーしておく必要があります。


下記は、受信したPOSTリクエストをそのままurl変数で指定されたサイトに再POSTする例です。file というnameのparamにファイルを指定することができます。以下の例では名前決めうちになっていますが、v.filename などが参照できるかをチェックして分岐しても良いでしょう。


なお、あまりに大きいファイル(10MBを超えるなど)はエラーになってしまうようです。

from google.appengine.api import urlfetch
from poster.encode import multipart_encode, MultipartParam
import urllib
import webapp2

class FileUploadTest(webapp2.RequestHandler):
    def post(self):
        url = 'https://example.com/file_upload'
        params = []
        for param in self.request.POST:
            v = self.request.POST[param]
            if param == 'file':
                params.append(MultipartParam(param, filename=v.filename, filetype=v.type, filesize=v.length, fileobj=v.file))
            else:
                params.append(MultipartParam(param, value=v))
        data, headers = multipart_encode(params)
        return urlfetch.fetch(url, payload="".join(data), headers=headers, method=urlfetch.POST)

Fedora21でdebuginfo-install

Linuxカーネル空間で テトリス2048で遊ぶ デバッグをするために必要なkernel-debuginfoですが、Fedora 21でインストールしようと下記のようにdebuginfo-installコマンドを叩くと、

# debuginfo-install kernel
...
Could not find a package for: kernel

と言われて !? となりますが、これはカーネル本体のパッケージ名がkernel-coreに変わったため。

# debuginfo-install kernel-core

とすればOKです。なお、上記の指定では提供されている最新のパッケージに対するdebuginfoが入るので、合わせてカーネルをupdateしておくのをお忘れなく。

iPhoneの充電電流ログ

電流センサが転がっていたので、iPhone 6の充電電流をロギングしてみました。

縦軸は電流(mA)、横軸は時間(分)です。


グラフには現れませんが、電池のみならず充電器側の能力(たぶん電圧、というか出力インピーダンス)もモニタリングしながら流す電流を決めているようで、ACアダプタや電源ケーブルを変えただけでかなり電流値(ひいては充電時間)が変わってしまうようです*1


そんだけ。

*1:内部抵抗が何段階か設定されていてその間で能力を見ながら切り替わる雰囲気