mojo's Blog
Files and Directories 본문
Concepts
File :
- byte 들의 단순한 선형적인 array로 정의된다.
- inode number 로서 low-level 이름을 각 파일마다 가지고 있다.
Directory :
- 디렉토리도 파일이다.
- A list of <user-readable filename, low-level filename> pairs.
Interface : Creating a file
O_CREAT flag을 사용하여 open system을 사용한다.
int fd = open("foo", O_CREAT | O_WRONLY | O_TRUNC, S_IRUSR | S_IWUSR);
O_CREAT : 파일을 생성
O_WRONLY : 파일이 열릴 때, 오직 write 만을 허용
O_TRUNC : 파일 사이즈를 0으로 만듬 (그러나 기존에 있던 내용물이 제거됨)
Interface : Reading and Writing Files
1. open() 을 함으로써 "foo" 파일을 연다. (이때 return 값은 3)
file descriptor는 3부터 시작함. (0, 1, 2는 stdin, stdout, stderror로 구성됨)
2. fd = 3 에다가 4Kb 만큼 "hello\n" 을 읽는다. (이때 반환값은 읽어드린 byte의 수)
3. fd = 1(stdout) 에다가 "hello\n" 를 읽어드린 byte의 수만큼 콘솔창에 출력한다.
OFFSET
읽거나 쓰기 위한 파일의 위치를 의미한다. (4096 byte씩 즉, 4Kb 만큼 읽음)
파일이 열릴 때, "offset" 이 할당된다.
read하고 write할 때 offset이 update된다.
lseek 함수의 세번째 argument 는 다음과 같이 세가지로 들어 올 수 있다.
(1) SEEK_SET : position(offset) update 가 가능하다.
(2) SEEK_CUR : 현재 position에 offset byte 만큼 더해준다.
(3) SEEK_END : 파일 사이즈를 offset byte 만큼 더해준다.
abstractions
ftable 에서 각 process의 fd(file descriptor)를 링킹하는 형태로 볼 수 있다.
위 예제를 살펴보면 read를 계속하다가 return 값이 0이라는 것은 즉, 더이상 읽을 수 있는 content 가 없음을
의미하므로 offset = 300 에서 모든 read, write 가 완료된 상태이다.
Sample traces
lseek 함수에서는 SEEK_SET argument 를 사용함으로써 초기 offset을 0이 아닌 200으로 변경하고 read 한다.
fork() and dup()
fork() : parent process의 file descriptor 가 복제된다.
즉, 동일하게 ftable을 point하고 그에 따른 ftable의 reference count 가 1에서 2로 증가됨 (2개의 링킹)
dup() : 위 코드에서 동일한 프로세스 내에서 dup(fd) 함수를 호출함으로써 얻은 fd2는 fd가 point 하고 있는 ftable
을 fd2도 동일하게 해당 ftable을 point 함으로써 즉, fd에 대한 복제라고 보면 된다.
fsync()
persistency
- write() : buffer에 data를 작성한 후에 storage 에 저장하는 과정을 거친다.
- 몇가지 application 에 대해서 더 많은 eventual gurantee를 필요오 한다. (DBMS)
fsync() : buffer에 작성하였던 contents 에 대하여 즉시 disk에 작성하도록 하는 함수이다.
즉, 메모리 버퍼에 쓰고 디스크에 쓸때의 시간의 gap이 존재한다.
위 코드로 1,2번 라인에서 buffer(memory)에 write 하고 3번 라인은 disk에 즉시 작성함으로써 persistency
보장을 가능하게 한다. (durablity 제공)
그리고 이러한 함수 fsync() 에 대해서 directory에서도 또한 필요로 한다.
Renaming Files
rename() : file의 이름을 다른 이름으로 변경시켜주는 함수이다.
- atomic한 call로 구현되어 있다.
- 예를 들어서 foo를 bar로 변경할 때 "mv foo bar" 와 같다.
만약에 4번 라인 close() 에서 프로그램이 죽어버리면?
=> 파일은 없고 temp라는 파일에 저장이 되는 경우가 발생! (기본 파일 이름이 temp인가 보다)
Getting Information About Files
stat() : 파일의 metadata를 알려줌
Removing Files
strace 를 사용하여 rm이 어떻게 돌아가는지에 대한 것을 확인해 보도록 하자.
rm 은 unlink("file 명") 를 호출함으로써 file을 제거하는 역할을 하는 것을 알 수 있다.
Making Directories
mkdir() : directory 를 만드는 함수이다.
- directory를 생성할 경우 비어있다.
- 비어있는 directory는 두가지 entry를 가지고 있다 : . (itself), .. (parent)
0777는 permision으로 User(111) Group(111) Others(111) 을 의미하며 각 숫자별로
read : 1 write : 1 execute : 1 를 의미한다.
Reading Directories
readdir()
- Directory 는 파일이지만 파일과 다르게 특별한 구조를 가지고 있다.
- Directory를 읽을 때, file에서의 read()와 다르게 특별한 system call을 사용한다.
구조체 DIR *dp 를 read 함으로써 구조체 dirent *d 에 할당하는데 NULL이 아닐때까지 loop를 돌린다.
그리고 NULL 이 아닐 경우 directory entry 에 대해서 inode와 file name 을 출력하도록 한다. (ls와 동일)
Directory entry
rmdir() : directory를 지우는 것을 의미한다.
- 만약 rmdir() 함수를 호출할 때 비어있지 않은 directory라면 실패한다.
Hard Links
link() : 동일한 파일을 가르키게 한다. (동일한 컨텐츠를 갖게되는 것)
inode 가 동일해서 결국 file, file2 가 동일한 컨텐츠를 갖게 된다.
How to create hard link file?
Step 1 : inode 를 만들고 file에 대한 모든 정보를 track 한다.
Step 2 : file에 대한 human-readable name을 link 한다.
Step 3 : 현재 directory안에 file을 link 한다.
file에 대한 hard link를 생성한 후에 만들어진 새로운 파일에 대해서 차이점이 존재하지 않는다.
즉, file을 제거할 때 unlink() 를 호출하게 된다.
unlink()
- inode number의 reference count 를 먼저 체크한다.
- human-readable name과 inode number 사이의 link를 제거한다.
- reference count를 1 감소시킨다.
(이때 0이 될 경우 file 은 제거된다. => inode와 관련된 block들에 대해 free)
즉, file table에서 기존의 old 파일이 있다고 가정할 때 (inode를 가르키는),
inode가 지워지지 않으면(not free) 파일이 지워지지 않음.
Symbolic Links
source directory에 대한 path를 포함하는 특별한 file 이다.
Hard Link는 directory를 만들 수 없으며 다른 partition에 대한 file을 또한 만들 수 없다.
Symbolic Links의 문제점은 삭제하면 link를 끊게 함으로써 path가 붕괴될 수 있다.
즉, dangling reference 가 발생할 수 있음.
'학교에서 들은거 정리 > 운영체제' 카테고리의 다른 글
File system Implementation (1) | 2021.12.01 |
---|---|
Hard Disk Drives (0) | 2021.11.24 |
Semaphore and Common Concurrency Problem (0) | 2021.11.18 |
Conditional Variables (0) | 2021.11.12 |
Lock based Data Structure (0) | 2021.11.11 |