Signatur
Beschreibung
Swoole\Mmap kapselt den systemnahen mmap()-Systemaufruf und ermöglicht es, Dateien oder anonyme Speicherbereiche direkt in den virtuellen Adressraum des Prozesses einzublenden. Das Betriebssystem verwaltet dabei das Caching selbst, was besonders bei großen Dateien deutlich weniger Kopieroperationen bedeutet als klassische read()/write()-Aufrufe.
Typische Anwendungsfälle sind Inter-Prozess-Kommunikation (IPC) zwischen mehreren Worker-Prozessen, das schnelle Lesen großer Binär- oder Log-Dateien sowie das gemeinsame Nutzen von Datenpuffern ohne explizite Serialisierung. Da der gemappte Bereich direkt aus dem Page-Cache des Kernels bedient wird, entfällt ein Userspace-Puffer-Roundtrip vollständig.
Über die statische Methode Swoole\Mmap::open() wird eine Datei geöffnet und ein Swoole\Mmap-Objekt zurückgegeben, das anschließend wie ein String-Puffer gelesen und beschrieben werden kann. Das Objekt implementiert dabei das ArrayAccess-Interface, sodass einzelne Bytes byteweise indiziert werden können.
Hinweis: Swoole\Mmap steht nur auf Linux und macOS zur Verfügung und erfordert, dass die zugehörige Swoole-Extension mit der entsprechenden Unterstützung kompiliert wurde. Unter Windows wird diese Klasse nicht unterstützt.
Beispiele
Datei per mmap öffnen und Inhalt lesen
<?php
// Datei vorbereiten
file_put_contents('/tmp/test.bin', str_repeat('A', 1024));
// Datei per mmap in den Adressraum einblenden
$mmap = Swoole\Mmap::open('/tmp/test.bin');
if ($mmap === false) {
echo 'Fehler beim Öffnen der mmap-Datei';
exit(1);
}
// Gesamten Inhalt als String lesen
$content = (string) $mmap;
echo 'Länge: ' . strlen($content) . ' Bytes' . PHP_EOL;
// Byteweiser Zugriff per Array-Index
echo 'Erstes Byte: ' . $mmap[0] . PHP_EOL;
Shared Memory zwischen Swoole-Worker-Prozessen nutzen
<?php
// Gemeinsame Datei als Shared Buffer anlegen
$path = '/tmp/swoole_shared.bin';
file_put_contents($path, str_pad('', 4096, "\0"));
$mmap = Swoole\Mmap::open($path, 4096, 0);
$server = new Swoole\Server('127.0.0.1', 9501);
$server->on('WorkerStart', function ($server, $workerId) use ($mmap) {
if ($workerId === 0) {
// Worker 0 schreibt Daten in den gemappten Bereich
$msg = 'Hello from Worker 0';
for ($i = 0; $i < strlen($msg); $i++) {
$mmap[$i] = $msg[$i];
}
echo '[Worker 0] Daten geschrieben.' . PHP_EOL;
} else {
// Worker 1 liest den Inhalt
Swoole\Timer::after(200, function () use ($mmap) {
$data = substr((string) $mmap, 0, 20);
echo '[Worker 1] Gelesen: ' . trim($data, "\0") . PHP_EOL;
});
}
});
$server->set(['worker_num' => 2, 'daemonize' => false]);
$server->start();
// Wichtig · Fallstricke
Plattform: Swoole\Mmap ist ausschließlich auf POSIX-kompatiblen Systemen (Linux, macOS) verfügbar. Auf Windows-Systemen wird diese Klasse nicht unterstützt und führt zu einem fatalen Fehler.
Synchronisation: Wird ein gemappter Bereich von mehreren Prozessen oder Threads gleichzeitig beschrieben, sind explizite Synchronisationsmechanismen (z. B. Swoole\Lock) notwendig, um Race Conditions und Datenverlust zu vermeiden.
Dateigröße: Die Größe der zugrunde liegenden Datei muss vorab festgelegt sein. Das Vergrößern einer bereits gemappten Datei während der Laufzeit erfordert ein Neu-Mapping (open() erneut aufrufen). Das Schreiben über das Ende der Datei hinaus führt zu einem Segmentation Fault.
Dokumentationslage: Die offizielle Swoole-Dokumentation zu Swoole\Mmap ist spärlich. Methoden und Verhalten können sich zwischen Minor-Versionen ändern. Ein Blick in die Swoole-Quelltexte sowie die CHANGELOG-Dateien wird empfohlen.