2019年6月26日水曜日

iPhone XでGoogle Fiをアクティベートしてみた

アメリカ出張中にBestBuyでGoogle Fi SIMを普通に買うことができたので、買って契約してみました。
Google Fi は日本ではほとんど知られていないと思いますが、 Google が米国で提供する携帯電話サービスです。だいたいのサービスの特徴として
  • 20ドルで1電話回線(通話、Text、データ)を利用可能。10USD/1GB利用、ただし80USD/月で課金打ち止め
  • 15GBぐらいまでは使える
  • 世界170カ国ぐらいで、上記価格でLTEデータ通信が使えるので海外行きには便利
  • 日本に持ってきているとUSの番号にかかってきた電話がローミングで受けられる?
といった感じになっています。詳しくは https://fi.google.com を見てみてください。


今まではどうしていたか

これまでは個人的にアメリカと連絡をとったりするときのために SkypeIn 番号をとっていました。はじめての海外がユタだったことから愛着もあり 1-801-****-**** の番号を押さえていました。

また、 iPad Pro の Apple SIM で 150日間で10GB程度使える $10 のプランこれまで3-4回契約してきました。だいたいの場合はこれで困らないのですが、以下のパターンでちょっと手間だなーというのがありました。
  • カーナビゲーションに iPhone を使うときに毎回 iPad Pro 経由でテザリングを有効にしないといけないのが地味に面倒
  • Apple SIM から T-Mobile 契約をアクティベートできずにハマったことがある。LTEがある前提でいったら宿泊先の情報をUS到着後に確認せねばならず、LTEなしで別のホテルで泣きついてWiFiを借りるという苦労を去年テキサス州でしました。SIMアクティベートに苦労した詳細は IIJmio SIM カードが入った iPad Pro (2017) 10.5インチモデルで Apple SIM を使おうとして苦労した話 にまとめてあります。
  • 結局、毎回 iPhone X 用に SIM が欲しいという状態になり、そのたびに AT&T や Verizon に駆け込み

Google Fi  SIM を BestBuy で普通に発見

ちょっと目立たないところではありましたが、  Google Fi の SIM が BestBuy の携帯電話売り場に普通に売られて居ることに気づいて、とりあえず二枚買ってみました。一枚おおよそ10ドルしますが、10ドル分のデポジットがあるので実質タダになります(申し込みをした場合は無料で宅配で送ってもらえるものを店頭で値付けしているが、その分はデポジットになるという仕組みです)。もしかしたらSIMを使わずに放置したら有効期限切れになってしまうかもしれませんが、まあ男の子のおもちゃ的要素も強いので、そのときは、まあ、それでいいでしょう(その場でプリペイドカードを activate している感じなどはないので、たぶん大丈夫だとは思います)

なお BestBuy での店頭売りがはじまったのは 2019年3月頃からのようです。


アクティベートに必要なもの

翌日、早速契約してみることにします。事前に調べていたこともあり、だいたい必要なのはこんな感じだということがわかっていました。
  • SIM カードを手元に準備する必要がある
  • Google US のアカウントでないとサインアップできないらしい?
  • US 内の住所が必要
  • 課金用クレジットカードも US みたいな話をみかける
SIMカードは Google Fi の Web サイトから郵送を申し込むと1週間以上かかるそうでホテル宿泊者にはつらいですが、 BestBuy で小売りがはじまったことで一気にハードルが下がりました。

Google のアメリカのアカウントは作ればいいだけです。  Google Fi 申し込み時だけ在住国をアメリカに変更すればいいという話も見かけるのですが、何か面倒がおきて普段使いの Google アカウントに影響が出る場合を嫌って、今回は新しく Google US アカウントを独立したかたちで取り直しました。

US 内の住所は持っていませんが、「滞在先ホテルの住所を使う(嘘はついていない)」「勤務先会社のブランチオフィスの住所を使う」「知り合いの家の住所を借りる」「コワーキングオフィスの住所を借りる」といった手があるかと思います。残念ながらいまは雇用関係にある会社で直接米国内にブランチをもっていないので、関連会社の住所とか借りちゃおうかといろいろ悪巧みの考えたのですが、最終的にはホテル住所を入れ、アパート名として「The North Side Inn Guest」という要領で登録して、無事に開通までこぎ着けました。すべて正直で、嘘は一切ついていません。

最後の課金用クレジットカードでUS発行のものを用意する方法は思いつかなかったのですが、Webサイトで前例を調べていたら、US国内で買えるVISAなどのプリペイドカードに現金をチャージするという方法があるそうです。たとえば50ドルをスーパーマーケットなどで支払うとVISAのクレジットカードとしてプリペイド分だけ使えるカードを発行してもらえます。
この手を使おうかなと思ったのですが、カードに残高を追加する refill が日本国内からできないであろうことを考え、とりあえず自分が持っているカードでダメ元で試すことにします。


Google USアカウントを作成する

まずは US 内で Google アカウントを作成します。 Google アカウントの作成自体は特に普通のことですし細かくは書きません。


Google Fi に加入する

米国内のホテルの WiFi を使って https://fi.google.com/signup から申し込みを進めていきます。今回は端末を購入せずに Apple Store で購入済みの iPhone X と手元に準備した SIM カードを使用します。その条件で画面を遷移していくと 1回線20USD+データ10USD/1GB/mo.のプランが表示されます。

サービスアドレス(サービスを受けるメインの住所、おそらく緊急車両などを呼ぶ場合のベースエリアになる)の入力があったので、宿泊中のホテルの住所などをベースで入力します。(スタバWiFiなどで自宅住所のZIPコードをきかれたりしますが、とりあえずホテルのものを入れておくと通過できたりしますね)

課金先は、日本で発行された Delta American Express Gold を使っているので、こちらでの支払いという形にしたらあっさりと契約できました。


Google Fi アプリを入手する

Google Fi は日本でサービスされていないので、 Apple のアカウントが日本在住になっていると Google Fi アプリが iPhone X 上の App Store で見つけられません。このため、一時的に普段使いの Apple アカウントを US に変更することにしました。

Apple サイトにログインし個人情報を変更します。先と同じ要領でホテル住所でアカウントを作成しました。ここで請求先クレジットカードを登録するように求められるのですが、単に None (なし)のみを選択して先に進みます。ここでは、 Google が許してくれた日本のクレジットカードは通りませんでした。また、一度でもカード番号などを入れ始めてしまうと None を選択してもカード番号が不正といったエラーメッセージが出て咲きに進めなくなってしまいました。

Apple アカウントが US ベースになってから iPhone X の App Store が US の App Store ベースになると、 Google Fi アプリが検索で出てくるようになりますので、インストールします。

ここまでが終わったら、 Apple アカウントの設定をまた日本に戻しておきます。


Google Fi SIM をアカウントに追加する

続いて SIM を使えるようにしていきます。購入済みの SIM をスロットに差し込み、先ほど  iPhone X にダウンロードした Google Fi アプリで SIM をアクティベーションします。SIMパッケージに付属のワンタイムキー入力、またAPN設定などを済ませると、端末を再起動し次第サービスが利用できるようになりますという旨のメッセージが表示されます。


おつかれさまでした

上記で、割とあっけなく Google Fi の SIM を開通させることができました。


どう使うつもり?

海外出張に出たときに、米国のほか Google Fi のサービスエリアであれば、空港に降り立った瞬間から音声、LTEデータが使える回線を手元に持つことができるのは十分なメリットあると思っています。

現地のAT&Tマンスリープランと比べて同じぐらいかちょっと高いぐらいの利用料ですが、データ通信が少なければ割安になりそうですし、データ通信は基本的に iPad Pro で利用できるプランでテザリングすれば Google Fi での通信量を抑えられ、Fi に課金されないので、USの電話番号とLTEデータ通信が iPhone X から利用できるというメリットが発生します。

Google Fi のLTEデータが高いと思うのなら、SIMを入手するまでの予備回線として利用するのもありかもしれません(まあ、それならAT&TとかのSIMカードを事前購入してアクティベートだけしろよという話はありそうですが)。

また米国内で取得したSIMを日本にもってきても、サービス的にはユーザがSIMを持って海外旅行した状態になります。米国電話番号に対する音声通話もローミングされる認識ですし、ある意味 SkypeIn みたいなものを SIM として持った状態になります。しかも多分 Text はできる。

また、日本で利用する場合、日本のMVNOと比べれば割高ではありますが、最大月80ドルで15GB以上通信できる非常用SIMとしても利用できます。

月20ドルを1年間寝かせても年間240ドルですし、激安とは思わないものの、SkypeIn番号を取得するのだけに月13ドルかかっているぐらいなら Google Fi を契約し続けても正直月7ドルぐらいしかランニングコストは変わりません。このため、 Google Fi はアクティブな状態で Skype In は解約することにしました。


eSIM じゃダメなの?

私が持っている iPhone X が eSIM 対応だったら eSIM で考えたかもしれません。ただ普通の SIM として持っていると、帰国後に自宅で余っているLTE端末などにさして電話を受けるといったことも可能なので、物理 SIM がいいかなーという思いはあります。


おわりに

正直身構えた割にあっけなく開通した Google Fi ですが、しばらく使って(?)みようと思います。飽きたりコスパ悪いなと思ったら解約するかもしれませんが。

2018年12月4日火曜日

AMD GPUによるディープラーニング環境の構築

こんにちわ。さくらインターネット 高火力コンピューティングの雑用担当 @hasegaw です。このエントリはさくらインターネット Advent Calendar 2018 4日目のエントリです。なお、前日のエントリは UIT#5 で登壇してきました + 資料への補足 でした。


新しい Radeon GPU が登場

1ヶ月ほど前になりますが、2018年11月6日に、AMDが新しいGPU 「Radeon Instict MI60」を発表しました。4096のストリームプロセッサー、1TB/sの高帯域幅な32GB HBM2メモリを搭載し、PCIe 4.0 16レーンに対応したGPUです。また、ストリームプロセッサーが 3840 に変更された Radeon Instict MI50 というモデルを紹介されています。

AMDが7nm提供開始、Vega「Radeon Instinct MI60」と最大64コアのRomeこと新「EPYC」を発表
http://ascii.jp/elem/000/001/768/1768981/


ディープラーニングと Radeon GPU

Radeon GPUといえば、2018年はマイニングで話題になったりもしましたが、OpenCLによる計算用途にも利用できます。また、最近では ROCm と呼ばれるソフトウェア群によってディープラーニング目的でも使えるようになりました。

本当に動くの?

Radeon でディープラーニングってきちんと動くの?ちょっと試してみないと判らないな……と思われたりするでしょうか?

私は、高火力コンピューティングの仕事をしつつ、サイドプロジェクトで GPU を使ったりもするので、そのときはデータセンターをおいたマシンを使ったりもするのですが、かといって高価な Tesla を常に浪費するのも心が痛むので、最近は 10分の1のコストで済む Radeon で事足りる作業なら Radeon GPU を使ってみています。にわか機械学習マンとしては、現状 Radeon GPU で困ったことはありません。

最近は TensorFlow もアップストリームに追従するかたちで ROCm 対応版が作られており、動かしてみても、だいたいの場合は問題なく動くようです。また、 Radeon Instict シリーズに一気にいかなくとも、秋葉原で手に入る Radeon シリーズでとりあえずの味見をすることも可能です。

「本当に自分が持っているワークロードが動くの?」と気になる方は、 Pegara 社の GPU EATER をお試しになられてはいかがでしょうか。

GPU EATER
https://www.gpueater.com/

なんと1時間あたり1ドル未満で、RadeonシリーズのGPUサーバーを試せます。また、ログインは事前に用意したSSH公開鍵に対応する秘密鍵でSSHするだけ。利用開始も簡単で、最初から ROCm フレームワークや TensorFlow サンプルなども入っています。

root@C-2b457c0e-0884-4f80-94fc-4bbeec7ecb4c-685:~/deep_learning_yolo_v3# python3 yolo.py  image.jpg
Using TensorFlow backend.
2018-10-10 04:56:03.761749: I tensorflow/core/common_runtime/gpu/gpu_device.cc:1519] Found device 0 with properties:
name: Device 687f
AMDGPU ISA: gfx900
memoryClockRate (GHz) 1.622
pciBusID 0000:03:00.0
Total memory: 7.98GiB
Free memory: 7.73GiB
2018-10-10 04:56:03.761786: I tensorflow/core/common_runtime/gpu/gpu_device.cc:1630] Adding visible gpu devices: 0
2018-10-10 04:56:03.761820: I tensorflow/core/common_runtime/gpu/gpu_device.cc:1039] Device interconnect StreamExecutor with strength 1 edge matrix:
2018-10-10 04:56:03.761829: I tensorflow/core/common_runtime/gpu/gpu_device.cc:1045]      0
2018-10-10 04:56:03.761848: I tensorflow/core/common_runtime/gpu/gpu_device.cc:1058] 0:   N
2018-10-10 04:56:03.761907: I tensorflow/core/common_runtime/gpu/gpu_device.cc:1178] Created TensorFlow device (/job:localhost/replica:0/task:0/device:GPU:0 with 7524 MB memory) -> physical GPU (device: 0, name: Device 687f, pci bus id: 0000:03:00.0)
model_data/yolo.h5 model, anchors, and classes loaded.
(416, 416, 3)
Found 5 boxes for img
person 0.94 (143, 281) (216, 495)
person 0.97 (112, 17) (207, 331)
person 0.99 (239, 297) (317, 514)
person 0.99 (253, 98) (319, 364)
person 1.00 (38, 165) (102, 436)
20.274007220985368
Output => image.jpg.out.jpg


ROCm 環境のインストールって難しくないの? → 思ったより簡単でした

手元に実際の Radeon GPU を用意し、環境を構築するにはどれぐらいの苦労があるでしょうか?実際  Ubuntu 16.04 ベースで試してみたときは、思ったほど難しくはありませんでした。 https://github.com/hasegaw/rocm-tensorflow-ansible/ に、私が環境作成に使用している Ansible role から抜粋したものをおいておきますので、必要に応じて加工して利用してください。何をしているかというと

ROCM 環境の構築)

  • カーネルの更新
  • apt に ROCm レポジトリを追加
  • ROCm 関連パッケージをインストール。カーネルモジュールは DKMS で設定されます
  • /etc/profile.d/ に設定ファイルを展開
  • 必要に応じてユーザ(既存/今後の作成時のデフォルト)のグループ設定を変更
TensorFlow のインストール)
  • virtualenv をインストール
  • virtualenv 上に tensorflow-rocm をインストール
といった感じです。 ROCm は repo.radeon.com からのパッケージを拾えば動きますし、 TensorFlow も AMD 社がポートしたバージョンを PyPI に適宜パブリッシュしてくれているので、 pip install するだけの時代が来ているのです。


利用感はどう?

どちらかといえば、パフォーマンスの面よりも、秋葉原などの店頭でカジュアルに手に入る Radeon Vega 64 は 8GB メモリモデルぐらいしか市場で見かけておらず、 Radeon Vega Frontier Edition (12GB) がほぼ市場から消えている状況で利用できるメモリ量が少ない点が、がつがつワークロードを回そうと思うと、ちょっと気になるかもしれません。

ワークロードによるので一概に言えないのですが、私が試した範囲では Radeon Vega 64 で NVIDIA TITAN X の8割から同等程度のパフォーマンスが得られていました。 GDDR5 搭載の NVIDIA GPU が HBM 搭載の Radeon Vega 64 に対して優位なのは NVIDIA すごいなーと思いますし、 Radeon 上でのチューニングはこれからなのかな、という感じがします。

現状の tensorflow-rocm は、CUDAバージョンのカーネルをコンバートして使っているようなので、このあたりの最適化が進めばさらに性能が伸びる余地もありそうです。例えば  GitHub 上のアクティビティを眺めていると、和算+活性の "Fusion" カーネルの実装なども最近行われていました。どんどんアップデートされているので、今後が楽しみです。


まとめ

AMD Radeon シリーズでのディープラーニングもそろそろ実用段階に入ってきたのではないか、という感じがしています。

ただ、ディープラーニング用途で Radeon 系 GPU をすでに持っている方はほとんどいないでしょう。そんな時でも、ご紹介したとおり、 Pegara 社が非常にお安い価格で Radeon GPU を利用できる GPU EATER を提供されていますので、興味が湧いたら、こちらのサービスを試してみてはいかがでしょうか。

2018年12月2日日曜日

ジオラインとスポーツタイツで出張を乗り切る

ここ1〜2年で出張が多くなった(たぶんいままでの人生でいちばん移動してる)のだけども、移動にあたってはスノーボード等で色々試してきたノウハウを適用している。基本はモンベル ジオラインとスポーツタイツだ。今回はどうして私がジオラインとスポーツタイツの組み合わせを勧めるのかを紹介してみたい。


ジオラインは日常生活でも便利な下着

ジオラインは綿のシャツよりも軽く、かさばらず、速乾性をもった素材で作られているアンダーウェアだ。汗をかいても、その汗を上のレイヤの方にさくっと移してくれる。結果として体から出た汗を肌から離してくれるので、汗冷めをしない。

ジオラインシリーズはこちら
https://webshop.montbell.jp/goods/list.php?category=71000

私が知っている範囲でジオラインの下着は4種類ある。

・クールメッシュタイプ
・薄手(L.W. = Light Weight
・中厚手(M.W. = Middle Weight)
・厚手(EXPedition)

仕事や町中での日常生活、もしくは出張で使うとしたら、クールメッシュタイプもしくは薄手タイプになる。クールメッシュタイプというのは、ユニクロでいうエアリズムラインのような、夏場に肌がさらさらに感じるようなタイプ。薄手をはじめとする他のタイプは、繊維のなかに空気を保持して、そこに体温で温まった空気が留まるため、暖かく感じる。なお、個人的には、いちばん汎用性が高いのはクールメッシュタイプかなと思っている。クールメッシュといっても不必要に冷感があるようなものではないので、冬でも「肌をドライに保ってくれる下着」として活躍する。

ジオラインをインナーとして利用していてメリットがあるのは、寒暖差があるところを行き来したときに汗をかいたりしてもへっちゃらなことだ。例えば、冬場だと、仕事を終えてからコートを着て駅まで歩き、電車にのったら電車内で暖房がかかっていて汗をかき、コートの下で汗びっしょりになった下着に凍えたり、とか、そんな経験はないだろうか。

ジオラインだとこのようなタイミングで汗をかいても上のレイヤに汗を発散してくれるので寒いと感じる事がほとんどない。ジオラインを使うようになる前に使っていたユニクロ ヒートテックなどを久々に着ると、ここでとても差があって、「うわ!今すぐ家にかえって着替えたい!」と思う程度には快適さに違いがある。

薄手のジオラインは基本的に暖かく感じるモデルなので、これは夏に来ていると本人はきにしていないくてもそれなりに汗をかいて服が濡れて、周りが「このひと汗っかき!」と驚かれたりするので、できれば夏はクールメッシュタイプを使うほうがいい。冬でも薄手が暑すぎるようならクールメッシュタイプでいいと思う。

個人差はあるだろうが、町中での仕事や電車・飛行機でなどの交通機関での移動なら中厚手・厚手タイプは不要だ。中厚手タイプは、私の場合はスノーボードで山にはいるとき(氷点下以下)にジャケットやフリースの下の肌着として着るレベル、厚手は冬山を縦走するような人向けのラインなので、少なくとも、どちらも町中で使うようなものではないだろう。


ジオラインを旅や出張で使うメリット

ジオラインを旅や出張で使うと大きなメリットがある。かさばらない、軽い、手洗いですぐ乾く、一枚で幅広い気温差に対応できる、の4点だ。

ジオラインは実際も手にしてみると判るけども、下手な綿の下着よりも薄い生地なので、替えを持っていっても、かさばらない。また、軽いので、下手な綿の下着を持っていくよりも荷物重量をセーブできるように感じる。

手洗いですぐ乾くのは、旅先や出張先でとても便利だ。ホテルに戻ってから洗面台やバスタブのなかで水/お湯洗いし、十分にしぼり、バスタオルなどで残りの水分を吸い取って干しておけば、最短30分後には着られる状態になるし、朝までには十分乾く。完璧ではなくても、着ると自分の体温で下着が温まって水分がとぶので、客室で着替えや歯磨きなどの準備をしているうちに落ち着く。

これが綿の下着だったりすると、夜に手洗いした下着が朝に着られる状態になっているなんてことは、まずあり得ない。アメリカなどではホテル客室のエアコン設定温度が18度前後みたいなことも多い(外出時に設定温度をあげておくことは可能だけどもハウスキーピングスタッフがウェッってなるだろう)。出先のホテルでなかなか綿の下着なんて乾かない、でもジオラインなら朝には着られる状態になるのだ。

ここまで書くと「下着の予備もっていかなくていいの?」という感じになるけど、実際のところジオラインだと毎日手洗い対応で1枚で数日間の日程を回せてしまったりする。でも実際には夕食などでホテル客室への戻りが遅くなったりとか、時差ボケなどで疲れていて「明日のために下着を洗う」なんて元気がないこともあるので、荷物のなかにはスペアのジオラインが1〜2着準備してあったりするが、3枚とも使うようなことはまず無い。

ジオラインで下着量が減れば荷物が減り、他の用意を増やせる

シャツタイプの下着のほか、パンツも利用している。こちらも基本的に同じ使い方ができて、綿のパンツだったら手洗いで乾かすのがほぼ無理に等しくても、ジオラインだったら客室のなかでカジュアルに手洗いして乾かすことができる。出発日に着ているものを含めて3着あれば、ほぼ無限に回せるので、長期間の出張でも着替えを増やしたり、ランドリーサービスで1品に3ドルなど取られる必要もない。

ジオラインのおかげでスーツケース内の下着量を減らせたので(これも下着だが)靴下を日数分+α分いれるようにしている。靴下は薄くなるとは着心地が悪くなるし、厚みがあるということは手洗い&客室内で乾かすのが難しいからだ(手洗いできて客室で1日以内に乾く快適な靴下があれば紹介してほしい、本当に)。

古い靴下が溜まっている場合には、古くなった靴下を履いては捨てる、履いては捨てる、みたいなことをして帰って来るときには身軽になっていたりもする。靴下だってホテルで洗濯を頼むと数ドル取られたりするので、こういう方法をとっている。


気温差を吸収できるスポーツ用タイツは移動にも便利

ワコールが販売するスポーツ用タイツ CW-X を使い始めたのは、スノーボード仲間の間で流行っていたからだ。

https://www.cw-x.jp/men/

これが移動中でもけっこう便利だったりする。 CW-X を出張などの遠出で使うメリットは「寒くても冷えない」「暑くても汗でベトベトしない」「あまりムレない」「まだ手で洗える」の4点だ。

CW-X のタイツは、アマチュアからプロのランナーまで、スキーやスノーボード、その他にも様々なスポーツをする人が持っているスポーツウェアのひとつだと思う。この CW-X タイツ、冬場にランニングしていても寒く感じない。自分がかいた汗を外側に発散して肌をドライに保ってくれる上、CW-Xが空気の層を作ってくれるので、寒さが和らぐ。

たとえば羽田を離陸してサンフランシスコまで10時間近く飛行機のなかでエコノミー席に座っていても、CW-Xをはいているとブランケットがかかっていなくても大丈夫だったりする。

また、真夏のむしむしした台湾で町中の歩けば汗をかき、それがズボンにつけばべとべとした感覚になるが、そういう感覚が和らぐのだ。ジーパンはホテルの客室で手洗いしても乾かしようがないが、 CW-X なら洗った後にバスタオルで吸い取ったり、肌につけていれば、水分は自然に飛んでいく。ベタベタするズボンを洗うより全然現実的なのだ。

ただし夏にCW-Xをズボンのなかに履くのはある程度ムレたりもするので、それが気になりそうな気候だった場合には、移動日以外はモンベルのジオライン クールメッシュタイプのタイツを使っていたりもする。

なお CW-X も着圧効果はあるとはいえ SKINS などだと血の巡りをよくしてエコノミー症候群を防ぐような効果が訴求されている?みたいなので、新たに買うのなら、そういった着圧タイプを選んだほうがいいのかもしれない。


ジオライン + スポーツタイツで夏・冬気候を行き来もして大丈夫

2017年の夏、オーストラリアのメルボルンまで出張で行ったときには、実際に ジオライン + CW-X を使った。

出張予算を削減する必要があったので、航空会社はタイ航空。タイ経由でオーストラリアに行くということは、真夏の日本から赤道の下みたいなタイを経由して、真冬のオーストラリアに行く、ということだ。しかも、帰路はオーストラリアを夜11時発、タイに朝6時頃に到着して、深夜の日本行きフライトに乗る、みたいな旅程で、つまりはオーストラリア市内とタイ市内でまる2日間、だらだら過ごすことになった。

この出張では、実際に神奈川の自宅を出発して飛行機にのりタイ経由でオーストラリアに到着、出張期間は現地の大学に行き、オーストラリア出発日はオーストラリア市内をふらふらして、翌日はタイ市内をふらふらしたけども、この間、実際にジオラインの薄手 + CW-X の組み合わせで乗り切ってしまった(さすがにタイとオーストラリアで、その上のレイヤリングは変えている。ズボンは替えなかった)。タイー羽田便は熟睡、目の前にすわっていたフライトアテンダントが「よくお休みになられていましたね」と声をかけてくるほどだった。


まとめ: ジオライン + スポーツタイツは長距離移動で活躍する

まとめると、ジオラインとスポーツタイツは「体を冷やさない」「必要以上に暑くならない」「汗が外に抜けていき肌をドライを保ってくれる」ので、気候変化が大きいような日程を組んだり、その途中で飛行機など体を冷やしがちな移動手段を使っても凍えるような思いを防ぐ下着として利用できる。

普段とは違う気候の場所でも、過ごしやすくければ見知らぬ地でのストレスも軽減されたりするので、出張先や移動中体が冷えたり暑かったり、持っていく下着の枚数を何枚にするか悩んでしまったりする時には、ジオラインやスポーツタイツを試してみてほしい。

2018年11月12日月曜日

IIJmio SIM カードが入った iPad Pro (2017) 10.5インチモデルで Apple SIM を使おうとして苦労した話

出張先(米国内)で内蔵 Apple SIM を使用して T-Mobile に接続しようとしたら、できなくて困った。



本来ならここで「データ通信プランを選択」というグループに、トレイに入っている SIM カードから NTT DoCoMo 、 Apple SIM で契約済みの T-Mobile 、そしてその他のキャリアへの新規加入が可能なメニュー選択肢が出るはず。

まずは IIJmio での接続に必要なAPNプロファイルを削除してみる。これが入っているとどちらにせよ T-Mobile で通信できないだろう。削除しても、 T-Mobile や Apple SIM の選択肢は出てこなかった。

次に iOS をリスタートしてみる。残念ながらこれでも改善しなかった。

続いて、 General > Reset > Reset Network Settings でネットワーク系の設定をリセットしてみる。これでも Apple SIM が見えない。困った。

Apple Support アプリから現地のサポートにチャットで相談してみたら、下記のとおりアドバイスをもらった。

・SIMスロットに入っている SIM カードを取り外してみる。
・それでだめならバックアップをとって Factory Reset (ひえー)

SIM スロットには IIJmio (DoCoMo)の SIM が刺さりっぱなし。そういえば前回渡米したときは IIJmio じゃなくて、さくらインターネットのセキュアモバイルコネクトを挿していたはずなので、前回問題なかった時とは状況が違うのは確か。

SIM スロットをイジェクトするピンを持ち合わせていなくて困ったのだが、宿泊先の施設に知っている日本人が泊まっていて(笑)ピンを借りることができた。で、 IIJmio の SIM カードを取り外してみると。。。



おうー。まじかよ! T-Mobile きましたわー。
ということで一件落着。

・IIJmio (DoCoMo) SIM が挿さった状態だと Apple SIM が見えない?状態になる
・この状態だと「データ通信プラン」(英語表記では Celluar Plans)が出てこない。
・SIM カードを抜くと Apple SIM が見える、ことが実際におきた
・出張セットのなかには SIM カード取り出し用のピンを忘れずに入れておくようにしましょう

2017年12月23日土曜日

【第1回 Cpaw AI competition】乱入レポート

この記事は、さくらインターネット Advent Calendar 2017 23日目の記事です。
22日目の記事: 日本初の競技機械学習大会!【第1回 Cpaw AI competition】開催レポート
24日目の記事: (追記予定)

こんにちわ。 hasegaw こと、さくらインターネット 高火力コンピューティングの長谷川です。

今回は、22日の記事にて紹介された第1回Cpaw AI Conpetitionについて、続きってわけでもないのですが、続編をお届けします。同コンペティションを開催したCpawの伊東さんは高火力コンピューティングにチームでアルバイトしてくれていまして、ある日のこと。

「AIコンペティションを開催したくて、場所を探しています」
「え?ウチ使えるよ」

ということで、さくらインターネットの西新宿セミナールームで開催することになりました。当日は台風が接近していたこともあり、参加者が少なくなってしまうのではないかと心配したのですが、悪天候のなか歩留まり6割というのは最近の機械学習系のイベントとしては良い意味で裏切られた気持ちでした。



先の記事のとおり、 Cpaw AI Competition では、さくらのクラウド 12コア・96GBメモリのインスタンス(Ubuntu 16.04)を用いて、与えられたデータセットに対する分類器を生成、分類結果を Web サイトから提出します。提出したスコアはそのまま 1% == 1ポイントとして加算されます。つまり65.2% の分類器をつくれば 65 ポイント獲得できるわけですね。

競技時間は 13:30-18:00 のおよそ 4.5 時間。さくらインターネットの社員(わたし含めて2名)は会場運営支援で現地にいたのですが、 4 時間ボケっとしているのは、ちょっと暇です。と、いうわけで。

「伊東くん、私にも問題解かせてよ」

とお願いして、他の参加者と同じように問題を解いてみることにしました。下記は、実際に問題を解いた手順を再現したものですが、当時書いたコードは既に失ってしまったので、書き直した「再現コード」で解説します。


■ 芸能人ブログ記事の分類問題→絶望

最初に手を出したのは芸能人ブログの分類問題(entertainer_blog)です。データセットは Cpaw オリジナルのもので(本稿執筆のために Cpaw から提供を受けていますが)、 Cpaw の皆さんがあらかじめスクレイプ、1記事1テキストファイルに変換されたものです。ブログエントリの教師データを用いて分類器を訓練し、クラスラベルが与えられていないブログエントリを分類することが目標です。

entertainer_blog/train/
entertainer_blog/train/mamoru_miyano
entertainer_blog/train/mamoru_miyano/10.txt
entertainer_blog/train/mamoru_miyano/1000.txt
entertainer_blog/train/mamoru_miyano/1005.txt
entertainer_blog/train/mamoru_miyano/1021.txt
entertainer_blog/train/sano_hinako
entertainer_blog/train/sano_hinako/1004.txt
entertainer_blog/train/sano_hinako/1008.txt
entertainer_blog/train/sano_hinako/1012.txt
entertainer_blog/train/sano_hinako/1014.txt
entertainer_blog/train/shinozaki_ai
entertainer_blog/train/shinozaki_ai/1003.txt
entertainer_blog/train/shinozaki_ai/1006.txt
entertainer_blog/train/shinozaki_ai/1010.txt
entertainer_blog/train/shinozaki_ai/1018.txt
entertainer_blog/train/shinozaki_ai/102.txt
....

データファイルの内容の例


訓練用データセットは下記のとおりの構成でした。

訓練用データ(ラベルあり)
461 shinozaki_ai
509 uesaka_sumire
397 mamoru_miyano
210 sano_hinako
合計 1577

テスト用データ(ラベルなし;スコア獲得用)
合計 1972

データセットを数ファイル覗いてみると、これらの芸能人が誰なのか正直全然わからないですけども、クラスによっては特定の締め方があったり、顔文字の傾向があったり、ということがわかりました。今回は、このデータセットを手軽に処理する目的で Jubatus を用いることにしました。 Jubatus の場合 ngram を用いた特徴量への変換などが標準で備わっていますので、今回のようなデータセットなら、簡単に「とりあえず」食わせられるからです。

wget http://download.jubat.us/apt/ubuntu/xenial/binary/pool/jubatus_1.0.6-1_amd64.deb
apt install ./jubatus_1.0.6-1_amd64.deb
pip3 install --user jubatus


今回は分類問題なので Jubatus のなかでも jubaclassifier を使用します。以下のようなファイルを作成します。 n=6 にしましたが、ここには強い理由はありません(とりあえずノリで決めました)。既存のサンプルを参考に、設定ファイルに指定して jubaclassifier を起動します。

jubaclassifier はポート 9199 で待ち受けており、 Python で記述する学習&予測プログラムから利用します。


jubaclassifier --configpath jubaclassifier.json


そして訓練用データセットがクラスラベルごとにディレクトリで分けられていること、データセットサイズに対してインスタンスのメモリ容量が十分なことから、下記関数でデータセットを読み込むことにしました。

次のコードが Jubatus を用いてデータセットを分類し、Cpaw AI Competition での提出用CSVフォーマットで stdout に出力するソースコードです。

ここまで準備ができたら、実際にデータセットをロードして、 jubaclassifier を用いてオンライン学習し、テストデータを分類します。ここで、標準出力に表示される結果の例を示します。

0.txt,uesaka_sumire
1.txt,shinozaki_ai
2.txt,uesaka_sumire
3.txt,uesaka_sumire
4.txt,mamoru_miyano
5.txt,mamoru_miyano
6.txt,shinozaki_ai
7.txt,shinozaki_ai
8.txt,uesaka_sumire
9.txt,shinozaki_ai

このデータをコンペティションの採点システムに提出すると、得られていた精度はなんと 30% 以下!!4クラス分類だと完全ランダムでも25%前後になるはずですから、いっそのこと全部 shinozaki_ai ラベルで提出した場合のスコアと大差がない。まったく駄目!!

正直、高火力コンピューティングをお客様に紹介して回ったり、プレゼンして回ったりする立場の私がコレなのは本当に恥ずかしてお客様などに顔向けできないなぁ、と思い、動揺し、死にたくなりました。いっそのこと Cpaw に貸してあげた採点サーバーに root で乗り込んでいって DROP DATABASE クエリを叩き込んでしまいたいという気持ちになりましたが、個人的な感情でそんなことをするわけにもいきません。実は、当日は ngram の n=2 で精度が得られなかったため順番に増やしていって 6 まで上げたのですが、これだけで、精度はあがりません。

一旦あきらめて、とりあえず他のデータセットに取り組むことにします。

■ 泣きそうになりながら、マルウェアURLの分類問題

次に取り組んだのは、マルウェアURLの分類問題です。下記URLで取得できる、URLデータセットが先と同じように1サンプル1テキストファイルとして用意されており、オリジナルデータからラベルが取り除かれたテストデータが正常なURLか、グレイゾーンなURLかを判断することが目標です。

Malware URL
http://malwareurls.joxeankoret.com/

データセットのディレクトリ/ファイル構造
train/normal/
train/normal//1007.txt
train/normal//101.txt
train/normal//1011.txt
train/normal//1013.txt
train/malicious/
train/malicious//0.txt
train/malicious//1.txt
train/malicious//10.txt
train/malicious//100.txt
...

あるデータファイルの中身の例


テキストファイルの中が芸能人のブログ記事からURLにかわり、ラベルが変わっただけで、基本的にデータフォーマットは一緒です。

というわけで、遠慮なく先程の dataset.py と classifier.py に突っ込んでみます。 URL は基本的にアルファベットや数字の集合で、N の値はそこそこ大きい必要があるでしょう。なので N はとりあえず、引き続き 6 ぐらいにしておきます。

先程起動した jubaclassifier は芸能人ブログの学習データを持っているので、ここでいったん同プロセスを再起動しておきます(もっといい方法があるのでしょうか?使い慣れているわけではないので、よくわかっていません)。malware_urls.py を実行した結果がこちら。

採点サーバに送ると、またもや精度は 60% にも及びません(2クラス分類なので全く駄目な結果ということです)。もうだめだー!!!逃げたい!!!

そう思っていたところで、 Cpaw 運営側から採点システムの不具合があり、正確な採点がされていないので,データを再提出するようにという指示。先の芸能人ブログ分類、マルウェアURL分類の結果を再提出した結果、こんな感じになりました。

entertainer_blog: 精度 94.6%
malware_urls: 精度 83.7%

なんだぁ〜〜〜〜。ちゃんと分類できてるんじゃん!本当に焦って泣きそうでしたよ!!よかった。

■ 調子に乗りながら、マルウェア分析の分類問題

次はマルウェア分析問題にとりかかっていきます。このデータセットは下記サイトから入手できる MalwareTrainingSets が先と同様のフォーマット(ただしJSON)に変換されているものです。

Free Malware Training Datasets for Machine Learning
https://github.com/marcoramilli/MalwareTrainingSets

データセットのディレクトリ/ファイル構造
train/APT1/1046.json
train/APT1/1051.json
train/APT1/1063.json
train/APT1/1065.json
train/Crypto/0.json
train/Crypto/100.json
train/Crypto/1000.json
train/Crypto/1002.json
train/Locker/1004.json
train/Locker/1012.json
train/Locker/1037.json
train/Locker/1048.json
train/Zeus/1.json
train/Zeus/10.json
train/Zeus/1001.json

train/Zeus/1005.json
...

あるデータファイルの中身の例


Cpawからデータセットのフォーマットが事実上先程と同じなので、遠慮なく分類器にかけていきます。もしかすると、当日では、JSONを解析して特定の値のみを評価したかもしれません(よく憶えていません)。

得られた結果は以下のとおり。
malware_analysis: 精度 99.6%

実はこのデータセットはある見方をするとルールベースで 100% を達成することができました。しかし、それでも追加のコードを書いたりせずに機械学習で殴っておけば 99% の精度が出せる点が、機械学習のメリットだと思います。

さてここまで entertainer_blog 94.6%, malware_urls 83.7%, malware_analysis 99.6% の精度が出せたので、私のスコアは 94+83+99 で合計 276 となり、二番手グループに大躍進です!! (会場スポンサーですけど)


■ ニューラルネットワークで"ファッションMNI?T"

さてさて!

気分がよくなってきたところで、次のデータセットに取り組んでいきましょう。ここまではテキストのデータセットばかりを選んできましたが、残っているデータセットは「ファッションMNI?T」と「古代文字」のふたつ。どちらかを先に試すか?と思ったら、まずは前者かな、と思いました。 MNIST といえば 28x28 の 10 クラス分類問題で、名前から想像するに同じような要領でいけるのではないか、と思い、データセットを覗いてみることに。



これもボーナス問題ですね!オリジナルの Fashion MNIST データセットでは黒塗りマスクがないのですが、今回のは黒塗りマスクのイタズラがされているデータでした。

これはイケる、という確信を得ます。MNIST同様、28x28のモノクロサイズの10クラス分類。データセットをひと目みるとわかりますが、全ての画像に同一パターンの黒塗りがかかっています。畳み込みニューラルネットワークを使用するとこの黒塗りエッジ部分などが邪魔をするかもしれませんが、このデータを単純に線形結合で入力する場合は、オリジナルのファッション MNIST を 14x14 にリサイズされた状態である、と解釈できるのではないでしょうか。もう、これは 14x14 の MNIST にしか、私には見えません。

この問題をどう解くか、ですが Cpaw AI Competition のレギュレーションでは、イベントで提供された 12コア96GB を使いまくっていいので(畳み込んでいるとあっという間に時間が過ぎてしまいそうですが)線形結合で殴るぐらいの計算リソースと残り時間はあります。また、畳み込むと上にかぶっているマスクが邪魔になるだろうでしょうから、結果が予測できません。なので、線形結合モデルでいくことにします。

とりあえず、Chainerフレームワークをインストールします。

pip3 install chainer

データセットはこれまで通り各クラスがディレクトリで分けられて提供されていましたが、テキストファイルではなく画像なので、データセット読み込みを実装します。普段は cv2.imread() のほうが使い慣れているのですが、cv2モジュールがすぐインポートできなかったので、今回はPILを使ってみました。

以下が Chainer を使ってニューラルネットワークを訓練し、テストデータを予測するためのコードの例です。

このコードを実行し、得られた結果を採点サーバに送信したところ 81% の精度が得られ、私は大会で暫定首位に躍り出ました。(会場スポンサーですけど)


■ これは引っ掛けデータセットな「古代文字」

さて、残りは古代文字データセットです。このデータセットは下記URLから入手できる古代文字画像が、一文字ごと、画像ファイルに分割された状態で提供されました。

文学オープンデータ共同利用センター / Center for Open Data in the Humanities
http://codh.rois.ac.jp/



正直、このデータセットはちらっと見るだけでも 13:30-18:00 のコンペティションの中で扱うデータセットとしては非常に重いです。ファッションMNISTのようにある程度の正規化がされているわけでもなく、さすがに畳み込みニューラルネットワークなどのアプローチで、きちんと回さないと、精度が出ないのではないか?という気がします。

とはいえ、この段階で残り1時間ほど。チャレンジできるところまでチャレンジしましょう。(会場スポンサーですけど)


■ 突然のカーテンコール

……と思ったところで、運営からその時点の暫定順位の発表があり、運営の伊東さんから下記の案内がありました。

「あ、ちなみにこの hasegaw って人は会場スタッフなので表彰対象外です」

というわけで、私の AI Competition は散って終わったのでした。



なお、今回のブログ記事執筆のために作成しなおしたコードでは、下記のスコアが得られました。

entertainer_blog: 精度 94.6%
malware_urls: 精度 83.7%
malware_analysis: 精度 99.6%
fashion_mnist: 精度 81.9%

小数点以下切り捨ての合計スコアは357ですので、当日このスコアが出せていたら、トップに踊りでて Google Home mini を勝ち取っていたかもしれません。😭

後日自分で購入した Google Home mini

もちろん、今回はたまたまデータセットと私のとった手段がうまくはまってスコアが伸びただけしかありません。会場には、スコアを伸ばすことを重きにおくのではなく、フルスクラッチで機械学習アルゴリズムを実装するところからスコアを積み上げていた方もいらっしゃるようで、本当に頭がさがります。

次の機会には、もし会場スポンサーの立場であっても、きちんと参加登録してコンペティションに臨んでみたいと思います。


■ 終わりに

機械学習って、聞いたことがあるけど未だ試していなかったり、もしくはちょっと勉強してみたという方も増えてきているのではないでしょうか。

私も、もともと「機械学習やディープラーニングってすごいなぁ」と思いながら、 IkaLog というスプラトゥーンの画像認識ソフトを作っていく過程で、意図せず、各種機械学習アルゴリズムのパワーを体感して、そこから Coursera の Machine Learning コースを受講した程度の知識しかありません。1年ほどスプラトゥーンの画像データに取り組んだ経験がある以外は、機械学習について凡人レベル、もしくはそこに毛が生えた程度の知識しかありません。

しかし機械学習は、ちょっとモチベーションがあると、その状況なりの使い道や楽しみ方が見つかります。また、今回のような問題で7割8割の精度が出せれば、業務上でも自分の仕事の手間を削減したり、ちょっとした業務効率化で効いたりするものです。さくらインターネットでも、機械学習未経験のデータセンター現地スタッフが独学で Jubatus を用いたオペレーション業務の効率化にも取り組んだりもしています。

Cpaw では、今後とも同様のオンラインイベントやオフラインイベントを開催すると伺っています。機会があれば、このようなイベントにぜひとも参加してみてください。

■ おまけ

過去に参加したアドベントカレンダー

2017年9月4日月曜日

Python 向け OpenCV 3.3.0 (Win32) ビルド済みライブラリのビルドオプション

下記サイトから入手可能な opencv_python-3.3.0-cp36-cp36m-win32.whl の cv2.getBuildInformation() の結果。



General configuration for OpenCV 3.3.0 =====================================

  Platform:
    Timestamp:                   2017-08-05T02:46:14Z
    Host:                        Windows 10.0.15063 AMD64
    CMake:                       3.7.2
    CMake generator:             Visual Studio 14 2015
    CMake build tool:            C:/Program Files (x86)/MSBuild/14.0/bin/MSBuild.exe
    MSVC:                        1900

  CPU/HW features:
    Baseline:                    SSE SSE2
      requested:                 SSE2
      required:                  SSE2
    Dispatched code generation:  SSE4_1 SSE4_2 FP16 AVX AVX2
      requested:                 SSE4_1 SSE4_2 AVX FP16 AVX2
      SSE4_1 (2 files):          + SSE3 SSSE3 SSE4_1
      SSE4_2 (1 files):          + SSE3 SSSE3 SSE4_1 POPCNT SSE4_2
      FP16 (1 files):            + SSE3 SSSE3 SSE4_1 POPCNT SSE4_2 FP16 AVX
      AVX (5 files):             + SSE3 SSSE3 SSE4_1 POPCNT SSE4_2 AVX
      AVX2 (7 files):            + SSE3 SSSE3 SSE4_1 POPCNT SSE4_2 FP16 FMA3 AVX AVX2

  C/C++:
    Built as dynamic libs?:      YES
    C++11:                       YES
    C++ Compiler:                C:/Program Files (x86)/Microsoft Visual Studio 14.0/VC/bin/cl.exe  (ver 19.0.24218.1)
    C++ flags (Release):         /DWIN32 /D_WINDOWS /W4 /GR  /EHa  /D _CRT_SECURE_NO_DEPRECATE /D _CRT_NONSTDC_NO_DEPRECATE /D _SCL_SECURE_NO_WARNINGS /Gy /bigobj /Oi /fp:fast   /arch:SSE /arch:SSE2 /wd4251 /wd4324 /wd4275 /wd4589 /MP12  /MD /O2 /Ob2 /DNDEBUG  /Zi
    C++ flags (Debug):           /DWIN32 /D_WINDOWS /W4 /GR  /EHa  /D _CRT_SECURE_NO_DEPRECATE /D _CRT_NONSTDC_NO_DEPRECATE /D _SCL_SECURE_NO_WARNINGS /Gy /bigobj /Oi /fp:fast   /arch:SSE /arch:SSE2 /wd4251 /wd4324 /wd4275 /wd4589 /MP12  /D_DEBUG /MDd /Zi /Ob0 /Od /RTC1
    C Compiler:                  C:/Program Files (x86)/Microsoft Visual Studio 14.0/VC/bin/cl.exe
    C flags (Release):           /DWIN32 /D_WINDOWS /W3  /D _CRT_SECURE_NO_DEPRECATE /D _CRT_NONSTDC_NO_DEPRECATE /D _SCL_SECURE_NO_WARNINGS /Gy /bigobj /Oi /fp:fast   /arch:SSE /arch:SSE2   /MP12  /MD /O2 /Ob2 /DNDEBUG  /Zi
    C flags (Debug):             /DWIN32 /D_WINDOWS /W3  /D _CRT_SECURE_NO_DEPRECATE /D _CRT_NONSTDC_NO_DEPRECATE /D _SCL_SECURE_NO_WARNINGS /Gy /bigobj /Oi /fp:fast   /arch:SSE /arch:SSE2   /MP12  /D_DEBUG /MDd /Zi /Ob0 /Od /RTC1
    Linker flags (Release):      /machine:X86  /INCREMENTAL:NO  /debug
    Linker flags (Debug):        /machine:X86  /debug /INCREMENTAL
    ccache:                      NO
    Precompiled headers:         YES
    Extra dependencies:          comctl32 gdi32 ole32 setupapi ws2_32 vfw32 glu32 opengl32
    3rdparty dependencies:

  OpenCV modules:
    To be built:                 core flann imgproc ml objdetect photo video dnn imgcodecs shape videoio highgui superres ts features2d calib3d stitching videostab python3
    Disabled:                    python2 world
    Disabled by dependency:      -
    Unavailable:                 cudaarithm cudabgsegm cudacodec cudafeatures2d cudafilters cudaimgproc cudalegacy cudaobjdetect cudaoptflow cudastereo cudawarping cudev java viz

  Windows RT support:            NO

  GUI:
    QT:                          NO
    Win32 UI:                    YES
    OpenGL support:              YES (glu32 opengl32)
    VTK support:                 NO

  Media I/O:
    ZLib:                        build (ver 1.2.8)
    JPEG:                        build (ver 90)
    WEBP:                        build (ver encoder: 0x020e)
    PNG:                         build (ver 1.6.24)
    TIFF:                        build (ver 42 - 4.0.2)
    JPEG 2000:                   build (ver 1.900.1)
    OpenEXR:                     build (ver 1.7.1)
    GDAL:                        NO
    GDCM:                        NO

  Video I/O:
    Video for Windows:           YES
    DC1394 1.x:                  NO
    DC1394 2.x:                  NO
    FFMPEG:                      YES (prebuilt binaries)
      avcodec:                   YES (ver 57.89.100)
      avformat:                  YES (ver 57.71.100)
      avutil:                    YES (ver 55.58.100)
      swscale:                   YES (ver 4.6.100)
      avresample:                YES (ver 3.5.0)
    GStreamer:                   NO
    OpenNI:                      NO
    OpenNI PrimeSensor Modules:  NO
    OpenNI2:                     NO
    PvAPI:                       NO
    GigEVisionSDK:               NO
    DirectShow:                  YES
    Media Foundation:            NO
    XIMEA:                       NO
    Intel PerC:                  NO

  Parallel framework:            Concurrency

  Trace:                         YES (with Intel ITT)

  Other third-party libraries:
    Use Intel IPP:               2017.0.2 [2017.0.2]
               at:               D:/Build/OpenCV/opencv-3.3.0-vc14-x32-py36/3rdparty/ippicv/ippicv_win
    Use Intel IPP IW:            prebuilt binaries (2017.0.2)
    Use Intel IPP Async:         NO
    Use Lapack:                  NO
    Use Eigen:                   NO
    Use Cuda:                    NO
    Use OpenCL:                  NO
    Use OpenVX:                  NO
    Use custom HAL:              NO

  Python 2:
    Interpreter:                 X:/Python27/python.exe (ver 2.7.13)

  Python 3:
    Interpreter:                 X:/Python36-x32/python.exe (ver 3.6.2)
    Libraries:                   X:/Python36-x32/libs/Python36.lib (ver 3.6.2)
    numpy:                       X:/Python36-x32/lib/site-packages/numpy/core/include (ver 1.13.1)
    packages path:               X:/Python36-x32/Lib/site-packages

  Python (for build):            X:/Python27/python.exe

  Java:
    ant:                         NO
    JNI:                         X:/Java18/include X:/Java18/include/win32 X:/Java18/include
    Java wrappers:               NO
    Java tests:                  NO

  Matlab:                        NO

  Documentation:
    Doxygen:                     NO

  Tests and samples:
    Tests:                       YES
    Performance tests:           YES
    C/C++ Examples:              NO

  Install path:                  D:/Build/OpenCV/opencv-3.3.0-vc14-x32-py36/install

  cvconfig.h is in:              D:/Build/OpenCV/opencv-3.3.0-vc14-x32-py36
-----------------------------------------------------------------

2017年2月8日水曜日

ブートイメージからカーネル、rootfs、configを取り出す

image.ub ファイルからカーネル、rootfs、/proc/configを取り出す

SDSoC 2016.3に含まれる ZYBO 向け Software Platform からカーネル、 rootfs、/proc/config を取り出したかったので取り出した。

そもそも image.ub ってなんだ


ARMで使えるブートローダu-bootが扱うイメージフォーマットらしい。

$ mkimage -l image.ub
FIT description: PetaLinux arm uImage with single Linux kernel and FDT blob
Created:         Fri Nov 18 04:07:34 2016
 Image 0 (kernel@1)
  Description:  PetaLinux Kernel
  Created:      Fri Nov 18 04:07:34 2016
  Type:         Kernel Image
  Compression:  gzip compressed
  Data Size:    8747883 Bytes = 8542.85 kB = 8.34 MB
  Architecture: ARM
  OS:           Linux
  Load Address: 0x00008000
  Entry Point:  0x00008000
  Hash algo:    crc32
  Hash value:   252654ca
 Image 1 (fdt@1)
  Description:  Flattened Device Tree blob
  Created:      Fri Nov 18 04:07:34 2016
  Type:         Flat Device Tree
  Compression:  uncompressed
  Data Size:    13962 Bytes = 13.63 kB = 0.01 MB
  Architecture: ARM
  Hash algo:    crc32
  Hash value:   66629950
 Default Configuration: 'conf@1'
 Configuration 0 (conf@1)
  Description:  PetaLinux Boot Linux kernel with FDT blob
  Kernel:       kernel@1
  FDT:          fdt@1


カーネルを取り出す


まずこのイメージからカーネルを取り出す。 mkimage -l の結果から gzip compressed であることがわかっているので、 magic を頼りに探すと 240バイト目から gzip データがあることがわかる。 mkimage の結果からファイルは 8747883 バイトであることがわかる。

$ grep -P -a -b  --only-matching $'\x1F\x8B\x08' image.ub
240:

なので

$ dd if=image.ub of=linux.bin.gz bs=1 skip=240 count=8747883
8747883+0 records in
8747883+0 records out
8747883 bytes (8.7 MB, 8.3 MiB) copied, 6.91697 s, 1.3 MB/s

$ file linux.bin.gz
linux.bin.gz: gzip compressed data, was "linux.bin",
  last modified: Thu Nov 17 19:07:33 2016, max compression, from Unix


カーネルの中から gzip データを取り出す


さらにこのアーカイブの中にrootfsが含まれている。cpioフォーマットで入っているかと思い、cpioフォーマットのヘッダである"070707"をgrepしたら発見... と思ったがハズレだった。これはcpioアーカイブじゃなくてcpioアーカイブを探すプログラムが参照している文字列っぽい。ということは...

$ grep -P -a -b  --only-matching $'\x1F\x8B\x08' linux.bin
6278680:
8588960:
9923536:

gzip のヘッダらしきものが3つ見つかった。まずひとつ目は...

$ dd if=linux.bin skip=6278680 bs=1 | gzip -dc > hoge

gzip: stdin: decompression OK, trailing garbage ignored

toor@gpusv:~/zynq7/extract_initramfs$ file hoge
hoge: Linux make config build file, ASCII text

ASCIIだと!?

$ head hoge
#
# Automatically generated file; DO NOT EDIT.
# Linux/arm 4.6.0 Kernel Configuration
#
CONFIG_ARM=y
CONFIG_ARM_HAS_SG_CHAIN=y
CONFIG_MIGHT_HAVE_PCI=y
CONFIG_SYS_SUPPORTS_APM_EMULATION=y
CONFIG_HAVE_PROC_CPU=y
CONFIG_NO_IOPORT_MAP=y

...config.gz だった。まあ、ついでなので保存。

$ mv hoge config


では次。

$ dd if=linux.bin skip=8588960 bs=1 | gzip -dc > hoge
gzip: stdin: decompression OK, trailing garbage ignored

toor@gpusv:~/zynq7/extract_initramfs$ file hoge
hoge: ASCII cpio archive (SVR4 with no CRC)

toor@gpusv:~/zynq7/extract_initramfs$ cat hoge | cpio -it | head
cpio: Substituting `.' for empty member name
.
dev
dev/pts
etc
etc/opkg
etc/opkg/arch
etc/rpm
etc/rpm/sysinfo
etc/rpm-postinsts
etc/network

今回は間違いなくinitrdイメージだ。

$ mv hoge initrd


目的な達成したけど、3つめはなんじゃらほい。
dd if=linux.bin skip=9923536 bs=1 | gzip -dc > hoge
gzip: stdin has flags 0xce -- not supported


これは有効なgzipじゃなかった。"070707" 同様に gzip をデコードするルーチンが参照している定数かも。