FreeBSD device driver で DMA

FreeBSD でデバイスドライバ書いて DMA を動かすためのいろいろ。とりあえず参考になりそうなのは、

このあたり。実例は /usr/src/sys/dev の下あたりをみればいくらでもあるけれど、とりあえず参考にしたのは /usr/src/sys/dev/hifn/hifn7751.c とか。
bus_alloc_resources() とかで BAR の値を読み出したり、DMAC を制御するためのレジスタを mmap() できるようにするあたりは今回はとりあえず省略して、DMA のアクセス先になるメインメモリ上の領域を確保するための手順をまとめておくことにします。

  1. bus_dma_tag_create()
    デバイスのDMACに関するいろいろを設定する。たとえば以下のようなこと。これを DMA tag という。

    • 何バイト単位でDMAできるか(1バイト単位か、4バイト単位か、など)
    • DMA可能なアドレスの範囲 (16MB, 4GB, それ以上、など)
    • DMA用のメモリの合計の最大サイズ
    • 上記メモリを最大いくつのセグメントに分割してよいか、セグメントサイズの上限はいくらか

    DMA tag を作るだけではメモリは確保されません。

  2. bus_dmamap_create()
    タグの情報に基づいて map を生成します。ひとつのタグに対応する複数の map を生成できます。map だけで、実際のメモリは確保されないっぽい。

  3. bus_dmamem_alloc()
    ここでmalloc() か contigmalloc() (確保する領域のサイズ次第ですね) が呼ばれます。確保されるサイズは tag を作るときに指定した最大サイズ。物理アドレスは分散している可能性がありますが、カーネル仮想アドレス空間では連続した領域になります (たぶん)。

  4. bus_dmamap_load()
    最後にこれでデバイス側から見えるアドレスのリストを受け取ります。bus_dmamap_load() ではすぐにリストがもらえなくて、callback 関数を指定しておいて、おわると結果が帰ってくる感じです。

片付けるときは逆順です。

  1. bus_dmamap_unload()
  2. bus_dmamem_free()
  3. bus_dmamp_destroy()
  4. bus_dma_tag_destroy()

ナゴチキン

おきなわ名店街シリーズ第一弾はとりあえずナゴチキン。名護市役所の(裏側の通りの)隣です。
IMG_3858.jpg
注文してから揚げてくれる唐揚げはめっちゃジューシー。名護に住んでたらこれで大宴会やりたい。
IMG_3861.jpg
半身揚げおいしそうなんですが、さすがに一人では・・・どうかな。メニューはこれだけです。かっこいい。
IMG_3859.jpg
あと、持ち帰り専門店です。
IMG_4370.JPG

TCP プログラミングあれこれ

ICFPT Design Competition の委員をやっているので、ホストになるコードをごりごり書いているわけですが、GTK とか Qt とかでユーザインタフェイス作るのだるいなー、と思って HTML+JavaScript でやることにしまいた。最近は nmny 作ったりしてけっこう JavaScript 書いてた (きれいなコードじゃないと怒られそうですが) ので、まあいけるかなー、と。
ブラウザで表示させる部分から AJAX でデータを取りにいけばいいわけですが、そうすると何が問題かというと、HTTP のところを自分で書かないといけないところです。今回の場合、会場でプロジェクタに接続するマシン一台だけで見られればいいので、複数のブラウザから同時にセッションを張られることは考えていません。
なんとかわりとちゃんと動くようになったのですが、引っかかったポイントを記録しておきます。なにしろ、MPI とかじゃなくて、直接 TCP で通信するプログラムをまともに書くのは、自分が学生だったときの学生実験以来なので…

Address already in use

デバッグ中はプログラムを走らせて止めて、修正してはすぐ起動するわけですが、すぐ同じポートを使うプログラムを走らせると Address already in use になって bind() できないことがあります。
これは、ソケットが close されてもしばらく再利用できないため (再利用できるまでの時間はTCP/IP stackの実装依存っぽい) で、setsockopt() を使って解決します。FreeBSD/MacOS X では SO_REUSEPORT も指定しますが、Linux では SO_REUSEADDR だけで動くみたい、というか、SO_REUSEPORT がありませんでした。
[code:cpp]
  setsockopt(sock, SOL_SOCKET, SO_REUSEADDR, (char*)&on, sizeof(on));
#if defined (__FreeBSD__)  || (__APPLE__)
  setsockopt(sock, SOL_SOCKET, SO_REUSEPORT, (char*)&on, sizeof(on));
#endif
[/code]

ブラウザへデータを送信するタイミング

いまのところ複数のクライアントから接続されることはないので、何回目のアクセスではこれを返す、というのが静的に決まっています。そこで、accept() で接続が成立したらすぐにブラウザにデータを送信すればいいや、と思ったのですが、ブラウザによってはブラウザがリクエストを送信するまえにデータが届くとエラーになるようです。
ちゃんと GET がくるまで待ちましょう。あたりまえか…

Socket を close() する前に

BSD 系のシステムでは問題が起きなかったのですが、Linux ではデータがブラウザ側に届く前に、サーバ側から RST が送信されて接続が切れてしまう問題がおきました (これは最初全然わからなくて、wireshark で通信の様子をのぞいてみてはじめて気づきました)。RST が突然送られるので、ブラウザにどこまでデータが送れるかは、毎回違う感じです。
最初は socket を fdopen() して fgets() や fprintf() でアクセスするのが悪いのかな、と思って、最後に fflush() してみたりしたのですが、状況は改善しません。それで、まじめに send() と recv() を使うようにもしてみましたが、やはりうまく動作しません。
で、いろいろ調べた結果、受信バッファにデータが残った状態で socket を close() すると RST が送信されるということがわかりました。つまり、GET がきただけで返事を送っていたのですが、最後の空行まで受信してから返事をすれば OK ということです。
受信バッファが空でないと close() のときに RST が送信されるという挙動、もしかしたら Linux だけなのかもしれませんが、気をつけないといけませんね。

SyntaxHighlighterいれてみた

同じような名前のエントリ書いてる人が100人くらいいそうですけど、MovableTypeでコード書くときに不便なので、SyntaxHighlighterいれてみた。これすごいね。
HTML Head のテンプレートの最後に、
[code:xml]
<$mt:SyntaxHighlighterInclude brush="cpp,php,jscript,xml" theme="default"$>
[/code]
と書くだけでした。あとは本家のサイトに説明がある通り。各種言語に対応しているのも非常にありがたいです。Verilog-HDL とか VHDL とかはないけどね… (書けって?)

綱ひき

綱引き、というと運動会な感じですが、沖縄では各地に綱引きの伝統がのこっており、すごいお祭りです。
那覇のなんかは、国道を封鎖して、しかも中央分離帯を取り外して (!) 行われます。
IMG_1665.JPG
いや、ほんとすごいよ。

Managed Switch 購入計画

研究室も早いもので3年目。
昨年度のはじめに学生用の端末なんかは充分な台数を確保したので、次はCADとかの環境だよなー、とか、前職の頃から使っているNASもバックアップがないしストレージもいるよなー、と思ったりしています。
去年、Netgear の GS716T というスマートスイッチを購入したときに、16ポートなのにLink aggregation group (LAG) が2本しか設定できないのでびっくりしました。で、ちょっと調べてみたところ、
GS716Tv2: 2 LAGs
GS724Tv3: 4 LAGs
だそうな。うちは教員研究室が機器室も兼ねているので、ファンレスなのが非常にありがたいのだけれど、ちょっとね…
というわけで全前職時代に Myrinet-10G とかでさんざんお世話になった Procurve のラインナップをみてみると、
HP Procurve 1810-24G: 8 LAGs up to 4 links/LAG
これかな。しかし、普及価格帯の managed switch って安くなりましたね…

台風とか

季節外れですけど、沖縄で台風くるとこうなりますよ、というアレ。
本番が近付くと、高い橋とかが閉鎖されます。これはどこでもあることですが。写真は那覇の泊大橋。
IMG_3429.JPG
木が折れるのはわりとあること。
IMG_1176.JPG
もちろん、根っこから倒れることだってあります。
IMG_1164.JPG
エアコンの室外機もよく壊れます。
ファンが壊れることもあるし、基板がやられることもあるし、台座ごとぶっ壊れることも…
集合住宅ではよく、「非常の際はここを破って隣へ」というアレを、エアコンの室外機が次々に突破していったという話を聞きます。
エアコン、自宅はガマンすればなんとかなるとして、職場のエアコンが壊れるとコンピュータは使えなくなるし、予算の都合とかでなかなか直せないしで、大打撃です。
IMG_3535.JPG
でも、屋根がこんなふうになるのはあんまり見ない… かな。瓦屋根は漆喰でちゃんと固めていますし、コンクリートのおうちが多いので。
IMG_3683.JPG
電話や電力といった電線を使ったインフラは当然のようにダメージを受けます。停電は那覇あたりではほとんどなくなっていますが、長い地域では2日から3日、電話だともっとかかることもあり、他の地域のNTTから救援部隊がやってきたりもします (鹿児島から船で1泊、大阪からなら2泊かかるので、つまりそれ以上かかっているということ)。
IMG_3530.jpg
これなんかは元がどうなってたかわからない感じですが、こういうことも…
IMG_3782.jpg
でも、沖縄にきて素晴らしいと思うのは、台風で暴風警報が出てバスが止まると、ほとんどの職場が休みになること。ひどくなったら外に出られなくなったり (風圧でドア開かなかったりしますし)、停電するのは当たり前。家に帰れなくなるまで仕事したりとか、そういうことはありません。
被害が出ることはわかっていても「どうせたいしたことないだろ」とタカをくくって普段通り過ごすからこそ「想定外」という言葉が出てきたりするわけで、備えられるものにはちゃんと備えるって大事だな、と思います。