Scroll to navigation

read(2) System Calls Manual read(2)

NAZWA

read - odczytuje z deskryptora pliku

BIBLIOTEKA

Standardowa biblioteka C (libc, -lc)

SKŁADNIA

#include <unistd.h>
ssize_t read(int fd, void buf[.count], size_t count);

OPIS

read() próbuje odczytać maksymalnie count bajtów z deskryptora plików fd do bufora, którego początek znajduje się w buf.

W przypadku plików, które obsługują przeszukiwanie (seeking), operacja odczytu rozpoczyna się od przesunięcia pliku i przesunięcie pliku jest zwiększane o liczbę odczytanych bajtów. Jeśli przesunięcie pliku jest na końcu pliku lub poza nim, nie są odczytywane bajty, a read() zwraca zero.

Jeśli count wynosi zero, read() może wykryć błędy opisane poniżej. Przy braku błędów lub gdy read() nie sprawdza błędów, read() z count wynoszącym 0, wyłącznie zwraca zero, nie wykonując innych działań.

Zgodnie z POSIX.1, jeśli count jest większe niż SSIZE_MAX, wynik zależy od definicji w implementacji; zob. UWAGI odnośnie górnego limitu w Linuksie.

WARTOŚĆ ZWRACANA

Po pomyślnym zakończeniu zwracana jest liczba odczytanych bajtów (zero oznacza koniec pliku), oraz o tę wartość przesuwana jest pozycja w pliku. Nie jest błędem, jeśli liczba ta jest mniejsza niż liczba żądanych bajtów; może się to zdarzyć np. ponieważ chwilowo dostępnych jest mniej bajtów (może z powodu bliskości końca plików, a może z powodu czytania z potoku lub z terminala), lub ponieważ read() zostało przerwane sygnałem.

Po błędzie zwracane jest -1 i ustawiane errno wskazując błąd. W tym przypadku nie jest określone czy pozycja w pliku się zmieni.

BŁĘDY

Deskryptor pliku fd odwołuje się do pliku innego niż gniazdo i został oznaczony jako nieblokujący (O_NONBLOCK), a odczyt go zablokuje. Zob. open(2) aby dowiedzieć się więcej o fladze O_NONBLOCK.
Deskryptor pliku fd odwołuje się do gniazda i został oznaczony jako nieblokujący (O_NONBLOCK), a odczyt go zablokuje. POSIX.1-2001 pozwala w tej sytuacji na zwrócenie błędu ale nie wymaga aby ta stała miała taką samą wartość, przenośna aplikacja powinna sprawdzać obie możliwości.
fd nie jest prawidłowym deskryptorem pliku, lub nie jest otwarty dla odczytu.
buf jest poza dostępną przestrzenią adresową.
Wywołanie zostało przerwane sygnałem przed odczytaniem danych; zob. signal(7).
fd jest dołączony do obiektu nieodpowiedniego do odczytu, plik został otwarty ze znacznikiem O_DIRECT i adres podany w buf bądź wartość count lub przesunięcie nie zostały odpowiednio dopasowane.
fd utworzono przez wywołanie timerfd_create(2) i do read() podano nieprawidłowy rozmiar bufora; więcej informacji w podręczniku timerfd_create(2).
Błąd wejścia/wyjścia. Zdarza się to na przykład, gdy proces jest w grupie procesów tła, próbuje czytać z kontrolującego terminala, i blokuje lub ignoruje sygnał SIGTTIN, lub jego grupa procesów jest osierocona. Może się to również zdarzyć, gdy wystąpi niskopoziomowy błąd wejścia/wyjścia podczas odczytu z dysku lub taśmy. Kolejną możliwością, na sieciowych systemach plików, jest sytuacja, gdy blokada doradcza została ściągnięta z deskryptora pliku i blokada ta została zagubiona. Więcej informacji w rozdziale Zagubione blokady podręcznika fcntl(2).
fd odnosi się do katalogu.

Zależnie od obiektu podłączonego do fd, mogą także zajść inne (nieopisane) błędy.

STANDARDY

SVr4, 4.3BSD, POSIX.1-2001.

UWAGI

Typy size_t i ssize_t to odpowiednio liczba całkowita bez i ze znakiem, zgodnie z POSIX.1.

W Linuksie, read() (i podobne wywołania systemowe) mogą dokonać transferu co najwyżej 0x7ffff000 (2 147 479 552) bajtów, zwracając liczbę bajtów rzeczywiście przetransferowanych (jest to prawdziwe zarówno w systamach 32- jak i 64-bitowych).

Na systemach plików NFS, odczytanie niewielkiej ilości danych spowoduje uaktualnienie znacznika czasu tylko za pierwszym razem, następne wywołania tego nie uczynią. Jest to związana z buforowaniem atrybutów po stronie klienta, gdyż większość (jeżeli nie wszystkie) klienty NFS pozostawiają uaktualnianie st_atime (czasu ostatniego dostępu do pliku) serwerowi, a odczyty po stronie klienta, odbywające się z buforów klienta nie spowodują uaktualnienia st_atime na serwerze, gdyż nie ma wówczas odczytów po stronie serwera. Semantykę UNIX-a można uzyskać poprzez wyłączenie buforowania atrybutów po stronie klienta. Jednakże, w większości przypadków spowoduje to istotny wzrost obciążenia serwera i zmniejszy wydajność.

USTERKI

Zgodnie z POSIX.1-2008/SUSv4 Section XSI 2.9.7 („Thread Interactions with Regular File Operations”):

Wszystkie poniższe funkcje powinny być atomowe w odniesieniu do innych, biorąc pod uwagę wyniki określone w POSIX.1-2008, gdy działają na zwykłych plikach lub dowiązaniach symbolicznych: ...

Spośród wymienionych tam dalej API są między innymi read() i readv(2). I spośród efektów, które powinny być atomowe pomiędzy wątkami (i procesami) jest aktualizacja przesunięcia pliku. Jednak przed Linuksem 3.14 tak się nie działo: jeśli dwa procesy dzielące otwarty deskryptor pliku (zob open(2)) przeprowadzały read() (lub readv(2)) w tym samym czasie, to operacje wejścia/wyjścia nie były niepodzielne w odniesieniu do aktualizacji przesunięcia pliku, co powodowało, że bloki danych odczytywane przez dwa procesy mogły się (nieprawidłowo) nakładać, w blokach danych, które uzyskały. Problem został naprawiony w Linuksie 3.14.

ZOBACZ TAKŻE

close(2), fcntl(2), ioctl(2), lseek(2), open(2), pread(2), readdir(2), readlink(2), readv(2), select(2), write(2), fread(3)

TŁUMACZENIE

Autorami polskiego tłumaczenia niniejszej strony podręcznika są: Przemek Borys <pborys@dione.ids.pl>, Andrzej Krzysztofowicz <ankry@green.mf.pg.gda.pl> i Michał Kułach <michal.kulach@gmail.com>

Niniejsze tłumaczenie jest wolną dokumentacją. Bliższe informacje o warunkach licencji można uzyskać zapoznając się z GNU General Public License w wersji 3 lub nowszej. Nie przyjmuje się ŻADNEJ ODPOWIEDZIALNOŚCI.

Błędy w tłumaczeniu strony podręcznika prosimy zgłaszać na adres listy dyskusyjnej manpages-pl-list@lists.sourceforge.net.

4 grudnia 2022 r. Linux man-pages 6.03