2010年6月24日木曜日

container_of

 

LinuxのDevice Driverを眺めていると、ちょくちょく見かけるマクロです。
使う機会も割と多いため、覚えて損は無いです。

私も忘れないように一応メモを。

 

定義場所は”$(kernel_dir)/include/linux/kernel.h”
(kernelはlinux-2.6.34を参照)

#define container_of(ptr, type, member) ({ \
        const typeof( ((type *)0)->member ) *__mptr = (ptr); \
        (type *)( (char *)__mptr – offsetof(type,member) );})

Cast a member of a structure out to the containing structure.
てことで、memberを入れると、それを持ってる変数のaddressを返してくれるです。

 

具体的には、

struct test_structure {
    struct sub_structure member;
};

struct test_structure parent;
struct sub_structure *child = &parent.member;

struct test_structure *test;
test = container_of(child, struct test_structure, member);

これでtestにはparentのアドレスが入るって動きです。

 

「”私(1)”は”○○構造体(2)”の”××っていうmember(3)”です!」と言えば、
親を探してくれるって感じで覚えてます。
# 数字は引数の順番

2010年6月14日月曜日

ticklessなkernel

 

ノートPCや組み込み用のkernelでよくよくお世話になる、
tickless(CONFIG_NOHZ)のお話です。

 

LinuxのKernelは、定期的なtimer割り込みによって、
schedulerの管理をしています。

その定期的なtimer割り込みの単位をtickっていう言い方をして、
tickを格納している変数がjiffiesです。

timer割り込みの間隔は、CONFIG_HZによって設定されていて、
100HZ, 250HZ, 1000HZから選べるようになっているはず。
(Targetによって違いがあるかも)

仮に100HZとなっていたら1秒間に100回、つまり10msに一回の
timer割り込みが入り、その度にtickがカウントされるという仕組み
になっています。

 

定期的に割り込み処理が入り、schedulerが呼ばれますから、
当然idleの時間は短くなってしまいます。
(何もしなくても、ね)

そうなると、消費電力を気にするモバイル機器にとっては、
邪魔者以外何物でもなくなります。

 

そこで登場したのがtickless。

tickless(CONFIG_NOHZ)では、timer割り込みは動作せず、
scheuleは他の割り込みから呼ばれることになります。

jiffiesも同じタイミングでカウントされる為、定期的なカウントアップはしませんが、
時間管理として使用できるようにきちんと補正しています。

そーすることで、定期的に起こる無駄な処理を省き、idle時間を長くすることで、
消費電力を抑えることができます。

 

っとまぁ、こんな感じのものです。

自分で選んで使用してる癖に、度忘れしてしまっていたので、
思い出しながら書いてみました。