C ++ verwendet den streamoff
Typ, um einen Offset innerhalb eines (Datei-) Streams darzustellen, und ist in [stream.types] wie folgt definiert:
using streamoff = implementation-defined ;
Der Typ Streamoff ist ein Synonym für einen der vorzeichenbehafteten integralen Grundtypen mit ausreichender Größe, um die maximal mögliche Dateigröße für das Betriebssystem darzustellen. 287)
287) Typischerweise lang lang.
Dies ist sinnvoll, da damit große Dateien gesucht werden können (im Gegensatz zur Verwendung long
, die möglicherweise nur 32 Bit breit ist).
[filebuf.virtuals] definiert basic_filebuf
die Funktion zum Suchen in einer Datei wie folgt:
pos_type seekoff(off_type off, ios_base::seekdir way, ios_base::openmode which = ios_base::in | ios_base::out) override;
off_type
ist äquivalent zu streamoff
, siehe [iostreams.limits.pos]. Der Standard erklärt dann jedoch die Auswirkungen der Funktion. Ich bin irritiert über den allerletzten Satz, für den ein Anruf erforderlich ist fseek
:
Effekte :
width
Bezeichnena_codecvt.encoding()
. Wennis_open() == false
oderoff != 0 && width <= 0
, schlägt der Positionierungsvorgang fehl. Wenn andernfallsway != basic_ios::cur
oderoff != 0
, und wenn die letzte Operation ausgegeben wurde, aktualisieren Sie die Ausgabesequenz und schreiben Sie eine beliebige Verschiebungssequenz. Suchen Sie als nächstes die neue Position: ifwidth > 0
, callfseek(file, width * off, whence)
, andernfalls callfseek(file, 0, whence)
.
fseek
akzeptiert einen long
Parameter. Wenn off_type
und streamoff
definiert sind als long long
(wie vom Standard vorgeschlagen), kann dies zu einer Abwärtskonvertierung auf long
beim Anruf führen fseek(file, width * off, whence)
(was zu möglicherweise schwer zu diagnostizierenden Fehlern führt). Dies stellt die gesamte Begründung für die Einführung des streamoff
Typs in Frage .
Ist dies beabsichtigt oder ein Fehler in der Norm?
seekoff
unbedingt Anwendungenfseek
unter der Motorhaube. Vielmehr wird das (vermutlich vertraute?) Verhalten vonfseek
verwendet, um zu erklären, was zuseekoff
tun ist.fseek
werden muss, solange er etwas mit demselben Effekt tut. Da jedochfseek
ein Versatz kleinerLONG_MIN
oder größer alsLONG_MAX
keine Auswirkung hat, ist die Erklärung bestenfalls unvollständig, zumindest für Implementierungen, bei denen derstreamoff
Abstand breiter als istlong
.Antworten:
Ich denke, dass die Schlussfolgerung, dass Sie daraus ziehen, dass es eine Nichtübereinstimmung zwischen C ++ - Streams gibt und
fseek
dies zu Laufzeitfehlern führt, falsch ist. Die Situation scheint zu sein:Auf Systemen mit
long
64 Bitstreamoff
ist definiert alslong
und dieseekoff
Funktion wird aufgerufenfseek
.Auf Systemen mit
long
32 Bit, aber das Betriebssystem unterstützt 64-Bit-Datei-Offsets,streamoff
ist definiert alslong long
undseekoff
ruft eine Funktion auf, die entweder aufgerufen wirdfseeko
oderfseeko64
einen 64-Bit-Offset akzeptiert.Hier ist ein Ausschnitt aus der Definition von
seekoff
auf meinem Linux-System:LFS steht für Large File Support .
Schlussfolgerung: Während der Standard eine Definition vorschlägt
streamoff
, die angeblich im Widerspruch zu derseekoff
aufrufenden Anforderung steht,fseek
verstehen Bibliotheksdesigner, dass sie die Variante aufrufen müssenfseek
, die den gesamten Bereich der vom Betriebssystem unterstützten Offsets akzeptiert.quelle
The situation seems to be:
- Die Situation ist , dass die Umsetzung nicht erlaubt ist , nicht zu nennenfseek
inseekoff
. Es muss anrufenfseek
, nicht, Standard sagt, es muss. Ich kann argumentieren, dass diese Implementierung ungültig ist. Ich glaube, es beantwortet die Frage nicht. Och, fand llvm , es ruftfseeko
._fseeki64
diese Funktion auf. das scheint auch zu verletzen, was der Standard sagt.fseek
. An anderer Stelle beschreibt der Standard etwas als "wie durch einen Anruffseek(...)
". Wenn es so sehr darum ging, buchstäblich anzurufenfseek
, wäre diese Aussage anders. Ernsthaft, was würden Sie tun, wenn Sie eine C ++ - Bibliothek implementieren würden? Würden Sie darauf bestehen,fseek
mit den unteren 32 Bit eines 64-Bit-Dateiversatzes aufzurufen, weil Sie in einem Dokument dazu aufgefordert werden? Würden Ihre Kunden Ihnen dafür danken?