【水羊羹】雪だるま作戦に思いを馳せながら雑談するスレッド Part4
まぁともあれ,乙でした.root さんも何回もカーネルパッチ当てたり奔走してましたが,
とりあえず一休みでごゆっくりと......といっても本業か......
で,余談.NFS で虫を踏んでいたかも知れない操作を Solaris 上で実験してみたらこんな結果でした.
----------------------------------------
#include <errno.h>
#include <fcntl.h>
#include <stdio.h>
#include <unistd.h>
#include <sys/mman.h>
#include <sys/stat.h>
int main(int argc, char **argv)
{
static const char oldstr[] = "old\n", newstr[] = "new new\n";
int fd_c, fd_s;
char *buf;
struct stat st;
fd_s = open("/tmp/nfs_s/test", O_WRONLY|O_CREAT|O_TRUNC, 0666);
write(fd_s, oldstr, sizeof oldstr - 1);
close(fd_s);
fd_c = open("/tmp/nfs_c/test", O_RDONLY);
usleep(100000);
fd_s = open("/tmp/nfs_s/.test", O_WRONLY|O_CREAT|O_TRUNC, 0666);
write(fd_s, newstr, sizeof newstr - 1);
close(fd_s);
rename("/tmp/nfs_s/.test", "/tmp/nfs_s/test");
usleep(100000);
if (fstat(fd_c, &st)) {
perror("fstat");
return errno;
}
if ((buf = mmap(NULL, st.st_size, PROT_READ, MAP_SHARED, fd_c, 0)) == MAP_FAILED) {
perror("mmap");
return errno;
}
printf("%.*s", (int)st.st_size, buf);
return 0;
}
----------------------------------------
# share -orw=localhost /tmp/nfs_s
# mount -Fnfs nfs://localhost/tmp/nfs_s /tmp/nfs_c
# ./a.out
fstat: Bad file number
fstat() のところでEBADFですか。
つうか
>>663-664 ちょっとボケてましたね...... root のまま a.out 実行してて,
それだと NFS 経由では nobody 権限になってファイルが開けないから EBADF になってました.
改めてやったところ,mount 時にオプション指定なしだと printf() のところで SIGBUS でコケて,
noac オプション付きでやると fstat() が ESTALE という結果です.
この対策としては,ファイル更新時に別ファイル名で生成→rename()
というやり方ではなくロックを使うということのようですが,
ロックするとなると書き込み側の bbsd だけでやっても意味なくて,
読み出し側の httpd 等でもロックしてくれなきゃしょうがないんですよね......