std.tar liest und schreibt TAR-Archive im POSIX ustar Format (IEEE Std 1003.1-1988). TAR komprimiert nicht — es ist ein reines Archivformat. Für komprimierte Archive (.tar.gz) wird TAR mit std.gzip kombiniert.
→ Archiv-Übersicht · std.zip · std.rar · std.gzip · Standard Library
Alle Beispiele dieser Seite sind mit lyxc 1.0.21A übersetzt und ausgeführt; die gezeigten Ausgaben sind echte Programmausgaben.
Einschränkungen: Max. 4096 Einträge, Dateinamen max. 100 Bytes (kein GNU LongLink / split-header). Beim Lesen werden nur reguläre Dateien (typeflag 0) erfasst — Verzeichnisse werden übersprungen.
| Konstante | Wert | Bedeutung |
|---|---|---|
TAR_BLOCK_SIZE | 512 | Header- und Datei-Blöcke sind je 512 Bytes |
TAR_MAX_ENTRIES | 4096 | Maximale Einträge pro Archiv |
TAR_ERR_OK | 0 | Kein Fehler |
TAR_ERR_NOTTAR | 1 | Keine gültige TAR-Datei |
TAR_ERR_IO | 2 | I/O-Fehler beim Lesen oder Schreiben |
TAR_ERR_CORRUPT | 3 | Archiv beschädigt |
TAR_ERR_FULL | 4 | TAR_MAX_ENTRIES erreicht |
| Funktion | Rückgabe | Beschreibung |
|---|---|---|
TarOpen(path) | int64 Handle oder 0 | Öffnet TAR-Archiv aus Datei |
TarClose(handle) | void | Gibt Handle und alle Ressourcen frei |
TarCount(handle) | int64 | Anzahl der regulären Datei-Einträge |
TarName(handle, idx) | int64 pchar | Name des idx-ten Eintrags (interner Puffer — nicht free'n) |
TarSize(handle, idx) | int64 | Größe in Bytes |
TarRead(handle, idx, outBuf, maxLen) | int64 Bytes oder -1 | Liest Eintrag in outBuf |
TarFind(handle, name) | int64 Index oder -1 | Sucht Eintrag nach exaktem Namen |
import std.tar;
import std.alloc;
import std.string;
fn main(): int64 {
var w: int64 := TarWriterNew();
TarWriterAdd(w, "daten/log.txt"c, "Zeile 1\nZeile 2\n"c as int64, 16);
TarWriterAdd(w, "README"c, "TAR aus Lyx"c as int64, 11);
var rc: int64 := TarWriterSave(w, "/tmp/lyx_test.tar"c);
TarWriterFree(w);
PrintLn(StrConcat("Save rc (0 = ok): ", IntToStr(rc)));
var h: int64 := TarOpen("/tmp/lyx_test.tar"c);
if (h == 0) { PrintLn("TarOpen fehlgeschlagen"); return 1; }
PrintLn(StrConcat("Eintraege: ", IntToStr(TarCount(h))));
var i: int64 := 0;
while (i < TarCount(h)) {
PrintLn(StrConcat(StrConcat(" ", TarName(h, i) as pchar),
StrConcat(" ", IntToStr(TarSize(h, i)))));
i := i + 1;
}
var idx: int64 := TarFind(h, "README"c);
var buf: int64 := alloc(256);
var n: int64 := TarRead(h, idx, buf, 256);
poke8(buf + n, 0);
PrintLn(StrConcat("Inhalt: ", buf as pchar));
TarClose(h);
return 0;
}
Save rc (0 = ok): 0
Eintraege: 2
daten/log.txt 16
README 11
Inhalt: TAR aus Lyx
GNU tar liest das Ergebnis unverändert:
$ tar -tvf /tmp/lyx_test.tar
-rw-r--r-- 0/0 16 1970-01-01 01:00 daten/log.txt
-rw-r--r-- 0/0 11 1970-01-01 01:00 README
| Funktion | Rückgabe | Beschreibung |
|---|---|---|
TarWriterNew() | int64 Writer-Handle | Erstellt neuen leeren Writer |
TarWriterAdd(writer, name, data, dataLen) | int64 Fehlercode | Fügt Eintrag hinzu (kopiert Name + Daten) |
TarWriterSave(writer, path) | int64 Fehlercode | Schreibt Archiv in Datei (POSIX ustar) |
TarWriterFree(writer) | void | Gibt Writer und alle Einträge frei |
Geschriebene Archive: mode 0644, uid/gid 0, mtime 0. Datenblöcke werden auf 512-Byte-Grenzen aufgerundet. Das Archiv endet mit zwei Null-Blöcken (POSIX-Anforderung).
TAR selbst komprimiert nicht. Um ein .tar.gz zu erzeugen, das Archiv in einen Puffer schreiben und anschließend mit std.gzip komprimieren:
import std.tar;
import std.gzip;
import std.fs;
import std.alloc;
import std.string;
fn main(): int64 {
// 1. TAR schreiben
var w: int64 := TarWriterNew();
TarWriterAdd(w, "datei.txt"c, "Inhalt aus Lyx\n"c as int64, 15);
TarWriterSave(w, "/tmp/demo2.tar"c);
TarWriterFree(w);
// 2. TAR-Datei einlesen
var sz: int64 := FileSize("/tmp/demo2.tar"c);
var buf: int64 := alloc(sz);
ReadFile("/tmp/demo2.tar"c, buf as pchar, sz);
PrintLn(StrConcat("TAR-Groesse: ", IntToStr(sz)));
// 3. Mit gzip komprimieren
var bound: int64 := GzipCompressBound(sz);
var cbuf: int64 := alloc(bound);
var clen: int64 := GzipCompress(buf, sz, cbuf, bound);
PrintLn(StrConcat("gzip-Groesse: ", IntToStr(clen)));
WriteFile("/tmp/demo2.tar.gz"c, cbuf as pchar, clen);
free(buf, sz); free(cbuf, bound);
return 0;
}
TAR-Groesse: 2048
gzip-Groesse: 105
$ tar -tzf /tmp/demo2.tar.gz
datei.txt
Die 2048 Byte sind kein Fehler: TAR rundet jeden Eintrag auf 512-Byte-Blöcke auf und hängt zwei Nullblöcke als Endmarke an. Genau diese Nullen komprimiert gzip auf 105 Byte.
Zu lange Pfade werden stillschweigend gekürzt. Das ustar-Namensfeld fasst 100 Byte;TarWriterAddnimmt auch längere Pfade an und meldet0(Erfolg),TarWriterSaveschreibt dann den auf 100 Zeichen abgeschnittenen Namen. Nachgemessen mit einem 110 Zeichen langen Pfad — sowohlTarNameals auch GNU tar zeigen anschließend den gekürzten Namen. Die ustar-Erweiterung mitprefix-Feld und GNU LongLink sind nicht umgesetzt; Pfade selbst auf ≤ 100 Byte prüfen.
std.tar schreibt keine echten Metadaten.5), Symlinks und Gerätedateien übersprungen; beim Schreiben entstehen Ordner allein durch Schrägstriche im Namen.TarWriterSave liefert 0 bei Erfolg, TarOpen dagegen 0 im Fehlerfall.TarRead terminiert nicht — Nullbyte selbst setzen, wenn der Puffer als Text ausgegeben wird.pchar: TarOpen(„/tmp/a.tar“c) — ohne as int64. std.zip macht es umgekehrt.| Handle | Freigabe |
|---|---|
TarOpen → Reader-Handle | TarClose(handle) |
TarWriterNew → Writer-Handle | TarWriterFree(writer) |
TarName → interner Puffer | nicht free'n — gehört dem Handle |
outBuf in TarRead | Aufrufer allokiert, Aufrufer gibt frei |
Letzte Aktualisierung: 2026-08-13 — Beispiele lauffähig gemacht, ausgeführt und mit GNU tar gegengelesen (lyxc 1.0.17K); belegt und dokumentiert: Pfade über 100 Byte werden stillschweigend gekürzt. .tar.gz-Beispiel neu geschrieben.
Codebeispiele geprüft: gegen lyxc 1.2.5C übersetzt (Prüflauf 2026-09-08 über die gesamte Doku: 574 Vollprogramme, 0 echte Fehler; zusätzlich 5159 Aufrufe gegen die pub fn-Signaturen in aurum/std gehalten, 0 Abweichungen).