Linuxファイルロック
3978 ワード
システム呼び出しfcntl
#include
#include
int fcntl(int fd, int cmd, struct flock *lock );
パラメータ:
fd
:ファイル記述子cmd
:F_GETLK, F_SETLK or F_SETLKW lock
:下記の規則に従って記入して、相応の効果を達成することができるF_GETLK, F_SETLK and F_SETLKW are used to acquire, release, and test for the existence of record locks (also known as file-segment or file-region
locks). The third argument, lock, is a pointer to a structure that has at least the following fields (in unspecified order).
struct flock {
...
short l_type; /* Type of lock: F_RDLCK,
F_WRLCK, F_UNLCK */
short l_whence; /* How to interpret l_start:
SEEK_SET, SEEK_CUR, SEEK_END */
off_t l_start; /* Starting offset for lock */
off_t l_len; /* Number of bytes to lock */
pid_t l_pid; /* PID of process blocking our lock
(F_GETLK only) */
...
};
ファイルロックのカプセル化
filelock.h:
#ifndef _FILE_LOCK_H
#define _FILE_LOCK_H
int lock_reg(int fd, int cmd, int type, off_t offset, int whence, off_t len);
int File_ReadLck(int fd, off_t offset, int whence, off_t len);
int File_WriteLck(int fd, off_t offset, int whence, off_t len);
int File_ReadLckW(int fd, off_t offset, int whence, off_t len);
int File_WriteLckW(int fd, off_t offset, int whence, off_t len);
int File_Unlock(int fd, off_t offset, int whence, off_t len);
#endif
filelock.c:
#include
#include
#include
#include "filelock.h"
int lock_reg(int fd, int cmd, int type, off_t offset, int whence, off_t len)
{
struct flock lock;
lock.l_type = type;
lock.l_start = offset;
lock.l_whence = whence;
lock.l_len = len;
return (fcntl(fd, cmd, &lock));
}
int File_ReadLck(int fd, off_t offset, int whence, off_t len)
{
return lock_reg(fd, F_SETLK, F_RDLCK, offset, whence, len);
}
int File_WriteLck(int fd, off_t offset, int whence, off_t len)
{
return lock_reg(fd, F_SETLK, F_WRLCK, offset, whence, len);
}
int File_ReadLckW(int fd, off_t offset, int whence, off_t len)
{
return lock_reg(fd, F_SETLKW, F_RDLCK, offset, whence, len);
}
int File_WriteLckW(int fd, off_t offset, int whence, off_t len)
{
return lock_reg(fd, F_SETLKW, F_WRLCK, offset, whence, len);
}
int File_Unlock(int fd, off_t offset, int whence, off_t len)
{
return lock_reg(fd, F_SETLK, F_UNLCK, offset, whence, len);
}
ルーチン
#include
#include
#include "filelock.h"
int main(void)
{
int fd = 0;
pid_t pid = 0;
fd = open("tmp", O_RDWR|O_CREAT|O_TRUNC, 0666);
unlink("tmp");
pid = fork();
if(0 == pid)
{
while(1)
{
File_WriteLckW(fd, 0, SEEK_SET, 1);
printf("====> child process
");
usleep(5000000);
File_Unlock(fd, 0, SEEK_SET, 1);
usleep(500000);
}
}
while(1)
{
File_WriteLckW(fd, 0, SEEK_SET, 1);
printf("#### parent process
");
usleep(5000000);
File_Unlock(fd, 0, SEEK_SET, 1);
usleep(500000);
}
return 0;
}
ファイルロックの使用方法:
:空のファイルを作成し、ファイルの最初のバイト(存在する必要はありません)をロックバイトとして使用し、unlinkファイルを作成します.リソースを取得する前に、バイトの書き込みロックを取得します.リソースを解放すると、バイトはロック解除されます.レコード・ロックの利点の1つは、ロックを持つプロセスが終了して終了すると、カーネルが自動的にロックを解放するため、プロセス間でプロセスがクラッシュしてデッドロックになることはありません.