2012. 7. 13. 16:06


#include <stdio.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>

main()
{
   int fd1, fd2;

   /* jkim 파일을 읽기 전용으로 열기. 반환되는 양의 정수 값을 파일 식별자라 함 */
   fd1 = open("jkim", O_RDONLY);
   /* kang 파일을 쓰기 전용으로 열기 */
   fd2 = open("kang", O_WRONLY);
   /* 배정받은 파일 식별자를 출력 */
   printf("jkim's file descriptor: %d\nkang's file descriptor: %d\n", fd1, fd2);
   /* 파일 식별자를 이용해서 파일 닫음 */
   close(fd1);
   close(fd2);
}

---------------------------------------------------------------------------------------

#include <fcntl.h>
#include <unistd.h>
#define BUFFSIZE 1024

main()
{
   int fd1, fd2;
   ssize_t n;
   char buf[BUFFSIZE];

   /* jkim 파일을 읽기 전용으로 열기. fd1은 jkim을 의미 */
   fd1 = open("jkim", O_RDONLY);
   /* kang 파일을 쓰기 전용으로 열기. fd2는 kang을 의미 */
   fd2 = open("kang", O_WRONLY);
   /* fd1 파일에서 문자를 BUFFSIZE 크기만큼 읽어 buf에 저장.
      read 함수에서도 파일 식별자를 사용하고 반환값은 실제로 읽은 바이트 수 */
   n = read(fd1, buf, BUFFSIZE);
   /* buf에 있는 내용을 n바이트만큼 fd2 파일에 저장.
      write 함수에서도 파일 식별자를 사용 */
   write(fd2, buf, n);
   /* fd1 파일 닫기 */
   close(fd1);
   close(fd2);
}

---------------------------------------------------------------------------------------

#include <fcntl.h>

main()
{
   int fd;

   /* jkim 파일을 읽기 전용으로 열기.
     만약 호출에 실패하게 되면 -1이 반환되므로 if 조건이 참이 됨 */
   if ((fd = open("jkim", O_RDONLY)) == -1) {
      perror("open failed");
      exit(1);
   }
   /* fd 파일 닫기 */
   close(fd);
   exit(0);
}

---------------------------------------------------------------------------------------

#include <fcntl.h>

main()
{
   int fd;

   /* 현재 디렉토리에 jkim 파일이 있으면 읽기 전용으로 열고,
      없으면 현재 디렉토리에 0바이트 크기의 jkim을 생성하고 이를 연다.
      생성된 파일의 접근 권한 정보는 0644 */
   if ((fd = open("jkim", O_RDONLY | O_CREAT, 0644)) == -1) {
      perror("open failed");
      exit(1);
   }
   close(fd);
   exit(0);
}

---------------------------------------------------------------------------------------

#include <fcntl.h>

main()

   int fd;

   /* 현재 디렉토리에 jkim 파일이 있으면 open 함수 호출에 실패하여 -1을 반환하고
      만약 없다면 현재 디렉토리에 jkim을 생성하고 읽기 전용으로 연다. */
   if ((fd = open("jkim", O_RDONLY | O_CREAT | O_EXCL, 0644)) == -1) {
      perror("open failed");
      exit(1);
   }
   close(fd);
   exit(0);
}

---------------------------------------------------------------------------------------

#include <fcntl.h>

main()
{
   int fd;

   /* jkim 파일이 있으면 파일을 쓰기 전용으로 열어 0 바이트로 자르고,
     만약 없다면 0바이트 크기의 jkim을 생성하고 쓰기 전용으로 연다. */
   if ((fd = open("jkim", O_WRONLY | O_CREAT | O_TRUNC, 0644)) == -1) {
      perror("open failed");
      exit(1);
   }
   close(fd);
   exit(0);
}

---------------------------------------------------------------------------------------

#include <stdio.h>

main()
{
   /* FOPEN_MAX는 하나의 프로그램에서 동시에 열 수 있는 파일의 수를 의미 */
   printf("FOPEN_MAX : %d\n", FOPEN_MAX);
   exit(0);
}

---------------------------------------------------------------------------------------

#include <stdio.h>
#include <fcntl.h>
#include <unistd.h>
#define MAX 10

main()
{
   int fd;
   char buf1[MAX], buf2[MAX];

   /* alphabet 파일을 읽기 전용으로 열기 */
   if ((fd = open("alphabet", O_RDONLY)) == -1) {
      perror("open failed");
      exit(1);
   }
   /* fd 파일로부터 처음 MAX바이트 크기만큼의 문자를 읽어 buf1에 저장 */
   read(fd, buf1, MAX);
   /* fd 파일로부터 17라인에서 읽힌 다음으로부터 MAX바이트 크기만큼의
     문자를 읽어 buf2에 저장 */
   read(fd, buf2, MAX);
   printf("buf1[0]: %c\nbuf2[0]: %c\n", buf1[0], buf2[0]);
   close(fd);
   exit(0);
}

---------------------------------------------------------------------------------------

#include <stdio.h>
#include <fcntl.h>
#include <unistd.h>
#define MAX 100   /* buf의 크기를 나타내는 매크로 */

main()
{
   int fd, i;
   char buf[MAX];
   long int length = 0;

   if ((fd = open("jkim", O_RDONLY)) == -1) {
      perror("open failed");
      exit(1);
   }
   /* fd 파일의 크기를 계산하는 부분으로, read가 반환하는 값은
     실제 읽어 들인 데이터의 바이트 수이다. */
   while ((i=read(fd, buf, MAX)) > 0)
      length += i;
   printf("Total characters in jkim : %ld\n", length);
   close(fd);
   exit(0);
}

---------------------------------------------------------------------------------------

#include <fcntl.h>
#include <unistd.h>

main()
{
   int fd;
   char buf[20]="Linux C Programming";
  
   /* newfile이 있으면 쓰기 전용으로 열고, 없으면 newfile을 생성하여 염 */
   if ((fd=open("newfile", O_WRONLY | O_CREAT, 0644)) == -1) {
      perror("open failed");
      exit(1);
   }
   /* fd 파일에 buf에 있는 20바이트 데이터 쓰기 */
   if (write(fd, buf, 20) == -1) {
      perror("write failed");
      exit(1);
   }
   close(fd);
   exit(0);
}

---------------------------------------------------------------------------------------

뒤에 연결해서 씀

#include <fcntl.h>
#include <unistd.h>
#define MAX 1024

main(int argc, char *argv[])
{
   int fd1, fd2;
   int count;
   char buf[MAX];

   if (argc != 3) {
      perror("argc is not 3");
      exit(1);
   }
   if ((fd1=open(argv[1], O_RDONLY)) == -1) {
      perror("open failed");
      exit(1);
   }  
   /* O_APPEND 옵션을 추가하고 파일을 열면 읽기/쓰기 포인터가
     파일의 끝을 가리킴 */
   if ((fd2=open(argv[2], O_WRONLY | O_APPEND)) == -1) {
      perror("open failed");
      exit(1);
   }
   while ((count=read(fd1, buf, MAX)) > 0) {
      if (write(fd2, buf, count) != count) {
         perror("write failed");
         exit(1);
      }
   }
   close(fd1);
   close(fd2);
   exit(0);
}

---------------------------------------------------------------------------------------

#include <fcntl.h>
#include <unistd.h>
#define MAX 1024

main()
{
   int count;
   char buf[MAX];

   /* STDIN_FILENO는 표준 입력을 의미. 표준 입력은 키보드를 통해 이루어 짐 */
   while ((count=read(STDIN_FILENO, buf, MAX)) > 0) {
      /* STDOUT_FILENO는 표준 출력을 의미. 표준 출력은 모니터를 통해 이루어 짐 */
      if (write(STDOUT_FILENO, buf, count) != count) {
         perror("write failed");
         exit(1);
      }
   }
   exit(0);
}

---------------------------------------------------------------------------------------

파일을 복사하는 프로그램

#include <fcntl.h>
#include <unistd.h>
#define MAX 1024

main(int argc, char *argv[])
{
   int fd1, fd2;
   int count;
   char buf[MAX];
   /* 명령 라인의 인수가 3개가 아니면 오류 메시지를 출력하고 종료한다. */
   if (argc != 3) {
      perror("argc is not 3");
      exit(1);
   }
   /* argv[1] 파일을 읽기 전용으로 연다. 실행 예에서는 file1이 된다. */
   if ((fd1=open(argv[1], O_RDONLY)) == -1) {/
      perror("open failed");
      exit(1);
   }  
   if ((fd2=open(argv[2], O_WRONLY | O_CREAT, 0644)) == -1) {
      perror("open failed");
      exit(1);
   }
   /* fd1 파일로부터 MAX바이트만큼의 데이터를 읽어서 buf에 저장 */
   while ((count=read(fd1, buf, MAX)) > 0) {
      /* fd2 파일에 buf에 있는 count바이트만큼의 데이터 쓰기 */
      if (write(fd2, buf, count) != count) {
         perror("write failed");
         exit(1);
      }
   }
   close(fd1);
   close(fd2);
   exit(0);
}

---------------------------------------------------------------------------------------

#include <fcntl.h>
#include <unistd.h>
#define MAX 10

main()
{
   int fd;
   char buf[MAX]="C Program";

   /* jkim 파일이 있으면 쓰기 전용으로 열고 읽기/쓰기 포인터가 파일의 끝을 가리키고,
     만약 jkim 파일이 없으면 파일을 생성하고 쓰기 전용으로 연다. */
   if ((fd = open("jkim", O_WRONLY | O_CREAT | O_APPEND, 0644)) == -1) {
      perror("open failed");
      exit(1);
   }
   write(fd, buf, MAX);
   close(fd);
   exit(0);
}

---------------------------------------------------------------------------------------

#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <unistd.h>
#define MAX 1024

main(int argc, char *argv[])
{
   int fd1, fd2;
   int count;
   char buf[MAX];
   if (argc != 3) {
      perror("argc is not 3");
      exit(1);
   }
   if ((fd1=open(argv[1], O_RDONLY)) == -1) {
      perror("open failed");
      exit(1);
   }  
   /* argv[2] 파일을 생성하여 쓰기 전용으로 연다.
     생성된 파일의 접근 권한은 0644 */
   if ((fd2=creat(argv[2], 0644)) == -1) {
      perror("creat failed");
      exit(1);
   }
   while ((count=read(fd1, buf, MAX)) > 0) {
      if (write(fd2, buf, count) != count) {
         perror("write failed");
         exit(1);
      }
   }
   close(fd1);
   close(fd2);
   exit(0);
}

---------------------------------------------------------------------------------------

#include <fcntl.h>
#include <sys/types.h>
#include <unistd.h>
#define MAX 10

main()
{
    int fd, count;
    char buf[MAX];

    if ((fd = open("alphabet", O_RDONLY)) == -1) {
       perror("open failed");
       exit(1);
    }
    /* fd 파일의 읽기/쓰기 포인터를 첫 위치로부터 뒤로 5칸 이동 */
    lseek(fd, 5, SEEK_SET);
    count = read(fd, buf, MAX);
    /* 표준 출력 장치로 buf에 있는 count 바이트의 데이터를 출력 */
    write(STDOUT_FILENO, buf, count);
    close(fd);
    exit(0);
}

---------------------------------------------------------------------------------------

#include <fcntl.h>
#include <sys/types.h>
#include <unistd.h>

main(int argc, char *argv[])
{
    int fd;
    if ((fd = creat(argv[1], 0644)) == -1) {
       perror("creat failed");
       exit(1);
    }
    write(fd, "abcdefghijklmnopqrstuvwxyz", 26);
    /* 파일의 끝보다 더 뒤의 위치를 지정하는 것도 가능하며
      빈 공간은 NULL로 채워짐 */
    if (lseek(fd, 30, SEEK_SET) == -1) {
       perror("lseek failed");
       exit(1);
    }
    write(fd, "ABCD", 4);
    close(fd);
    exit(0);
}

---------------------------------------------------------------------------------------

#include <stdio.h>
#include <fcntl.h>
#include <sys/types.h>
#include <unistd.h>

main(int argc, char *argv[])
{
    int fd;
    off_t filesize;

    if ((fd = open(argv[1], O_RDONLY)) == -1) {
       perror("open failed");
       exit(1);
    }
   /* 읽기/쓰기 포인터가 파일의 끝을 가리키게 되고,
       변경된 읽기/쓰기 포인터가 반환되는데 이는 파일의 크기가 된다. */
    if ((filesize=lseek(fd, 0, SEEK_END)) == -1) {
       perror("lseek failed");
       exit(1);
    }
    printf("%s\'s size is %d\n", argv[1], filesize);
    close(fd);
    exit(0);
}

---------------------------------------------------------------------------------------

#include <fcntl.h>
#include <sys/types.h>
#include <unistd.h>

main(int argc, char *argv[])
{
    int fd;

    if ((fd = open(argv[1], O_WRONLY)) == -1) {
       perror("open failed");
       exit(1);
    }
    /* 읽기/쓰기 포인터가 파일의 끝으로 이동 */
    if (lseek(fd, 0, SEEK_END) == -1) {
       perror("lseek failed");
       exit(1);
    }
    /* 쓰기를 하면 파일의 뒤에 연결 */
    write(fd, " ABCD", 5);
    close(fd);
    exit(0);
}

---------------------------------------------------------------------------------------

#include <fcntl.h>
#include <sys/types.h>
#include <unistd.h>

main(int argc, char *argv[])
{
    int fd;

    if ((fd = open(argv[1], O_WRONLY)) == -1) {
       perror("open failed");
       exit(1);
    }
    /* fd 파일을 100바이트 크기로 자름 */
    if (ftruncate(fd, 100) == -1) {
       perror("ftruncate failed");
       exit(1);
    }
    close(fd);
    exit(0);
}

---------------------------------------------------------------------------------------

#include <fcntl.h>
#include <sys/types.h>
#include <unistd.h>

main(int argc, char *argv[])
{
    int fd;

    if ((fd = open(argv[1], O_WRONLY)) == -1) {
       perror("open failed");
       exit(1);
    }
    /* fd 파일을 150 바이트 크기로 만든다. 파일의 크기가 150바이트보다
     작아도 150바이트 크기가 되는데 빈 공간은 NULL로 채워진다. */
    if (ftruncate(fd, 150) == -1) {
       perror("ftruncate failed");
       exit(1);
    }
    close(fd);
    exit(0);
}

---------------------------------------------------------------------------------------
표준 출력을 의미하는 1번 파일 식별자에 대한 새로운 파일 식별자를 부여받아 이를 이용하여
출력하는 프로그램 즉 표준 출력 장비인 모니터로 출력

#include <fcntl.h>
#include <sys/types.h>
#include <unistd.h>

main()
{
   int fd;

   /* 1번 파일 식별자에 새로운 파일 식별자를 부여받아 fd에 저장한다.
      1번은 표준 출력을 의미하므로 fd도 표준 출력을 나타낸다. */
   if ((fd=dup(1)) == -1) {
      perror("dup failed");
      exit(1);
   }
   /* fd번 파일에 “ABCD”를 쓰는 동작으로 표준 출력 장치인 모니터로 출력 */
   write(fd, "ABCD", 5);
   exit(0);
}


---------------------------------------------------------------------------------------
파일에 새로운 파일 식별자를 부여받아 쓰기 동작을 하는 프로그램

#include <fcntl.h>
#include <sys/types.h>
#include <unistd.h>

main(int argc, char *argv[])
{
    int fd, newfd;

    if ((fd = open(argv[1], O_WRONLY)) == -1) {
       perror("open failed");
       exit(1);
    }
    /* fd 파일에 대한 새로운 파일 식별자를 부여받아 newfd에 저장 */
    if ((newfd=dup(fd)) == -1) {
       perror("dup failed");
       exit(1);
    }
    if (lseek(newfd, 0, SEEK_END) == -1) {
       perror("lseek failed");
       exit(1);
    }
    write(newfd, " ABCD", 5);
    close(fd);
    exit(0);
}

[~~localhost]#od -c alphabet

---------------------------------------------------------------------------------------

앞의 프로그램을 dup2를 이용하여 다시

#include <fcntl.h>
#include <sys/types.h>
#include <unistd.h>

main(int argc, char *argv[])
{
   int fd;

   if ((fd = open(argv[1], O_WRONLY)) == -1) {
      perror("open failed");
      exit(1);
   }
   /* dup2를 이용하여 fd번 파일에 대한 새로운 파일 식별자 7을 부여받음 */
   if ((dup2(fd, 7)) == -1) {
      perror("dup2 failed");
      exit(1);
   }
   if (lseek(7, 0, SEEK_END) == -1) {
      perror("lseek failed");
      exit(1);
   }
   write(7, " ABCD", 5);
   close(fd);
   exit(0);
}

---------------------------------------------------------------------------------------

파일의 상태정보를 알아냄


#include <stdio.h>
#include <stdlib.h>
#include <fcntl.h>
#include <sys/types.h>
#include <unistd.h>

int filestatus(int fd, char *file);

main(int argc, char *argv[])
{
    int fd, newfd, mode;

    /* argv[2]에 저장되어 있는 정수 형태의 문자열을 정수로 변환하여 mode에 저장 */
    mode = atoi(argv[2]);
    if ((fd = open(argv[1], mode)) == -1) {
       perror("open failed");
       exit(1);
    }
    if (filestatus(fd, argv[1]) == -1) {
       exit(2);
    }
    close(fd);
    exit(0);
}

int filestatus(int fd, char *file)
{
    int flag;

    /* 파일의 상태 정보를 알아내 flag에 저장. 가장 우측 두 개의 비트는 00, 01, 또는 10 */
    if ((flag=fcntl(fd, F_GETFL)) == -1) {
       perror("fcntl failed");
       return -1;
    }
    /* O_ACCMODE는 3이므로 flag & O_ACCMODE 결과는 flag의 가장 우측
      두 개의 비트가 00이면 0, 01이면 1, 10이면 2가 된다. */
    switch (flag & O_ACCMODE) { // AND 연산을 이용
       case O_RDONLY:   /* O_RDONLY는 0으로 정의 */
          printf("%s is read only file\n", file);
          break;
       case O_WRONLY:   /* O_WRONLY는 1로 정의 */
          printf("%s is write only file\n", file);
          break;
       case O_RDWR:   /* O_RDWR는 2로 정의 */
          printf("%s is read-write file\n", file);
          break;
       default:
          printf("no such mode\n");
    }
    return 0;
}

---------------------------------------------------------------------------------------

O_APPEND속성을 이용한 입력


#include <stdio.h>
#include <stdlib.h>
#include <fcntl.h>
#include <unistd.h>

main(int argc, char *argv[])
{
   int fd, flag;
   struct {
      char name[15];
      char phone[15];
   } student;

   if ((fd = open(argv[1], O_RDWR | O_CREAT, 0644)) == -1) {
      perror("open failed");
      exit(1);
   }
   /* 파일 상태 정보를 알아내 flag에 저장 */
   if ((flag=fcntl(fd, F_GETFL)) == -1) {
      perror("fcntl failed");
      exit(1);
   }

   /* 상태 정보가 저장되어 있는 flag에 O_APPEND를 추가 */
   flag |= O_APPEND;
   /* fd 파일의 상태 정보를 flag로 설정 */
   if ((fcntl(fd, F_SETFL, flag)) == -1) {
      perror("fcntl failed");
      exit(1);
   }

   while(1) {
      printf("input name => ");
      scanf("%s", student.name);
      if (!strcmp(student.name, "quit"))
          break;
      printf("input phone number => ");
      scanf("%s", student.phone);
      write(fd, (char *)&student, sizeof(student));
   }
   close(fd);
   exit(0);
}

Posted by 몰라욧