1 / 25

Системни примитиви на файловата система Работа с обикновени файлове

Системни примитиви на файловата система Работа с обикновени файлове. гл. ас. Моника Филипова ФМИ, Катедра Изчислителни системи. Системни примитиви. Обработка на грешки При успех функцията на системния примитив връща цяло неотрицателно число.

lobo
Télécharger la présentation

Системни примитиви на файловата система Работа с обикновени файлове

An Image/Link below is provided (as is) to download presentation Download Policy: Content on the Website is provided to you AS IS for your information and personal use and may not be sold / licensed / shared on other websites without getting consent from its author. Content is provided to you AS IS for your information and personal use only. Download presentation by click this link. While downloading, if for some reason you are not able to download a presentation, the publisher may have deleted the file from their server. During download, if you can't get a presentation, the file might be deleted by the publisher.

E N D

Presentation Transcript


  1. Системни примитиви на файловата системаРабота с обикновени файлове гл. ас. Моника ФилиповаФМИ, Катедра Изчислителни системи

  2. Системни примитиви • Обработка на грешки • При успех функцията на системния примитив връща цяло неотрицателно число. • При грешка функцията на системния примитив връща -1 и променливата errno съдържа код на грешката. • Кодове на грешки и символни константи за тях #include <errno.h> • Библиотечни функции #include <stdio.h> void perror(const char *s); int fprintf(FILE *stream, char *frm ...); • Примитивни системни типове данни #include <sys/types.h>

  3. Съдържание • Основни понятия • Системни таблици • Системни примитиви за обикновени файлове • Създаване на файл • Отваряне на файл • Затваряне на файл • Четене и писане във файл • Позициониране във файл • Информация за файл • Копиране на файлов дескриптор • Неделимост на операциите

  4. Основни понятия Файлов дескриптор (file descriptor) • Цяло неотрицателно число, което се свързва с файл при отваряне и се използва за идентифицирането му. • Файловите дескриптори имат локално значение за всеки процес. • Връзката между файловия дескриптор и файла се разрушава при затваряне на файла. Текуща позиция във файла (file offset, file pointer) • Определя позицията във файла, от която ще бъде четено или записвано със системните примитивиreadи write. Режим на отваряне на файла • Определя начина на достъп до файла чрез съответния файлов дескриптор докато е отворен от процеса.

  5. Системни таблици Таблица на индексните описателиСъдържа точно един запис за всеки отворен файл. • копие на i-node на файла от диска • адрес на i-node • състояние на i-node • брояч Таблица на отворените файловеВсеки запис съдържа данни за едно отваряне на файл. • режим на отваряне • текуща позиция във файла • указател към запис от таблицата на индексните описатели • брояч

  6. Системни таблици (2) Таблици на файловите дескриптори • Всеки процес има собствена Таблица на файловите дескриптори. • Запис в Таблицата съдържа указател към запис от Таблицата на отворените файлове. • Файловият дескриптор представлява индекс на записа от Таблицата на файловите дескриптори, който е използван при отварянето на файла.

  7. Системни таблици (3)

  8. Системни примитиви за обикновени файловеСъздаване на обикновен файлint creat(const char *filename, mode_t mode); Отваряне на файл #include <fcntl.h> int open(const char *filename, int oflag[,mode_t mode]); O_RDONLY, O_WRONLY, O_RDWRO_CREAT, O_EXCL, O_TRUNCO_APPEND, O_SYNC Връщат файлов дескриптор на отворения файл, -1 при грешка. fd=open(fname,O_WRONLY|O_CREAT|O_TRUNC,mode);

  9. Алгоритъм на open 1. Преобразува пълното име на файла в номер на i-node. 2. Ако файлът съществува и са зададени флагове O_CREAT и O_EXCL, завършва и връща -1. 3. Ако файлът не съществуваи е зададен флаг O_CREAT, създава файл с име filename, в противен случай завършва и връща -1. 4. Зарежда i-node на файла в Таблицата на индексните описатели. 5. Проверява правата на процеса за достъп към файла. 6. Разпределя свободен запис от Таблицата на отворените файлове и го инициализира: брояч - 1; текуща позиция - 0; режим на отваряне - от oflag; указател към записа от Таблицата на индексните описатели от стъпка 4. 7. Разпределя свободен запис от Таблицата на файловите дескриптори и го инициализира с указател към записа от Таблицата на отворените файлове от стъпка 6. 8. Ако е зададен флаг O_TRUNC, то се освобождават блоковете на файла. 9. Връща файловия дескриптор.

  10. Процес A fd1=open(“/usr/share”, O_RDONLY); fd2=open(“/usr/share”, O_WRONLY); Процес B fd1=open(“/usr/share”, O_RDONLY); fd2=open(“private”, O_RDWR);

  11. Затваряне на файлint close(int fd);Връща 0 при успех, -1 при грешка. Алгоритъм на close • Освобождава записа от Таблицата на файловите дескриптори. • Намалява с 1 полето брояч в записа от Таблицата на отворените файлове. • Ако новото значение е по-голямо от 0, то завършва като връща 0. • Ако новото значение е 0, то освобождава записа от Таблицата на отворените файлове. • Намалява с 1 полето брояч в записа от Таблицата на индексните описатели. • Ако новото значение е 0, то записва i-node на диска (ако е бил изменен). • Връща 0.

  12. Процес B close(fd1); close(fd2); Пример

  13. Четене и писане във файл ssize_t read(int fd, void *buffer, size_t nbytes); Връща действителния брой прочетени байта, 0 при EOF, -1 при грешка. ssize_t write(int fd, void *buffer, size_t nbytes); Връща действителния брой записани байта, -1 при грешка. Позициониране във файл off_t lseek(int fd,off_t offset, int flag); SEEK_SET (0) fp = offsetSEEK_CUR (1) fp = fp + offsetSEEK_END (2) fp = file_size + offset Връща новото значение на текущата позиция, -1 при грешка.

  14. Пример. Създава на "файл с дупка". #include <stdio.h> #include <fcntl.h> char buf1[] = "ABCDEF"; char buf2[] = "abcdef"; main(void) { int fd; if (( fd = creat("file.hole", 0640) ) ==-1){ fprintf(stderr, "can't create\n"); exit(1); } if (write(fd, buf1, 6) != 6){ fprintf(stderr, "write buf1 error\n"); exit(1); } if (lseek(fd, 10, SEEK_CUR) == -1){ fprintf(stderr, "lseek error\n"); exit(1); } if (write(fd, buf2, 6) != 6){ fprintf(stderr, "write buf2 error\n"); exit(1); } close(fd); exit(0); }

  15. Резултат от изпълнение на програмата $ a.out $ ls -l file.hole -rw-r----- 1 moni staff 22 Apr 12 05:58 file.hole $ od -c file.hole 0000000 A B C D E F \0 \0 \0 \0 \0 \0 \0 \0 \0 \0 0000020 a b c d e f 0000026 Пример • Запомняне на текущата позиция във файл • Проверка, дали файлът позволява позициониране off_t position; position = lseek(fd, 0, SEEK_CUR);

  16. Информация за файл #include <sys/stat.h> int stat(const char *filename, struct stat *sbuf); int fstat(int fd, struct stat *sbuf); int lstat(const char *filename, struct stat *sbuf);Връщат 0 при успех, -1 при грешка.

  17. Структура stat struct stat { dev_t st_dev; /* device where inode belongs */ ino_t st_ino; /* inode number */ mode_t st_mode; /* mode word */ nlink_t st_nlink; /* number of hard links */ uid_t st_uid; /* user ID of owner*/ gid_t st_gid; /* group ID of owner */ dev_t st_rdev; /* device type for special files */ off_t st_size; /* file size */ blksize_t st_blksize; /* blocksize for filesystem I/O */ blkcnt_t st_blocks; /* number of blocks allocated */ time_t st_atime;/* time of last access */ time_t st_mtime; /* time of last modification */ time_t st_ctime; /* time of last change */ };

  18. Пример. Създава ново копие на съществуващ файл. #include <stdio.h> #include <sys/stat.h> #include <fcntl.h> #define BUFS 4096 main(int argc, char *argv[]) { int fdr, fdw, n; struct stat sbuf; char buff[BUFS]; if (argc != 3) { fprintf(stderr, "usage: copy from_file to_file\n"); exit(1); } if ( stat(argv[1], &sbuf) == -1) { fprintf(stderr, "copy: %s: No such file\n", argv[1]); exit(1); }

  19. if ( ! S_ISREG(sbuf.st_mode) ) { fprintf(stderr, "copy: %s: Not a regular file\n", argv[1]); exit(1); } if (( fdr = open(argv[1], O_RDONLY)) == -1) { fprintf(stderr, "copy: %s: can't open\n", argv[1]); exit(1); } if (( fdw = creat(argv[2], 0644)) == -1) { fprintf(stderr, "copy: %s:can't create\n", argv[2]); exit(1); } while (( n = read(fdr, buff, BUFS)) > 0) write(fdw, buff, n); close(fdr); close(fdw); exit(0); }

  20. Общото между двата файлови дескриптора:- един и същи отворен файл- общ указател на текуща позиция- еднакъв режим на отваряне на файла Копиране на файлов дескриптор int dup(int fd); int dup2(int fd, intnewfd); Връщат новия файлов дескриптор при успех,-1 при грешка.

  21. fd1=open("/usr/share", O_RDONLY);fd2=open("/usr/share", O_WRONLY);fd3=dup(fd1);

  22. Пример. Пренасочване на стандартния вход от файл if ( (fd = open(infile, O_RDONLY)) == -1 ) { fprintf(stderr, "can't open file %s\n", infile); exit(1); } close(0); dup(fd); close(fd);

  23. Неделимост на операциите • Ядрото гарантира неделимост (атомарност) за всеки отделен системен примитив. Пример. Позициониране в края на файл и писане • Първи вариант fd = open("/home/share", O_WRONLY); lseek(fd, 0, SEEK_END); /* position to EOF */ write(fd, buf, 10); /* and write */ • Втори вариант fd = open("/home/share", O_WRONLY |O_APPEND); write(fd, buf, 10); /* position to EOF and write */

  24. Пример.Извежда на стандартния изход съдържанието на файлове, чиито имена са зададени като аргументи. #include <stdio.h> #include <fcntl.h> #include <sys/stat.h> main(int argc, char *argv[]) { int fdr, i; struct stat sbuf; char buff; if (argc < 2) { fprintf(stderr,"usage: typef file...\n"); exit(1); }

  25. for ( i=1; i<argc; i++ ) { if ( stat(argv[i], &sbuf) ==-1) { fprintf(stderr,"typef: %s: No such file\n", argv[i]); continue; } if ( ! S_ISREG(sbuf.st_mode) ) { fprintf(stderr,"typef: %s: is not a regular file\n", argv[i]); continue; } if (( fdr = open(argv[i], O_RDONLY) ) == -1) { fprintf(stderr, "typef: %s: can't open\n", argv[i]); continue; } while ( read(fdr, &buf, 1) ) write(1, &buf, 1); close(fdr); } exit(0); }

More Related