CS/System Programming

File IO (2): System Call

dawonny 2022. 3. 20. 21:16
728x90
반응형
Linux File System 

리눅스 커널은 몇 가지로 모듈화 되어 있음

가장 중요한 것은 disk 안에 있는 파일을 관리 한다는 것

파일에 관련된 인터페이스를 유저에게 제공하는 system call API를 제공

유저는 이 system call API를 통해 커널에 접근 가능

그리고 커널은 자신이 관리하는 구조에 의해서 파일에 대한 쓰기 읽기/접근 권한/삭제/생성 을 관리한다.

 

-  파일 시스템 안의 각각의 파일들은 inode 를 가진다.

- inode 는 파일에 대한 정보를 관리하는 자료구조이다.

- 일반적으로 파일 시스템은 파일의 데이터 영역(실제 파일이 적혀 있는)과 파일 정보를 관리하는 영역(Metadata)으로 나뉨. Metadata 중 하나가 inode

- inode contents (C struct)

• file name • file type (regular, directory,...)

• file owner id

• 접근권한

      rwxr-xr-x (for owner, group, others)

• 접근한 시간, 생성시간, 수정시간

• file size

• file data block addr. table (see the next page!) -> 실제로 파일 데이터가 disk의 어디에 적혀있는지

• ..


Inode structure example

disk I/O를 할 때에는 block 단위 개념으로 데이터를 주고 받음

block size는 512byte, 1kb, 2kb, 4kb 그정도 크기

요즘은 대부분 block 크기는 4kb 임. 

 

block 의 address 를 파일마다 할당해줌 -> 그럼 할당된 block number 가 있을 텐데 이걸 inode 에 적어주는 것임.

inode 의 첫번째에 정보들이 있고, 할당된 block number 를 관리하는 table이 있음

 


Linux File System (2)

 

 File types

   • regular file <- 대부분 파일은 이거임

   • directory file

   • FIFO file (pipe)

   • special files (IO devices)

   • symbolic link files

 

 

 

 Directory file

   디렉토리를 파일의 형태로 나타내는 것임. 리눅스에서는 디렉토리도 하나의 파일로 관리를 한다. 

   • 디렉토리는 그 디렉토리가 가지고 있는 파일에 대한 inode #(number), 파일 이름과 같은 리스트 정보를 가지는 파일이다.

   • inode is a data structure which contains all the information about the file and file data blocks

   • inode # is a unique file id number in the file system

   • “ls –al john” is a shell command that just displays the “john” directory file

 


Linux File Types

 Ordinary File (Regular File)

  • 텍스트, 이미지, 비디오, 실행파일, 오디오파일 - binary files

 

 Directory File

  • 자신이 가진 파일에 대한 정보(the set of (file-name, inode #))를 담고 있음

 

Special File은 두 가지

IO 디바이스에 대한 IO연산을 도와주는 기능 제공

시스템에 연결된 각종 IO 장치에 user 가 접근하도록 만들어주기 위해 file 형태의 구조체를 통해서 장치에 접근할 수 있는 통로를 만들어 주는 파일

 Character Special File

   • Character-oriented device에 대한 접근을 할 수 있도록 해줌 (e.g. Keyboard //character 형태로 된 디바이스) 

 

 Block Special File

  • Block-oriented device에 대한 접근을 할 수 있도록 해줌(e.g. HDD file systems, eth0 )

 

 FIFO file

    파이프 형태, 프로세스간 데이터를 주고받기 위한 통로

   • Named pipe / Unnamed pipe cf. pipe in a process is usually unnamed.

 

 Symbolic link file

   다른 파일에 대해서 우회로 접근할 수 있는 경로를 만들어주는 파일

   • a file which points to another file cf. hardlink is NOT a file.


​File Descriptor

 커널에서 파일을 handle 하기 위해 파일에 할당해준 a small, non-negative integer

   inode 는 파일 시스템(매체)에서 파일을 구분하기 위한 정보를 쓰는 것

   실제 그것이 커널에서 사용될때에는 inode 의 정보가 쓰이는 것이 아니고 file descriptor 라고 하는 정보로 파일을 커널 내부에서 사용. 반환값이라고 하는게 file descriptor 라고 하는 것.

   • Traditionally, stdin(표준 입력), stdout(표준 출력) and stderr(표준 에러) are 0, 1 and 2 respectively.

   • Relying on “magic numbers” is BAD. – Use STDIN_FILENO, STDOUT_FILENO and STDERR_FILENO defined in or stdin, stdout, and stderr defined in .

 

 

 Maximum number of files

   • 프로세스는 1024개의 파일을 열 수 있다.

   • we can check the system resource configuration.

 

 

 

 

 

 

 


Basic File I/Os

 가장 기본이 되는 유닉스/리눅스 파일 I/Os 5가지

   • open(2)

   • close(2)

   • lseek(2)

   • read(2)

   • write(2)


File open
#include <fcntl.h>
int open(const char *path, int oflag);
int open(const char *path, int oflag, mode_t mode)

 parameters

   • path: 열거나 생성할 파일의 이름

   • oflag: 파일 열기 옵션

   • mode: 접근권한 (at file creation)

 

 return

   • file descriptor if OK

   • 1 on error

 

 oflag options

   • must be one of these

option1 meaning defined
O_RDONLY 읽기 0
O_WRONLY 쓰기 1
O_RDWR 읽고 쓰기 2

• and can be OR’ed with any of these (by “|”)

option2 meaning
O_CREAT 파일이 존재하지 않으면 생성
O_EXCL used with O_CREAT, 이미 파일이 존재하면 에러 return
O_TRUNC 파일이 존재하면 empty(파일크기0)로 만들기
O_APPEND 파일의 마지막위치부터 쓰기
O_SYNC 파일을 I/O 할때 disk 동기화를 하기

File access modes


File close

커널 내부에서 메모리를 잡고있는 data structure 를 해제시켜줌.

열린 파일에 대해서 유저가 닫아줄 필요가 있음.

#include <unistd.h>
int close(int fd);

 parameters

   • fd: file descriptor

 

 return

   • 0 if OK

   • -1 on error


File open example


File creation
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
int creat(const char *path, mode_t mode)

 parameters

   • path : 파일 이름

   • mode : 접근 권한

 

 return

   • file descriptor if OK

   • -1 on error


File seeking
#include <sys/types.h>
#include <unistd.h>
off_t lseek(int fd, off_t offset, int whence);

 parameters

   • fd : file descriptor

   • offset : offset from the beginning to seek (move)

   • whence : SEEK_SET, SEEK_CUR, SEEK_END

 

 return

   • new offset value if OK

   • -1 on error


File reading

buffer 에서 데이터를 읽는다.

#include <unistd.h>
ssize_t read(int fd, void *buf, size_t nbyte)

 parameters

   • fd : file descriptor

   • buf : buffer address

   • nbyte : number of bytes to read

 

 return

   • number of bytes read successfully if OK

   • -1 on error


File writing

write 할 땐 buffer 에 data가 있어야 한다.

#include <unistd.h>
ssize_t write(int fd, const void *buf, size_t nbyte)

 parameters

   • fd : file descriptor

   • buf : buffer address

   • nbyte : number of bytes to write

 

 return

   • number of bytes written successfully if OK

   • -1 on error


File create/lseek example

File copy example (1)

File copy example (2)


File descriptors & File table

두 개의 프로세스(프로그램)에서 각각 파일에 대한 연산을 한다고 했을 경우 각각의 프로세스에서는 file descriptor를 관리한다

각가의 파일에 대해서 운영체제 레벨(OS level)에서는 어떤 파일의 descriptor 가 생성되었는지를 global하게 파일 table을 관리한다. 그래서 각각의 프로세스는 해당되는 file descriptor에 접근할 수 있게 되고 

실제적으로 이 데이터는 파일 시스템에서 관리가 되고 

파일 시스템에 있는 inode 라고 하는 객체를 통해서 실제 데이터를 매체로 쓰도록 되어 있다.

이 통로는 파일 테이블에 있는 각각 파일 객체의 v-node pointer을 통해 파일 시스템에 있는실제 파일에 대해서 접근할수 있게 됨. 그리고 inode 정보를 통해 실제 파일의 데이터 block, 정보에 접근할 수 있다.


Duplication of file descriptor (1)

동일한 파일에 대해서 동일하게 접근하는 중복된 file descriptor를 만들 수 있다.

#include <unistd.h>
int dup(int fd);

 parameters

   • fd : file descriptor to duplicate

 

 return

   • newly duplicated file descriptor if OK

   • -1 on error


dup과 동일한 기능을 하지만, 기존에 생성된 file descriptor 에 대해서 복제된 또다른 파일 지정자를 argument로 만들어냄.

#include <unistd.h>
int dup2(int fd1, int fd2);

 parameters

   • fd1 : source file descriptor

   • fd2 : destination file descriptor

 

 return

   • copied file descriptor (should be same as fd2) if OK

   • -1 on error

 

 note

   • functionally same as dup except that dup2 designates destination file descriptor (fd2) the user wants


I/O redirection example (1)

I/O redirection example (2)

화면에는 Hello, world! !(1) 이랑 (3)이 출력되고

(2)는 test.txt 라는 파일에 기록이 됨.


Link (1)

 Symbolic link

   • soft link 라고도 불림

   • 원본 파일에 대해서 그 파일 이름에 link함. 파일에는 타겟으로 하는 파일의 path가 기록됨.

     파일에 대한 실제적인 내용을 가지고 있는 것은 아님.

   • 타겟 파일이 지워지면, 링크는 더이상 유효하지 않음, 하지만 symbolic link 파일은 여전히 존재.

 

 Hard link

   • 존재하는 inode를 가리키는 link. 실제 파일 시스템 정보를 가짐.

   • an inode can be shared by two or more filenames (hardlinks)

   • 파일이 업데이트 되면, 업데이트 된 것을 모든 hard link 파일에서 볼 수 있음

   • 파일이 삭제되더라도, hard link가 남아있기 때문에 또 다른 hard link를 통해 파일의 접근할 수 있다. 


Link (2)

 Linux command

   • symbolic link:

      $ ln –s original_file symbolic_link

   • hard link:

      $ ln original_file hard_link_name


Hard link
#include <unistd.h>
int link(const char *existing, const char *new_link);

 parameters

   • existing : original file name

   • new_link : new link name which will share the inode of existing file

 

 return

   • 0 if OK

   • -1 on error


File permission attributes


Process’s Creator (1)
#include <sys/types.h>
#include <unistd.h>
uid_t getuid(void) // process creator’s uid

 return

   • user ID of the process if OK

   • -1 on error

#include <sys/types.h>
#include <unistd.h>
uid_t getgid(void) // process creator’s gid

 return

   • group ID of the process if OK

   • -1 on error

 

uid_t geteuid(void)

 return

   • effective user ID of the process if OK

   • -1 on error  note

   • process’s effective user id is used as a key for a kernel’s protection system, and normally uid = euid,

   • but sometimes euid is a different one from uid for the dynamic protection system,

uid_t getegid(void)

 return

   • effective group ID of the process if OK

   • -1 on error


File’s ID

 When a process is created, the user(creator)’s IDs are assigned to the process.

 

 But, in the following cases, a process’s effective IDs are set to a file owner’s IDs

   • if we run a program file with S_ISUID (or S_ISGID) bit, the process’s UID is not my UID, but the file owner’s UID (or S_ISGID).

 

 How to set the bits (example)

   $ chmod u+s a.out

   $ chmod g+s a.out

 

 Example

$ ls –al /bin
-rwsr-xr-x 1 root root 26492 Dec 1 2017 moun

   • this mount command is executed, the mount process’s UID is set to root, not the user.

-> i.e. with the root’s authority, the mount will be run!


Sticky bit: S_ISVTX

 In a directory with sticky bit

   • 유저는 그들만의 파일이나 directory에 대한 subdirectory를 만들 수 있다.

   • but, each file can be deleted only by its owner or supervisor.

 

 Example

   자신이 생성하지 않은 파일은 지울 수 없음.


File access of a process

 File access (read/write/execute) is allowed in the following cases

   • 만약 프로세스의 effective UID가 0인경우 (supervisor)

   •만약 프로세스의 effective UID가 파일의 소유자와 같을 경우, 그리고 소유자의 접근 권한 bit가 설정되어있는 경우

   • 만약 프로세스의 effective UID가 파일의 소유자와 같을 경우, 그리고 그룹의 접근 권한 bit가 설정되어 있는 경우

   • 만약 접근권한이 누구든지 사용할 수 있도록 설정되어 있는 경우


File’s access permission
#include<unistd.h>
int access(const char *path, int amode);

 프로세스가 path 에 있는 파일에 접근할 수 있는지 체크

 

 parameter

   • path : path 이름

   • amode : 체크하고 싶은 접근 모드가 무엇인지

 return

   • 0 if OK

   • -1 on error


Permission check example


Default permission change
#include<sys/types.h>
#include<sys/stat.h>
mode_t umask(mode_t cmask);

 By default

   • 디폴트로, 파일의 permission 은 0666 (rw-rw-rw) 로 설정됨

   • 디폴트로, directory의 permission 은 0777 (rwxrwxrwx) 로 설정됨

 

 umask() changes the default permission

   • set unmask which masks off (i.e. not permits)

   • e.g. if umask is 0022, a new file permission is set to 0644

 

 parameter

   • cmask : new umask

 

 return

   • previous umask


umask value

 OR’ed combination of these modes mode meaning


File permission change
#include<sys/types.h>
#include<sys/stat.h>
int chmod(const char *path, mode_t mode);
int fchmod(int fd, mode_t mode);

 파일의 권한 모드를 바꾸기

   • 파일의 owner나 supervisor(root)가 이것을 할 수 있음

 

 parameters

• path : 파일의 path 이름

• 바꿀 새로운 접근권한 - 모드는 또한 접근 모드의 OR'ed combination이다(see previous)

• fd : file descriptor

 

 return

   • 0 if OK, -1 on error


Permission change example (1)


Ownership change
#include <unistd.h>
#include <sys/types.h>
int chown(const char *path, uid_t owner, gid_t group);
int lchown(const char *path, uid_t owner, gid_t group); 
// doesn’t follow links
int fchown(int fd, uid_t owner, gid_t group);

 parameters

   • path : 파일의 path 이름

   • owner : owner의 UID

   • group : group의 GID

   • fd : file descriptor

 

 return

   • 0 if OK, -1 on error

 


Ownership change example (1)


Hard link example


Symbolic link
#include <unistd.h>
int symlink(const char *existing, const char *link_name);

 parameters

   • existing : 기존의 파일 이름

   • link_name : 존재하는 파일을 가리키는 link의 이름

 

 return

   • 0 if OK

   • -1 on error

 


Symbolic link example

 “mylink” 파일의 포함하는 것은 무엇인가?

   • “myfile” -> 따라서 파일의 크기는 6 bytes.


system calls and symbolic links


Following a link (1)
#include <unistd.h>
int readlink(const char *path, void *buf, size_t bufsize);

 parameters

   • path : link 이름

   • buf : buffer의 주소 (기존 파일 이름)

   • bufsize : buffer의 크기

 

 return

   • number of bytes read if OK

   • -1 on error


Following a link example (1)


File information retrieval (1)

파일에 대한 여러가지 정보를 가져올 수 있는 system call

#include<sys/types.h>
#include<sys/stat.h>
#include<unistd.h>
int stat(const char *path, struct stat *buf);

 parameters

   • path : 파일 path 이름

   • buf : (파일의 정보를 포함한) struct stat의 주소

 

 return

   • 0 if OK

   • -1 on error

 

int lstat(const char *path, struct stat *buf);

 기본적으로 stat()와 같다, 하지만

   • 파일이 symbolic link인 경우, 링크가 원본파일이 아닌 링크파일 자체에 대한 정보를 받아옴

 

 parameters

   • path : 파일 path 이름

   • buf : (파일의 정보를 포함한) struct stat의 주소

 

 return

   • 0 if OK

   • -1 on error

int fstat(int fd, struct stat *buf)

 parameters

   • fd : file descriptor

   • buf : (파일의 정보를 포함한) struct stat의 주소

 

 return

   • 0 if OK

   • -1 on error


struct stat fields


Macros for struct stat

File stat example 

 

728x90
반응형