어떤 파일이 현재 다른 프로세스에 의해 사용중인지 아닌지 알아내려면 어떻게 해야 할까.
단순히 fopen해보고 NULL을 반환하지 않으면 된다고 생각했지만
그게 아니었다. -_- 상당한 삽질을 필요로 했는데,
다른 프로세스에서 작업 중인 파일이라도, fopen이나, fstream.open, 은 모두 가능하다.
이런경우는 c/c++ 언어 자체에서 지원하지는 않고, 사용하고 있는 OS의 라이브러리 또는 api의 힘을 빌려야 한다.
구글세상에 나와있는 정보중 window의 정보는 많지만, (게다가 친절하게 ms에서 관련 msdn까지 제공해준다..특히 C# ㅠㅠ)
리눅스에서 어찌해야할지 삽질을 상당히 해야 했다. ㅠㅠ
결국 찾은 system call을 찾았는데
바로
open(), fcntl() 이다.
linux man page를 보면 알겠지만 이것의 헤더들은
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <errno.h>
#include <unistd.h>
이고
open()으로 file descriptor을 얻어준후,
fcntl 을 이용해 현재 파일의 Locking상태를 알 수 있다 .
fcntl은 이 자세히 설명된 싸이트
http://linux.about.com/library/cmd/blcmdl2_fcntl.htm
에 보면 나와있다 .
fcntl은 이미 열려있는 파일의 파일 특성 제어를 위해 사용되는데 원형을 보면
int fcntl(int fd, int cmd); int fcntl(int fd, int cmd, long arg); int fcntl(int fd, int cmd, struct flock *lock);
이다.
fd는 앞서 생한한 descriptor, cmd는 1차 옵션, flock * lock는 2차 옵션인데
각각 command의 목록 을 보려면 man page들을 찾아보면 된다..
간단한 코드를 보면,
#include <sys/types.h> #include <sys/stat.h> #include <fcntl.h> #include <stdio.h> #include <errno.h> #include <unistd.h> #include <iostream> using namespace std; int main(int argc, char ** argv) { int fd = open(argv[1], O_RDONLY); if (fd < 0) { perror("open"); return 1; } if (fcntl(fd, F_SETLEASE, F_WRLCK) && EAGAIN == errno) { puts("file is used. "); } else { fcntl(fd, F_SETLEASE, F_UNLCK); puts("file is free. "); } close(fd); return 0; }
이렇게 할 수 있다.
fcntl의 2번째 인자, F_SETLEASE는
File을 Write or Read 할 수 있는 권한을 lease해 오는 것을 의미하는것 같다(?)
lock 로 F_WRLCK는 쓰는 권한을 가져 오는데 이 방법으로 이 파일이 다른 프로세스에 의해 작업중인지 알 있다.
이것 알아두면 꽤나 유용할 듯 하다.
*cf)
물론 C코드가 아니라 Shell상에서 알아보려면
root> fuser filename
하면 된다.
'Programming' 카테고리의 다른 글
리눅스 C 에서 파일 다루기 (0) | 2012.05.03 |
---|---|
fopen 의 segmentation fault. (0) | 2012.05.03 |
visual studio 2010 path, library 관리 (0) | 2012.02.27 |
MFC 메세지 처리, MFC winsock 비동기 방식 (0) | 2011.12.01 |
float, double 소수점 아래 계산 오류 (0) | 2011.11.22 |