[Suzaku:00591] Re: キャラクタデバイスのドライバーの作成
Yasushi SHOJI
email@hidden
2006年 7月 13日 (木) 17:41:35 JST
At Thu, 13 Jul 2006 17:11:19 +0900,
Abe wrote:
[...]
> f_posは「・・ユーザーがアクセスしているファイルの位置を示す・・」と
> ありましたので、seekで設定した値が反映されると思っていました。
> ではseekは意味が無いと言う事なんでしょうか。
カーネルの世界へようこそ。:-)
ユーザランドでは
fd = open("/path/to/file", ...);
lseek(fd, offset, SEEK_SET);
write(fd, buf, c);
とすることで、/path/to/fileの offset目からデータを書くことができます。
これは kernelが見せている虚像にすぎません。
kernel側から上記の挙動を見ると openではファイル名が渡され、lseekではシー
クするための値が渡され、writeではデータの入ったメモリ領域のアドレスと
バイト数が渡されるだけです。
kernelはそれぞれ渡されたデータをある場所に書いたり、読んだりという実際
の処理を行なわなければなりません。kernelには虚像を見せてくれる人はいな
いのです。
ですから「seekは意味が無い」ということではなく、「(必要であれば) seek
に意味を持たせなくてはならない」のです。
> それと、
> > *(volatile unsigned long *)ADDRESS = VALUE;
> >
> > と書くと ADDRESSで指定した値で address busがドライブされ、data busでは
> > VALUEの値がドライブされると思います。
> ですが、
> どのように関数の中に書けばよいのか分かりません。
仮に opb_emcがマップされているアドレスが 0xffffd000、書きたい値を 0x5a
としたとき
ssize_t s_write(struct file *filp, const char *buf, ssize_t count, loff_t *f_pos)
{
*(unsigned long *)0xffffd000 = 0x5a;
return 0;
}
としてはどうでしょうか?与えられるデータや、seekの有無に関わらず
0xffffd000に 0x5aが書かれるはずです。しかもユーザランドから見ると
write()システムコールは、なにも書かれなかったことを示す 0を返すはずで
す。
--
yashi
suzaku メーリングリストの案内