iget (2)
メモリiノードの確保という文書によると iget は疑似コード的に表現すると以下らしい
iget(iノード番号) if(上記iノードキャッシュ内に目的のiノードが見つかった) return 見つかったiノード iノード番号に対応するメモリiノードを作成する(get_new_inode関数) return 新規に作成したiノード
との事。おそらくこの文書は相当古いものではないか、と判断。
ちょっと 2.6.20 方面をざくざくっと掘っておいてメモだけ残します。
iget
include/linux/fs.h にて以下な定義
static inline struct inode *iget(struct super_block *sb, unsigned long ino) { struct inode *inode = iget_locked(sb, ino); if (inode && (inode->i_state & I_NEW)) { sb->s_op->read_inode(inode); unlock_new_inode(inode); } return inode; }
引数は struct super_block なオブジェクトと i ノード番号な模様。
iget_locked
定義は fs/inode.c で以下
struct inode *iget_locked(struct super_block *sb, unsigned long ino) { struct hlist_head *head = inode_hashtable + hash(sb, ino); struct inode *inode; inode = ifind_fast(sb, head, ino); if (inode) return inode; /* * get_new_inode_fast() will do the right thing, re-trying the search * in case it had to block at any point. */ return get_new_inode_fast(sb, head, ino); } EXPORT_SYMBOL(iget_locked);
なんとなくキャッシュから探して云々な処理に見える。ええと hash は fs/inode.c の以下なのかなぁ。
static unsigned long hash(struct super_block *sb, unsigned long hashval) { unsigned long tmp; tmp = (hashval * (unsigned long)sb) ^ (GOLDEN_RATIO_PRIME + hashval) / L1_CACHE_BYTES; tmp = tmp ^ ((tmp ^ GOLDEN_RATIO_PRIME) >> I_HASHBITS); return tmp & I_HASHMASK; }
あるいは ifind_fast も fs/inode.c にて定義。
static struct inode *ifind_fast(struct super_block *sb, struct hlist_head *head, unsigned long ino) { struct inode *inode; spin_lock(&inode_lock); inode = find_inode_fast(sb, head, ino); if (inode) { __iget(inode); spin_unlock(&inode_lock); wait_on_inode(inode); return inode; } spin_unlock(&inode_lock); return NULL; }
もう少しゆっくり検討する時間が欲しいなぁ。なんとなくざくっと意味は分かる気がするんですが、先に引用した疑似コードの意図と何となく合致はしているか。
ちょっと追記
struct inode 型の i_state 属性。include/linux/fs.h にてフラグが定義されている模様。
/* Inode state bits. Protected by inode_lock. */ #define I_DIRTY_SYNC 1 /* Not dirty enough for O_DATASYNC */ #define I_DIRTY_DATASYNC 2 /* Data-related inode changes pending */ #define I_DIRTY_PAGES 4 /* Data-related inode changes pending */ #define __I_LOCK 3 #define I_LOCK (1 << __I_LOCK) #define I_FREEING 16 #define I_CLEAR 32 #define I_NEW 64 #define I_WILL_FREE 128 #define I_DIRTY (I_DIRTY_SYNC | I_DIRTY_DATASYNC | I_DIRTY_PAGES)
struct inodeな LKHJ に記述あり。そろそろ寝ます。