linux-4.4.1/container_of()
をテンプレートにして作成
[
トップ
] [
新規
|
一覧
|
検索
|
最終更新
|
ヘルプ
|
ログイン
]
開始行:
*参照元 [#l4abc1ba]
#backlinks
*説明 [#f407ef63]
-パス: [[linux-4.4.1/include/linux/kernel.h]]
-ポインタが指す構造体のメンバ、それを含む構造体へのポイン...
--例えば、
struct example {
int mem_a;
char mem_b;
};
struct example hoge;
--という構造体があったとする。
int *mem_ptr = &hoge.mem_a;
--上記のような、構造体のメンバへのポインタ mem_ptr しか
分からない状態から hoge へのポインタを得たいときに contai...
使う。
struct example *ptr = container_of(mem_ptr, struct examp...
--すると ptr が指す先(hoge.mem_a)を含む構造体への
ポインタ(&hoge)が得られる。
**引数 [#l7a91094]
-ptr
--構造体のメンバへのポインタを指定する。
-type
--ptr に指定したポインタが指すメンバ、これを含む「構造体...
マクロはここで指定した型のポインタを返す。
---上記の例で言うと変数名の hoge ではなくて、変数の型の
名前 struct example を指定する。
-member
--ptr に指定したポインタが指す「メンバ名」を指定する。
--type に指定した型は member に指定した名前のメンバを持っ...
---上記の例で言うとポインタ変数 mem_ptr ではなくて、
struct example 構造体のメンバ名である mem_a を指定する。
**返り値 [#yc282494]
-type *
--指定した構造体のメンバへのポインタ(ptr に指定する)が...
(メンバの名前は member に指定する)、
これを含む構造体(構造体の型は type に指定する)へのポイ...
--例えば list_entry(a, struct hogehoge, b) とすれば、stru...
**参考 [#j69a398a]
*実装 [#s25eb86e]
/**
* container_of - cast a member of a structure out to th...
* @ptr: the pointer to the member.
* @type: the type of the container struct this is...
* @member: the name of the member within the struct.
*
*/
#define container_of(ptr, type, member) ({ ...
const typeof( ((type *)0)->member ) *__mptr = (p...
-member の型のポインタ __mptr を宣言し、ptr の値を代入す...
--一見すると変なキャストであるが、
typeof( ((type *)0)->member )
は member の型を取得するための細工である。
---type 型のポインタにキャストした null ポインタと、
参照剥がしを使って member を参照する。
---typeof は gcc の拡張構文で、指定した変数の型を返す。
--わざわざ member の型のポインタにキャストする理由
---ポインタを計算するだけなら (char *) へのキャストで計算...
一旦 member の型のポインタにキャストして、
コンパイル時に型チェックをしていると思われる。
---これにより ptr に member と異なる型のポインタを渡して...
異常なポインタを参照してしまうバグを防いでいる。
例:
struct st_a {
int a;
long b;
int c;
} var_a;
正しい場合
int *ptr = &var_a.a;
container_of(ptr, struct st_a, a);
a と b を間違えた場合
long *ptr = &var_a.b;
container_of(ptr, struct st_a, a);
検出可能
a と c を間違えた場合
int *ptr = &var_a.c;
container_of(ptr, struct st_a, a);
検出不可能
(type *)( (char *)__mptr - offsetof(type,member)...
-構造体の先頭へのポインタを計算する。この値がマクロの戻り...
--member を指すポインタから、メンバーのオフセットを引く。
メンバーのオフセットは構造体の先頭から、メンバーまでの距...
メンバーのポインタから引いてやれば、構造体の先頭を指すポ...
return -> ---- ----
mem_a |
---- | offset
mem_b ___|
---- <- __mptr
mem_c
----
---offsetof マクロは構造体のメンバー(member)が構造体(t...
どの位置にいるか(オフセット)をバイト数で返す。
---拡張構文ではなく C の標準的なマクロで、stddef.h で定義...
manpage offsetof(3) などを参照のこと。
*コメント [#sdf40253]
終了行:
*参照元 [#l4abc1ba]
#backlinks
*説明 [#f407ef63]
-パス: [[linux-4.4.1/include/linux/kernel.h]]
-ポインタが指す構造体のメンバ、それを含む構造体へのポイン...
--例えば、
struct example {
int mem_a;
char mem_b;
};
struct example hoge;
--という構造体があったとする。
int *mem_ptr = &hoge.mem_a;
--上記のような、構造体のメンバへのポインタ mem_ptr しか
分からない状態から hoge へのポインタを得たいときに contai...
使う。
struct example *ptr = container_of(mem_ptr, struct examp...
--すると ptr が指す先(hoge.mem_a)を含む構造体への
ポインタ(&hoge)が得られる。
**引数 [#l7a91094]
-ptr
--構造体のメンバへのポインタを指定する。
-type
--ptr に指定したポインタが指すメンバ、これを含む「構造体...
マクロはここで指定した型のポインタを返す。
---上記の例で言うと変数名の hoge ではなくて、変数の型の
名前 struct example を指定する。
-member
--ptr に指定したポインタが指す「メンバ名」を指定する。
--type に指定した型は member に指定した名前のメンバを持っ...
---上記の例で言うとポインタ変数 mem_ptr ではなくて、
struct example 構造体のメンバ名である mem_a を指定する。
**返り値 [#yc282494]
-type *
--指定した構造体のメンバへのポインタ(ptr に指定する)が...
(メンバの名前は member に指定する)、
これを含む構造体(構造体の型は type に指定する)へのポイ...
--例えば list_entry(a, struct hogehoge, b) とすれば、stru...
**参考 [#j69a398a]
*実装 [#s25eb86e]
/**
* container_of - cast a member of a structure out to th...
* @ptr: the pointer to the member.
* @type: the type of the container struct this is...
* @member: the name of the member within the struct.
*
*/
#define container_of(ptr, type, member) ({ ...
const typeof( ((type *)0)->member ) *__mptr = (p...
-member の型のポインタ __mptr を宣言し、ptr の値を代入す...
--一見すると変なキャストであるが、
typeof( ((type *)0)->member )
は member の型を取得するための細工である。
---type 型のポインタにキャストした null ポインタと、
参照剥がしを使って member を参照する。
---typeof は gcc の拡張構文で、指定した変数の型を返す。
--わざわざ member の型のポインタにキャストする理由
---ポインタを計算するだけなら (char *) へのキャストで計算...
一旦 member の型のポインタにキャストして、
コンパイル時に型チェックをしていると思われる。
---これにより ptr に member と異なる型のポインタを渡して...
異常なポインタを参照してしまうバグを防いでいる。
例:
struct st_a {
int a;
long b;
int c;
} var_a;
正しい場合
int *ptr = &var_a.a;
container_of(ptr, struct st_a, a);
a と b を間違えた場合
long *ptr = &var_a.b;
container_of(ptr, struct st_a, a);
検出可能
a と c を間違えた場合
int *ptr = &var_a.c;
container_of(ptr, struct st_a, a);
検出不可能
(type *)( (char *)__mptr - offsetof(type,member)...
-構造体の先頭へのポインタを計算する。この値がマクロの戻り...
--member を指すポインタから、メンバーのオフセットを引く。
メンバーのオフセットは構造体の先頭から、メンバーまでの距...
メンバーのポインタから引いてやれば、構造体の先頭を指すポ...
return -> ---- ----
mem_a |
---- | offset
mem_b ___|
---- <- __mptr
mem_c
----
---offsetof マクロは構造体のメンバー(member)が構造体(t...
どの位置にいるか(オフセット)をバイト数で返す。
---拡張構文ではなく C の標準的なマクロで、stddef.h で定義...
manpage offsetof(3) などを参照のこと。
*コメント [#sdf40253]
ページ名: