localhostと127.0.1.1

127.0.0.1は自分自身を表すIPだが,debianでマシン名に対応するIPは127.0.1.1となっている. つまり,自分自身には,127.0.0.1と127.0.1.1と割り当てられているIPが対応している. サーバーを立てているPCから,そのサーバーにアクセスしたときには,上記のどのIPを使うかによって,サーバーから見た接続先が異なっている.

例えば,rubyでserve側で

require "socket"
s=TCPServer.new(3030)
p s.accept.peeraddr

としてから,client側で

require "socket"
s=TCPSocket.open('localhost',3030)

とすると,serve側には

["AF_INET", 37666, "127.0.0.1", "127.0.0.1"]

などと表示される. 一方,localhostの代わりに,割り当てられたIPを指定すると,割り当てられたIPが表示される.

今回苦しんだのが,127.0.1.1にアクセスした場合の振る舞いである. 私の2009/1/16のブログを見るとその時のrubyでは,127.0.1.1と表示されたようである. しかし,最近のrubyでは,127.0.0.1と表示されるように変わったようである. 昔書いたプログラムを新しいPCで動かそうとして,なかなか思ったように動かなかったが,これが原因だったようである.

Read more...

Python-FuでGimpのFilter

Gimpで画像を処理させるときに,以前はScript-Fuを使っていてscheme言語で書くのが難しかったが,最近はPython-Fuを使えるようになって,楽になった. ちなみに私がpythonを使うのは,micropythonかPython-Fuが主な気がする. 少しは慣れて来たのだが,Filterなどの高度な処理をPython-Fuから行う方法が分からなかった. Gimp3.0になったし,新たに調べてみたら,やり方が分かったので,書いておきたい.

まず,画像の一部を選択した状態にする. Filters - Development - Python-Fu - Python Consoleからコンソールを開いて,以下のコマンドを実行すると,medianフィルターが適用される.

img=Gimp.get_images()[0]
lyr=Gimp.Image.get_layers(img)
chl=Gimp.Selection.save(img) #unselect layer
Gimp.Image.set_selected_layers(img,lyr)
drw=Gimp.Image.get_selected_drawables(img)[0]
flt = Gimp.DrawableFilter.new(drw, "gegl:median-blur", "")
fc = flt.get_config()
fc.set_property("radius", 10)
drw.append_filter(flt)

filterやそのpropertyの名前は,GEGLのサイトで調べることができる. get_configで作ったものに対してset_propertyをするという少し回りくどい設定をしてから,適用する. append_filterでは元の画像を保持したままfilterが非破壊に適用されますが,元の画像を保持する必要が無いときにはmerge_filterを使って下さい.

Read more...

ch32x035でmrubyc-arduinoを動かす

ch32v203をmrubyc-arduinoから動かすことが出来たので、ch32x035でも出来るだろうと思って、やってみた。 しかし、両者には二つの大きな違いがあることが判明した。 一つは、flashの容量がch32v203が64kなのに対して、ch32x035は少し小さくて62kであることである。 2kぐらいは、工夫すればなんとかなるだろうと予想した。 もう一つの大きな違いが、ch32v203にあった隠しflashがch32x035には無いということである。 mrbのコードを隠しflashに置くことによって、flashが節約できる上に、後からそこだけを書き換えるという使い方が出来たのだが、ch32x035では同じことが出来無い。 これらを以下のように対応して、ch32x035でも、Arduinoを使ってmruby/cから制御できるようになった。 まず、ch32v203と同様に、vm_config.hの設定は、以下のようにした。 #define MAX_VM_COUNT 1 #define MRBC_USE_FLOAT 0 #define MRBC_REQUIRE_32BIT_ALIGNMENT 最適化はsmallest+LTOとしてコンパイルすると、digital,adc,pwmを組込んだ状態で、ギリギリflashには収まるようになったが、mrb用の領域や今後の拡張も考えると、もう少し工夫したい。 そこで、昨日のブログに書いたように、同時に一つのmrbしか動かさないことにして、rrt0をいじってみた。 rrt0.hは、MRBC_TASK_NAME_LENとmrbc_tcbとmrbc_initの部分だけを残した。 rrt0.cは、c_sleepやc_sleep_msからはarduinoのdelayを呼び出すようにして、mrbc_initは以下のように最低限のコマンドだけにした。 void mrbc_init(void *heap_ptr, unsigned int size) { hal_init(); mrbc_init_alloc(heap_ptr, size); mrbc_init_global(); mrbc_init_class(); mrbc_define_method(0, 0, "sleep", c_sleep); mrbc_define_method(0, 0, "sleep_ms", c_sleep_ms); } そして、_autogen_class_rrt0.hは削除した。 mrbのコードを走らせるコマンドは、以下のコマンドの替わりに、mrbc_run_mrblibを用いた。 mrbc_create_task( MRB_CODE_ADRS, 0 ); mrbc_run(); これで、一つのタスクしか動かせなくなったが、3kほど容量に余裕ができた。 mrbのコードは、余っているflashに置くことになるのだが、Arduinoには組み込まないようにしたい。 また、ch32x035ではUSBからのプログラムの書き込みが出来るので、それを使いたい。 これらの要請を、どのようにしたら実現できるかを考えていたが、以下のようにすれば可能となることに気が付いた。 まず、mrbのコードはスケッチには組み込まずに、例えば以下のように指定して、コンパイルしたバイナリを出力する。 mrbc_run_mrblib( 0x8000000+57976 ); そして、そのbinファイルのバイトサイズを先の+以降に指定して、もう一度コンパイルする。 binのサイズが変っていないことを確認する。 もしbinのサイズが変ったら、変らなくなるまでこれを繰り返す。 この直後にmrbのコードを置けば、それが実行される仕組みである。 そのために、実行したいrubyスクリプトを用意して、mrbcで処理してできたmrbをbinファイルと結合する。 mrbc test.rb cat ch32.ino.CH32X035G8U.bin test.mrb >test.bin これをflashに書き込めば良いのである。 USBの書き込みは、wchispを用いたが、最初はverifyに失敗して苦労したが、何度も書き込んだらうまく行った。 ch32x035ボードを使ったのだが、書き込みモードにするためにBOOTボタンを押しながらUSBに接続して、すぐに以下のコマンドを実行する。
Read more...