Your Browser is not longer supported

Please use Google Chrome, Mozilla Firefox or Microsoft Edge to view the page correctly
Loading...

{{viewport.spaceProperty.prod}}

fopen, fopen64 - Datenstrom öffnen

&pagelevel(4)&pagelevel

Definition

#include <stdio.h>

FILE *fopen(const char *filename, const char *mode);
FILE *fopen64(const char *filename, const char *mode);

Beschreibung

fopen() öffnet die Datei, deren Pfadname die Zeichenkette ist, die auf filename zeigt, und ordnet ihr einen Datenstrom zu.

filename kann sein:

  • ein gültiger POSIX-Dateiname

  • ein gültiger BS2000-Dateiname:

    • link= linkname linkname bezeichnet einen BS2000-Linknamen.

    • (SYSDTA), (SYSOUT), (SYSLST), die entsprechende Systemdatei

    • (SYSTERM), Terminal-Ein-/Ausgabe

    • (INCORE), temporäre Binärdatei, die nur im virtuellen Speicher angelegt wird.

mode ist eine Zeichenkette, die die gewünschte Zugriffsart angibt und dafür einen der folgenden Werte annehmen:

r      

Öffnen Textdatei zum Lesen. Die Datei muss bereits vorhanden sein.

w

Öffnen Textdatei zum Neuschreiben. Ist die Datei vorhanden, wird der alte Inhalt gelöscht. Ist die Datei nicht vorhanden, wird sie neu erstellt.

wx

Öffnen Textdatei zum Neuschreiben. Die Datei darf noch nicht vorhanden sein.

a

Öffnen Textdatei zum Anfügen ans Ende der Datei. Ist die Datei vorhanden, wird auf das Dateiende positioniert, d.h. der alte Inhalt bleibt erhalten und die neuen Daten werden ans Ende der Datei angefügt. Ist die Datei nicht vorhanden, wird sie neu erstellt.

rb

Öffnen Binärdatei zum Lesen. Die Datei muss bereits vorhanden sein.

wb

Öffnen Binärdatei zum Neuschreiben. Ist die Datei vorhanden, wird der alte Inhalt gelöscht. Ist die Datei nicht vorhanden, wird sie neu erstellt.

wbx

Öffnen Binärdatei zum Neuschreiben. Die Datei darf noch nicht vorhanden sein.

ab

Öffnen Binärdatei zum Anfügen ans Ende der Datei. Ist die Datei vorhanden, wird auf das Dateiende positioniert, d.h. der alte Inhalt bleibt erhalten und die neuen Daten werden ans Ende der Datei angefügt. Ist die Datei nicht vorhanden, wird sie neu erstellt.

r+w, r+

Öffnen Textdatei zum Lesen und Schreiben. Die Datei muss bereits vorhanden sein. Der alte Inhalt bleibt erhalten.

w+r, w+

Öffnen Textdatei zum Neuschreiben und Lesen. Ist die Datei vorhanden, wird der alte Inhalt gelöscht. Ist die Datei nicht vorhanden, wird sie neu erstellt.

w+x

Öffnen Textdatei zum Neuschreiben und Lesen. Die Datei darf noch nicht vorhanden sein.

a+r, a+

Öffnen Textdatei zum Anfügen ans Ende der Datei und zum Lesen. Ist die Datei vorhanden, bleibt der alte Inhalt erhalten und die neuen Daten werden ans Ende der Datei angefügt. Eine bereits vorhandene Datei ist nach dem Öffnen bei KR-Funktionalität (nur bei C/C++ Versionen kleiner V3 vorhanden) auf das Dateiende, bei ANSI-Funktionalität auf den Dateianfang positioniert. Ist die Datei nicht vorhanden, wird sie neu erstellt.

r+b, rb+

Öffnen Binärdatei zum Lesen und Schreiben. Die Datei muss bereits vorhanden sein. Der alte Inhalt bleibt erhalten.

w+b, wb+

Öffnen Binärdatei zum Neuschreiben und Lesen. Ist die Datei vorhanden, wird der alte Inhalt gelöscht. Ist die Datei nicht vorhanden, wird sie neu erstellt.

w+bx, wb+x

Öffnen Textdatei zum Neuschreiben und Lesen. Die Datei darf noch nicht vorhanden sein.

a+b, ab+

Öffnen Binärdatei zum Anfügen ans Ende der Datei und zum Lesen. Ist die Datei vorhanden, bleibt der alte Inhalt erhalten und die neuen Daten werden ans Ende der Datei angefügt. Eine bereits vorhandene Datei ist nach dem Öffnen bei KR-Funktionalität (nur bei C/C++ Versionen kleiner V3 vorhanden) auf das Dateiende, bei ANSI-Funktionalität auf den Dateianfang positioniert. Ist die Datei nicht vorhanden, wird sie neu erstellt.

Das Zeichen b wird in den obigen Zugriffsarten ignoriert. Das Öffnen einer Datei zum Lesen, d.h. mit r als erstem Zeichen im Argument mode, schlägt fehl, wenn die Datei nicht existiert oder nicht gelesen werden kann.

Wird eine Datei zum Anfügen geöffnet, d.h. mit a als erstem Zeichen im Argument mode, erfolgen alle nachfolgenden Schreiboperationen in die Datei am aktuellen Dateiende, ohne dass dabei eventuell dazwischen erfolgte Aufrufe von fseek() eine Rolle spielen.

Wird eine Datei zum Aktualisieren geöffnet, d.h. mit + als zweitem Zeichen im Argument mode, dann können auf dem zugeordneten Datenstrom sowohl Ein- als auch Ausgabeoperationen durchgeführt werden. Dennoch darf auf eine Ausgabeoperation nicht unmittelbar eine Eingabeoperation folgen, ohne dass dazwischen ein Aufruf der Funktion fflush() oder einer der Funktionen zur Positionierung, fseek(), fsetpos() oder rewind(), erfolgt ist.

Auf eine Eingabeoperation darf nicht unmittelbar eine Ausgabeoperation folgen, ohne dass dazwischen eine der Funktionen zur Positionierung aufgerufen wurde, außer die Eingabeoperation hat das Dateiende erreicht.

Ist ein Datenstrom geöffnet, so ist er genau dann vollständig gepuffert, wenn sichergestellt ist, dass er keine Verweise auf ein interaktives Gerät hat, z.B. Terminal. Die Kennzeichen für Dateiende und Fehler dieses Datenstroms werden gelöscht.

Für die automatische Konvertierung darf das b für binär in modus nicht angegeben werden. Die Umgebungsvariable IO_CONVERSION darf nicht vorhanden sein oder muss den Wert YES haben.

BS2000

Wenn BS2000-Dateien ausgeführt werden, ist Folgendes zu beachten: In mode können mit optionalen Zusatzangaben weitere Funktionen gesteuert werden:

Zusatzangabe

Funktion

tabexp=yes/no

Behandlung des Tabulatorzeichens (\t)

lbp=yes/no

Behandlung des Last Byte Pointers (LBP)

split=yes/no

Verarbeitung von Textdateien mit der Angabe einer maximalen Satzlänge

Tabulatorzeichen (\t)

In mode kann zusätzlich zur Zugriffsart eine Angabe zur Behandlung des Tabulatorzeichens (\t) gemacht werden. Diese Angabe ist nur für Textdateien mit den Zugriffsmethoden SAM und ISAM relevant.

"...,tabexp=yes"

Das Tabulatorzeichen wird in die entsprechende Anzahl Leerzeichen expandiert; Voreinstellung bei KR-Funktionalität (nur bei C/C++ Versionen kleiner V3 vorhanden).

"...,tabexp=no"

Das Tabulatorzeichen wird nicht expandiert; Voreinstellung bei ANSI-Funktionalität.

Last Byte Pointer (LBP)

In mode kann kann zusätzlich zur Zugriffsart eine Angabe zur Behandlung des Last Byte Pointer (LBP) gemacht werden. Diese Angabe ist nur für Binärdateien mit Zugriffsart PAM relevant. Falls lbp=yes angegeben ist, wird geprüft, ob LBP-Unterstützung möglich ist. Ist dies nicht der Fall, so schlägt die Funktion fopen(), fopen64() fehl und errno wird auf ENOSYS gesetzt. Weitere Auswirkungen hat der Schalter erst, wenn die Datei geschlossen wird.

Beim Öffnen und Lesen einer bestehenden Datei wird der LBP unabhängig vom lbp-Schalter immer berücksichtigt:

  • Ist der LBP der Datei ungleich 0, wird er ausgewertet. Ein eventuell vorhandener Marker wird ignoriert.
  • Ist der LBP = 0, wird nach einem Marker gesucht und die Dateilänge daraus ermittelt. Falls kein Marker gefunden wird, wird das Ende des letzten vollständigen Blocks als Dateiende betrachtet.

"...,lbp=yes"

Beim Schließen einer Datei, die verändert oder neu erstellt wurde, wird kein Marker geschrieben (auch wenn einer vorhanden war) und ein gültiger LBP gesetzt. Auf diese Weise können Dateien mit Marker auf LBP ohne Marker umgestellt werden.Bei NK-Dateien wird der letzte logische Block mit binären Nullen aufgefüllt, bei K-Dateien wird die Datei bis zum physikalischen Dateiende aufgefüllt.

"...,lbp=no"

Beim Schließen einer Datei, die neu erstellt wurde, wird der LBP auf Null (=ungültig) gesetzt. Es wird ein Marker geschrieben. Bei NK-Dateien wird der letzte logische Block mit binären Nullen aufgefüllt, bei K-Dateien wird die Datei bis zum physikalischen Dateiende aufgefüllt.

Beim Schließen einer Datei, die verändert wurde, wird der LBP auf Null (=ungültig) gesetzt. Ein Marker wird nur dann geschrieben, wenn vorher bereits ein Marker vorhanden war. Falls die Datei beim Öffnen einen gültigen LBP besaß, wird kein Marker geschrieben, da in diesem Fall davon ausgegangen wird, dass kein Marker vorhanden ist. Bei NK-Dateien wird der letzte logische Block mit binären Nullen aufgefüllt, bei K-Dateien wird die Datei bis zum physikalischen Dateiende aufgefüllt.

Wird der Schalter lbp nicht angegeben, hängt das Verhalten von der Umgebungsvariablen LAST_BYTE_POINTER ab (siehe auch Abschnitt "Umgebungsvariablen“):

LAST_BYTE_POINTER=YES

Die Funktion verhält sich so, als ob lbp=yes angegeben wäre.

LAST_BYTE_POINTER=NO

Die Funktion verhält sich so, als ob lbp=no angegeben wäre.

Split/Nosplit-Schalter

Dieser Schalter steuert die Verarbeitung von Textdateien mit der Zugriffsart SAM und variabler Satzlänge, wenn zusätzlich eine maximale Satzlänge angegeben ist.

"...,split=yes"

  • Beim Lesen gilt:
    Hat ein Satz die maximale Satzlänge, wird angenommen, dass es sich bei dem Folgesatz um die Fortsetzung dieses Satzes handelt, und die Sätze werden verkettet.
  • Beim Schreiben gilt:
    Ein Satz, der länger als die maximale Satzlänge ist, wird in mehrere Sätze aufgeteilt. Hat ein Satz genau die maximale Satzlänge, wird nach diesem ein Satz der Länge Null geschrieben.

"...,split=no"

Beim Lesen werden Sätze maximaler Länge nicht mit dem darauffolgenden Satz verkettet. Beim Schreiben mit einer der Funktionen fwrite(), fprintf(), printf(), vfprintf(), vprintf(), fwprintf(), wprintf(), vfwprintf(), vwprintf(), fputs(), fputws() und puts() werden Sätze, die länger als die maximale Satzlänge sind, auf die maximale Satzlänge gekürzt.

Wird der Schalter nicht angegeben, gilt "...,split=yes". (Ende)

Es besteht kein funktionaler Unterschied zwischen fopen und fopen64, außer dass fopen64 einen Dateizeiger zurückgibt, der über die 2GB-Grenze hinausgehen kann. fopen64() setzt das O_LARGEFILE Bit im File Status Flag.

Returnwert

Dateizeiger

bei Erfolg.

 

Nullzeiger

wenn auf filename nicht zugegriffen werden kann, mode ungültig ist oder die Datei nicht geöffnet werden kann. errno wird gesetzt, um den Fehler anzuzeigen.

Fehler

fopen() und fopen64() schlagen fehl, wenn gilt:

 

EACCES

Für eine Komponete des Pfades existiert kein Durchsuchrecht.

Die Datei existiert, und die für mode geltenden Zugriffrechte werden verweigert.

Die Datei existiert nicht, und das übergeordnete Verzeichnis der zu erstellenden Datei hat kein Schreibrecht.

 

EINTR

Während des Systemaufrufs fopen() wurde ein Signal abgefangen.

 

EINVAL

Der Wert des Arguments mode ist ungültig.

 

EISDIR

Die angegebene Datei ist ein Dateiverzeichnis und mode verlangt Schreibrecht.

 

EMFILE

{OPEN_MAX}-Dateideskriptoren sind bereits für den aufrufenden Prozess geöffnet.

{FOPEN_MAX}-Datenströme sind bereits für den aufrufenden Prozess geöffnet.

{STREAM_MAX}-Datenströme sind bereits für den aufrufenden Prozess geöffnet.


ENAMETOOLONG 



Die Länge von filename überschreitet {PATH_MAX}, oder eine Komponente des Pfades ist länger als {NAME_MAX}.

 

ENFILE

Die maximale Anzahl von Dateien im System ist bereits geöffnet..

 

ENOENT

Die angegebene Datei existiert nicht, oder filename zeigt auf die leere Zeichenkette.

 

ENOMEM

Es ist nicht ausreichend Speicherplatz vorhanden.

 

ENOSPC

Die Datei existiert nicht, und das Dateiverzeichnis, in dem eine neue Datei erstellt werden soll, kann nicht erweitert werden.

 

ENOTDIR

Eine Komponente des Pfades ist kein Dateiverzeichnis.

 

ENXIO

Die angegebene Datei ist eine Gerätedatei für ein zeichen- oder blockorientiertes Gerät und das dieser Datei zugeordnete Gerät existiert nicht.

 

EROFS

Die angegebene Datei befindet sich in einem Dateisystem, das nur Leserecht hat, und mode verlangt Schreibrecht.

 

ETXTBSY

Bei der Datei handelt es sich um eine reine Prozedurdatei (gemeinsam verwendete Textdatei), die nur ausgeführt wird und für mode ist Schreibzugriff erforderlich.

 

EOVERFLOW

Die genannte Datei ist eine reguläre Datei und die Größe der Datei kann in einem Objekt des Typs off_t nicht korrekt dargestellt werden.

Hinweise

{STREAM_MAX} entspricht der Anzahl der Datenströme, die ein Prozess zu selben Zeit geöffnet haben darf und hat denselben Wert wie {FOPEN_MAX}, nämlich 2048.

Ob fopen() für eine BS2000- oder eine POSIX-Datei ausgeführt wird, hängt von der Programmumgebung ab.

BS2000 Der BS2000-Dateiname bzw. -Linkname kann in Klein- und Großbuchstaben geschrieben werden; er wird automatisch in Großbuchstaben umgesetzt. Durch die Angabe eines b an zweiter bzw. dritter Stelle im Parameter mode wird die Datei als Binärdatei geöffnet. Die Angabe ist nur für SAM-Dateien relevant, da nur SAM-Dateien sowohl im Binär- als auch im Textmodus verarbeitet werden können.

Systemdateien und ISAM-Dateien werden immer als Textdateien verarbeitet. Die Angabe des Binärmodus führt bei diesen Dateien zu einem Fehler beim Öffnen.

(INCORE)- und PAM-Dateien werden immer als Binärdateien verarbeitet. Aus Kompatibilitätsgründen funktioniert das Öffnen als Binärdatei auch ohne explizite Angabe des Binärmodus.

Wird eine nicht vorhandene Datei neu angelegt, dann wird standardmäßig eine Datei mit folgenden Attributen erzeugt:


Binärdatei

Textdatei

Zugriffsmethode

SAM

SAM (KR-Funktionalität, nur bei C/C++ Versionen kleiner V3 vorhanden)

ISAM (ANSI-Funktionalität)

Satzformat

F

V

Bei Verwendung eines Linknamens lassen sich mit dem ADD-FILE-LINK-Kommando folgende Dateiattribute ändern: Zugriffsmethode, Satzlänge, Satzformat, Blocklänge und Blockformat.

In allen Fällen, in denen der alte Inhalt einer bereits existierenden Datei gelöscht wird (geöffnet zum Neuschreiben bzw. zum Neuschreiben und Lesen), bleiben die Katalogeigenschaften dieser Datei erhalten.

Wenn eine Datei zum Aktualisieren geöffnet wird, kann das Lesen und Schreiben über denselben Dateizeiger erfolgen. Dennoch sollte auf eine Ausgabe nicht unmittelbar eine Eingabe folgen ohne ein vorhergehendes Positionieren (fseek(), fsetpos(), rewind(), oder einen fflush-Aufruf. Dasselbe gilt für eine Ausgabe, die einer Eingabe folgt.

Position des Lese-/Schreibzeigers im Anfügemodus

(INCORE)-Dateien können nur zum Neuschreiben (w), zum Neuschreiben und Lesen (w+r) oder zum Lesen (r) geöffnet werden. Es müssen zuerst Daten geschrieben werden. Um die geschriebenen Daten wieder einlesen zu können, gibt es folgende Möglichkeiten: Wurde die Datei nur zum Neuschreiben geöffnet, kann man sie mit der Funktion freopen() zum Lesen öffnen. Wurde die Datei zum Neuschreiben und zum Lesen geöffnet, kann man den Lese-/Schreibzeiger mit der Funktion rewind() auf den Dateianfang positionieren.

Eine Datei kann gleichzeitig für verschiedene Zugriffsmodi geöffnet werden, sofern diese Modi im BS2000-Datenverwaltungssystem miteinander verträglich sind.

Startet ein Programm, werden ihm automatisch drei Dateizeiger wie folgt zugeordnet:

stdin

Dateizeiger für Standard-Eingabe (Terminal)

stdout

Dateizeiger für Standard-Ausgabe (Terminal)

stderr

Dateizeiger für Standard-Fehlerausgabe (Terminal)

Es können maximal _NFILE-Dateien gleichzeitig geöffnet sein. _NFILE ist in stdio.h mit 2048 definiert.

Für das Öffnen von Dateien mit Satz-Ein-/Ausgabe wird mode um zwei Angaben erweitert. Diese Angaben folgen in der Zeichenkette hinter der Zugriffsart (s.o.), jeweils durch ein Komma getrennt:

"...,type=record [,forg={seq/key}]"

type=record

Die Datei wird für Satz-Ein-/Ausgabe geröffnet.
Fehlt diese Angabe, wird die Datei für Strom-Ein-/Ausgabe geöffnet.

forg=seq

Die Dateiorganisation ist sequenziell.
Sequenzielle Dateien können SAM- oder PAM-Dateien sein.

forg=key

Die Dateiorganisation ist indexsequenziell.
Indexsequenzielle Dateien sind ISAM-Dateien.

Fehlt die Angabe von forg(), ist die Dateiorganisation vom FCBTYP der Datei abhängig:Der FCBTYP ist durch den Katalogeintrag einer bereits existierenden Datei festgelegt bzw. durch ein ADD-FILE-LINK-Kommando. Für SAM- und PAM-Dateien wird sequenzielle Dateiorganisation angenommen, für ISAM-Dateien indexsequenzielle Dateiorganisation.

Fehlt die Angabe von forg() und der FCBTYP ist nicht festgelegt (Datei nicht vorhanden, kein ADD-FILE-LINK-Kommando), wird sequenzielle Dateiorganisation angenommen und eine SAM-Datei erstellt.

Für die Satz-Ein-/Ausgabe gelten nachstehende Einschränkungen; werden diese Einschränkungen nicht eingehalten, wird die Datei nicht geöffnet und ein Fehler-Returnwert geliefert:

Die Datei muss im Binärmodus geöffnet werden (Angabe b bei der Zugriffsart).

type=record ist zulässig für SAM-, PAM- oder ISAM-Dateien.

forg=seq ist zulässig für SAM- oder PAM-Dateien, forg=key für ISAM-Dateien.

Bei ISAM-Dateien ist der Anfügemodus a unzulässig. Die Position wird aus dem Schlüssel im Satz bestimmt.

Siehe auch

creat(), fclose(), fdopen(), ferror(), freopen(), open(), stdio.h.