2010年02月09日

go言語でgosqlite3を使ってみるためのcgoへのパッチ

以下のパッチは2/23現在不要なようです。

go言語でもsqlite3を使ってみたいと思い探してみると、いくつか既に拡張を作っている方がいたので以下のものをゲットしてみたのですが、残念ながらコンパイルエラー。

原因を調べてみるとgoからC言語のライブラリを呼び出すラッパー生成ツールのcgoによって生成された_cgo_gotypes.goで型の前方参照をしており定義順がおかしいとのこと。 (ちなみにgosqlite3に付属のcgoパッチは未適用。既に不要と思われます。)

どう考えてもcgoで解決すべき問題な気がするので Quick and Dirtyに解決パッチを作ってみました。恥ずかしながらまだgoに慣れていないので我ながら情けないコードですが。 

$GOROOT/src/cmd/cgoで以下のパッチを適用。

--- out.go.orig    2010-02-08 17:19:13.000000000 +0900
+++ out.go    2010-02-09 04:18:59.000000000 +0900
@@ -10,6 +10,7 @@
     "go/printer"
     "os"
     "strings"
+    "bytes"
 )
 
 func creat(name string) *os.File {
@@ -20,6 +21,25 @@
     return f
 }
 
+type defent_t struct {
+    def  string
+    done bool
+}
+
+func outdefs (fo *os.File, defs map[string]defent_t, name string) {
+    d := defs[name]
+    if !d.done {
+        next := d.def
+        d.done = true
+        defs[name] = d
+        _, ok := defs[next]
+        if ok && !defs[next].done {
+            outdefs(fo, defs, next)
+        }
+        fmt.Fprintf(fo, "type %s %s\n", name, d.def)
+    }
+}
+
 // writeDefs creates output files to be compiled by 6g, 6c, and gcc.
 // (The comments here say 6g and 6c but the code applies to the 8 and 5 tools too.)
 func (p *Prog) writeDefs() {
@@ -40,10 +60,19 @@
     fmt.Fprintf(fgo2, "import \"unsafe\"\n\n")
     fmt.Fprintf(fgo2, "type _ unsafe.Pointer\n\n")
 
+    var defs map[string]defent_t = make(map[string]defent_t, len(p.Typedef))
+    var bufs = bytes.NewBuffer(make([]byte, 0, 10000))
     for name, def := range p.Typedef {
-        fmt.Fprintf(fgo2, "type %s ", name)
-        printer.Fprint(fgo2, def)
-        fmt.Fprintf(fgo2, "\n")
+        bufs.Reset()
+        err := printer.Fprint(bufs, def)
+        if err != nil {
+            fatal("%s", err)
+        } else {
+            defs[name] = defent_t { bufs.String(), false }
+        }
+    }
+    for name,_ := range defs {
+        outdefs(fgo2, defs, name)
     }
     fmt.Fprintf(fgo2, "type _C_void [0]byte\n")
 

内容的には定義のテキスト表現を先に生成しておいて、前方参照がないかどうか探しているだけです。gosqlite3だけに限れば単純にgo言語の組み込みデータ型へのtypeを先に出力するだけでもコンパイルは通りますが。

ちなみにまだ試していませんが"go-db", "phf/go-sqlite3"というのがあり、こちらの方がいろいろやってくれるかもしれません。

go言語はCで書かれたライブラリへのラッパーが非常に楽に作れるみたいですね。いろいろと面白いことが出来そうです。

2010年02月02日

macでもgo言語でX11に描画してみるメモ

最近個人的に興味を持っているのがGoogleのGo言語です。今年に入ってからぼちぼち勉強がてら軽く使ってみているのですが、少し癖はあるものの悪くありません。さほど高速ではありませんが、丁度C言語とスクリプト言語の間の隔たりをカバーできそうな感じです。

go言語のコンパイル/インストールは本家ページのInstalling Goを見ればとても簡単です。リポジトリは積極的にアップデートされているのでたまに問題があることもあるかもしれません。続けて使うなら時折"hg pull ; hg update"して"make"しておいたほうがよさげです。本家でのサポートが決まったということで期待のgccベースのgccgoはコンパイルに結構時間がかかる上、GCがまだとのことなので様子見です。

で表題の件ですが

上のページを発見。go付属のライブラリを使ってx11に絵を描くサンプルを公開されています。これはと思い早速Macでも試そうとしたところexpのx11がないと宣われてしまいました。

少し調べてみると"muddy brown thang"さんのサンプルにも少し修正は必要そうなものの、ext/draw/x11がそもそもコンパイルされていない模様。手動でmake && make installしてみても"unsupported DISPLAY"などと言われ動作しません。

ライブラリをチラ見するとUnixドメインソケットが半分決め打ちになっています。仕方がないのでちょこっと以下のようなパッチをでっち上げてみました。

diff -rw x11.orig/auth.go x11/auth.go
10a11,12
>
>       "strings"
15a18,37
>       if strings.Index(d,"/tmp/launch") >= 0 {
>           return d
>       }
>       if len(d) < 1 || d[0] != ':' {
>               return ""
>       }
>       i := 1
>       for ; i < len(d); i++ {
>               if d[i] < '0' || d[i] > '9' {
>                       break
>               }
>       }
>       return "/tmp/.X11-unix/X" + d[1:i]
> }
>
> func getDisplayNum() string {
>       d := os.Getenv("DISPLAY")
>       if strings.Index(d,"/tmp/launch") >= 0 {
>           return "0"
>       }
27a50
>
75c98
<       display := getDisplay()
---
>       display := getDisplayNum()
diff -rw x11.orig/conn.go x11/conn.go
456c456
<       s, err := net.Dial("unix", "", "/tmp/.X11-unix/X"+display)
---
>       s, err := net.Dial("unix", "", display)

$GOHOME/go/src/pkg/exp/draw/x11に入って上のパッチを適用。手動で

make
make install

後は上の"muddy brown thang"さんから描画するサンプルプログラムをもらってきて、先頭付近のimport文中の"draw"を"exp/draw", "draw/x11"を"exp/draw/x11"に変更してコンパイル

以上。
パッチはいい加減ですがめでたくX11に円が表示されました。

まだ余り調べていませんがCとはリンクできるみたいなので、Objective Cとのリンク方法を調べてみて、うまくいけたらCocoaとの連携、armバージョンでiPhoneアプリが作れたりしたら面白いかもしれません。

2010年01月16日

LinuxでコマンドラインからURLやファイルを開けるxdg-open/gnome-openのメモ

LinuxのデスクトップのコマンドラインからNautilusでのWクリックなどと同じようにファイルを開くことが出来るコマンドがxdg-openとgnome-open。結構前からあるコマンドなのでご存じの方には今更なにをだと思いますが、不勉強で知らなかった(か忘れていた)ので忘れないようにメモ。参考にしたのは以下のページ。

Mac OSXを使っていて便利なのはTerminalから'open'コマンドでたいていのファイルやディレクトリが開けること。例えば'open .'と打ち込むとカレントディレクトリをFinderが開いてくれる。'open hoge.c'等とするとXCodeで開いてくれる。'open -a Emacs'とやるとApplicationのEmacs.appが起動。'open hoge.dmg'とやるとディスクイメージがマウントされるといった感じ。丁度FinderでファイルをWクリックしたのと同じ動作が行われます。

同じようにUbuntu等のLinuxデスクトップを使用していてファイルやフォルダを開けないものかと思っていたのですが、これを実現するのがgnome-open, xdg-openの両コマンド。

その名の通りgnome-openはgnomeデスクトップ用。xdg-openはデスクトップを認識して適切にファイルを開いてくれるもの。

ターミナルアプリケーションから'xdg-open URL or File'とすることで URLならデフォルトのブラウザが、ファイルなら関連づけに従ってアプリケーションが開いてくれます。例えば'xdg-open hoge.xls'等とするとOpenOfficeが起動するということで。CLIをよく使う方にはかなり便利と思います。

なんだかコマンドがダサいと思われる方は.bashrcでinteractiveか判定した後に

alias open=xdg-open

等としておけばいいかもしれません。

2010年01月06日

明けましておめでとうございます

ちょっと遅ればせですが、新年あけましておめでとうございます。

なかなか先行き不透明な不況下、みなさまいかがお過ごしでしょうか。企業の設備投資もさほど伸びていませんし、本業の組み込みシステム関連は今年も厳しい一年となりそうです。とはいえ、そんなことも言ってもいられません。お仕事頑張りますので関係各位殿よろしくお願いいたします。 まだ関係のない方も組み込みシステム、制御システムのファームなどの設計・実装・教育・技術コンサルなど全般やっておりますので、お声かけくださいませ。

新年早々から新しいAppleのデバイス(巨大iPhoneともいわれる)や新iPhone、GoogleのAndroidも元気。今年も携帯端末が面白そうです。お金を貯めておかねば(笑。ソフト作成もぼちぼち遊びながら試しています。

とりあえず最近は調査という心の名目を立てて時々iPhoneのゲームで遊んでます。あんまり新しいゲームでもないのですが

  • GD Swarm -- Tower Defence系。パズルゲームとして楽しめます
  • Cartoon Wars -- 必勝法があったりするのですが、普通にやれば結構楽しいです
  • War Generation -- 劣化版大戦略ですがそれなりに面白いです
  • Sorcerer #1/#2 -- Wizクローン。細部は違いますが雰囲気バリバリです

特に最近はGD Swarmが面白くて時々寝不足になってしまいます。

では、今年も宜しくお願いいたします。

2009年12月04日

Google Public DNS/OpenDNS/プロバイダ/ローカルでDNSの速度比較

Googleが安全で高速なDNSサービスを開始したとのことでちょっと使ってみました。これはまあ一言で誰でも使えるCaching NameServerということでクライアントのDNSの設定をこれに置き換えるといいとのこと。

同じく安全で高速なDNSサービスとしてOpenDNSがありますので、これらと普通のプロバイダのモノ、ローカルのキャッシングnamed等と比較してみました。

ちなみにこれらのいう"安全"とはDNSに対するDosアタックやPoisoning等に強いという意。

計測はLinux Box(Ubutu 9.04/AMD Phoenom2 2.5Ghz)/GB LAN/WAN ADSLです。測定回数は5回で平均は最大最小をのぞいた3回の平均値。 引いた名前はwww.yahoo.co.jp。

  IP
最大
最小
平均
 ローカルのCaching NameServer  ローカル(LAN)  121ms  11ms
 11ms
 ルータのDNSリピート機能  ローカル(LAN)  40ms
 11ms  12ms
 プロバイダのDNS  ns1.wakwak.com
 44ms  39ms  40ms
 Google Public DNS  8.8.8.8
 152ms  71ms  71ms
 OpenDNS  208.67.222.222  293ms  155ms  165ms

 ということで、速度を求めるのなら普通にプロバイダのDNS、caching namedかルータのDNSリピータを使うのがいいという結果となりました。DNSサーバのフォワード先やルータのセカンダリなどに設定するくるくらいならいいかもしれません。

まあ、なによりGoogleのDNSは覚えやすいIPアドレスなのが利点なので、なにかのおりに使ってみてもいいかもしれません。

ということで、高速化を行えるかもとか思うと期待はずれ、というかあんまり変わらないと思います。



2010年03月

  1 2 3 4 5 6
7 8 9 10 11 12 13
14 15 16 17 18 19 20
21 22 23 24 25 26 27
28 29 30 31      

カテゴリー

モバイル版

このページは携帯電話からもご覧いただくことが出来ます。
blog.browncat.org qr-code
Powered by
Movable Type 3.36

Twitter

@yamap

注目エントリー

人気エントリー

デル株式会社ads