Am Dienstag, 2. Januar 2007 23:00 schrieb Klaus Klein:
> Max Trense wrote:
> > So einfach ist es eben nicht unbedingt. Striping bedeutet, dass
> > aufeinanderfolgende Blöcke (auf den Arbeitsspeicher übertragen sind das
> > dann wohl am ehesten Pages) auf unterschiedlichen physikalischen Medien
> > befinden. Der entscheidende Vorteil dieser Technik kommt zum Tragen, wenn
> > eine Datei sequentiell in den Arbeitsspeicher gelesen wird. Bei diesem
> > Vorgang wird jeder einzelne Block gelesen und an eine bestimmte Stelle in
> > den Arbeitsspeicher geschrieben. Da aber die meisten Komponenten eines
> > Computers Daten viel schneller übertragen können, als selbst die
> > schnellsten Festplatten, warten logischerweise während der Übertragung
> > alle diese Komponenten auf die Daten von der Festplatte. Legt man jetzt
> > aber die einzelnen Blöcke auf unterschiedliche Medien und ist die
> > Read-Ahead-Funktionalität richtig konfiguriert, kann man eben mehrere
> > Blöcke gleichzeitig laden. Selbst mit vielen Festplatten erreicht man so
> > kaum die Geschwindigkeit des Arbeitsspeichers, kann jedoch bei einer
> > genügenden Anzahl von Festplatten die Durchsatzrate erheblich steigern.
> > Diese Steigerung liegt im Regelfall bei nahezu 100%, was das Striping
> > gerade für große Dateien recht interessant macht.
>
> Um das kurz auf den Punkt zu Bringen: Bei grossen Dateien, welche
> sequenziell gelesen werden, wird das optimum da liegen wo der Read-Ahead
> ein ganzzahliges mehrfaches der Groesse eines Stripes entspricht.

Genau. Das auf jeden Fall. Allerdings ist der Read-Ahead-Algorithmus 
wesentlich wichtiger als die Größe des Read-Ahead-Buffers. Allerdings hat man 
als reiner Bediener auf den Algorithmus wenig Einfluss :-(

> > Ein Problem ist aber auch hier der Overhead. Der fällt im
> > Vergleich zur Performancesteigerung zwar recht gering aus, aber es gibt
> > eben auch Fälle, in denen es nicht möglich ist, mehrere Blöcke parallel
> > zu lesen. Eben dieser Fall ist bei Swap gegeben: Arbeitsspeicher wird in
> > der Regel nicht in zusammenhängenden Clustern benötigt, sondern meistens
> > nur einzelne Pages. Und das entspricht dem Laden eines einzelnen Blocks
> > von der Festplatte.
>
> Kurze Frage: Warum müssen Pages, gerade bei multithreaded Anwendungen
> oder MultiKern/Prozessoren, immer 'sequenziell' geswapped (Autsch, ganz
> übles Neudeutsch) werden? 

Das werden Sie nicht. Das Betriebssystem (hier natürlich vor allem die 
Speicherverwaltung) wird eine bestimmte Menge an Speicherseiten auslagern, 
wenn der Systemspeicher knapp wird. Welche das sind, das bestimmt ein 
spezieller Paging-Algorithmus. Der lässt sich im Linux-Kernel zum Beispiel 
auch auswählen (Allerdings ist der voreingestellte Algo wohl definitiv der 
Beste). Diese Speicherseiten sind in der Regel weder zusammenhängend, noch 
stehen sie in irgendeiner Relation zueinander. Und genau da beginnt natürlich 
auch das große Problem. Während des Einlagerns von Speicherseiten wird wieder 
zufällig auf eine Speicherseite zugegriffen. Welche Speicherseite das sein 
wird, lässt sich nicht vorhersagen und damit auch nicht optimieren. Es gab 
vor einigen Jahren mal einen Ansatz, Page-Faults (Also die Ereignisse, die 
zum Einlagern einer Speicherseite führen) in Gruppen zusammenzufassen und 
über Heuristiken vorhersagbar zu machen. Allerdings steht der Aufwand für 
diese Methodik wohl in keinem Verhältnis zur erreichten 
Performance-Steigerung.

> Ich denke schon das hier mächtig 
> 'parallelisiert' werden kann. Zudem ist die Wahrscheinlichkeit, das die
> Blöcke welche gelesen oder geschrieben werden müssen auf
> unterschiedlichen Platten liegen, beim Stripping (über zwei oder mehrere
> Platten) nun mal nahe 50:50 (bei zwei) oder grösser (bei mehreren
> Platten). Somit sollte eigentlich genau hier das Thema mit der
> Verteilung des Overheads (Kopfbewegung) greifen.

Das sieht natürlich erstmal so aus. Allerdings musst Du auch bedenken, dass 
für diese Optimierung mehr als ein Block in einem gewissen Zeitabschnitt 
gelesen werden muss. Im Falle von Page-Faults kann aber eben das nicht 
vorhergesagt werden. Man würde also eine Weile warten und mehrere Page-Faults 
sammeln, damit man sie dann gemeinsam bearbeiten kann. Da aber nicht 
vorhergesagt werden kann, ob in den nächsten n Zeiteinheiten weitere (und 
wenn ja, wieviele) Page-Faults auftreten, muss man auf jeden Fall bis zu 
einem bestimmten Timeout warten. Ist innerhalb dieses Timeouts mindestens ein 
weiterer Page-Fault aufgetreten, könnte diese Methode tatsächlich etwas 
schneller sein, als das herkömmliche Lesen einer Speicherseite. Ist jedoch 
kein weiterer Page-Fault aufgetreten, kommt zu der Zeit, die der Rechner 
benötigt, um eine Seite einzulagern natürlich noch die Zeit des Timeouts 
hinzu. Leider ist der letzte Fall der deutlich häufigere (vgl. Stallings, 
William: Betriebssysteme).
Ein weiterer Einflussfaktor ist die Reaktionszeit von Prozessen. Natürlich 
kann ein Prozess, der einen Page-Fault ausgelöst hat, nicht fortgesetzt 
werden, bis der Page-Fault korrigiert ist. Dadurch würden im schlimmsten Fall 
mehrere Prozesse hängen, bis der Timeout abgelaufen ist.

> > Da dieser Vorgang nicht parallelisierbar ist, gibt es natürlich
> > auch keine Performance-Steigerung.
>
> Nochmal. Warum nicht?

Weil auf die Daten in zufälliger Reihenfolge nacheinander zugegriffen wird. 
Das heißt, man kann nicht anhand des aktuell abgefragten Datums auf die 
zukünftig abgefragten Daten schließen.

> BTW. die Grösse einer Page ist nicht zufällig ein Vielfaches von 512
> Byte und somit ein ideales Vielfaches der Blockgrösse, was dann wieder
> ideal zum Read-Ahead passt?

Die Größe einer Page hängt vor allem vom verwendeten Paging-Algorithmus ab. 
Diese Größe muss allerdings nicht mal für alle verwendeten Pages fest sein. 
Der Buddy-Algorithmus verwendet zum Beispiel statt der Pages sogenannte 
Buddies, die für jede Invokation der Buddy-Funktion halbiert werden, bis ein 
Buddy von optimaler Größer erreicht ist.

> > Einen ähnlichen Fall gibt es bei sehr
> > kleinen Dateien. Natürlich könnte man nun die Blockgröße des Dateisystems
> > auf einen kleineren Wert konfigurieren. Das bringt allerdings wegen der
> > Seektime der Festplatte nicht besonders viel.
>
> Bei der Änderung der Blockgrösse wird man bei einer nicht fragmentierten
> Datei wohl keinen Unterschied messen, zumindest nicht wenn die Datei
> nicht über die Zylindergrenze der Platte hinausreicht und somit ohne
> Kopfbewegung gelesen wird. (und so ein Zylinder ist schon mächtig gross.
> ;-) )

Was wiederum auch nur für das sequentielle Lesen von Daten von der Festplatte 
stimmt. Bei mehreren kleinen Dateien, die über die Partition verteilt sind 
(das ist genau das Szenario des ausgelagerten Speichers; hier liegen mehrere 
Speicherseiten an unterschiedlichen Stellen im Swap) ist natürlich im 
schlimmsten Fall (übrigens streng genommen auch im durchschnittlichen Fall) 
für jeden einzelnen Lesevorgang eine Neupositionierung nötig.
Ausserdem lässt sich Swap nicht sinnvoll defragmentieren, da sich der Inhalt 
regelmäßig ändert.

> > Die Abwägung zwischen Striping oder nicht ist also wirklich nicht ganz
> > trivial und definitiv nicht allgemein entscheidbar ;-)
>
> Genau dies kann ich aber aus Deinen Ausführungen eben nicht entnehmen. :-(

Nimm an, Du hast einen Webserver mit vielen (kleinen) statischen Seiten. In 
diesem Fall ist Striping völlig überflüssig, weil jede andere 
Optimierungstechnik (von denen die meisten einen geringeren Overhead haben) 
nahezu das selbe Ergebnis bringt. Hast Du allerdings einen Downloadserver mit 
vielen größeren Dateien, dann wird Dir Striping sicherlich viel mehr bringen, 
als der Overhead schadet. 

Allerdings solltest Du natürlich auch noch die Geschwindigkeit des Bus, an dem 
die Festplatten hängen, in Betracht ziehen. Ausserdem die Geschwindigkeit der 
Platten selbst. Hast du beispielsweise eine langsame und eine schnelle 
Festplatte, wird das Striping des LVM böse auf die Schnauze fallen. Denn 
dieser Read-Ahead-Algorithmus arbeitet mit Data-Windows (als ob das nicht 
schon schlimm genug wäre ;-) ). Das bedeutet, da er die Stripes (gleicher 
Größe) auf der schnellen Platte natürlich schneller liest, dass die Stripes 
dieser Platte das Ende des Fensters erreichen, während die Stripes der 
langsamen Platte das Verschieben des Fensters blockieren. Damit bremst die 
langsamste Platte im Verbund natürlich alle anderen aus.

Schaut man sich bei AIX um, gibt es dort eine Implementation eines 
Volume-Managers, die für unterschiedlich schnelle Platten unterschiedlich 
große Stripes erlaubt... All diese Dinge (und leider noch einige mehr, die 
glücklicherweise nicht in meiner Abschlußprüfung vorkommen :-) ) sollte man 
aber wissen, wenn man wirklich die optimale Performance erreichen will. Nicht 
umsonst beschäftigt Oracle mehr als 200 wirklich fähige Mitarbeiter mit 
solchen Optimierungen.

> >> Wo ist da eigentlich der Unterschied zwischen zusammenhängendem Speicher
> >> und Dateien?
> >
> > Hauptsächlich in der Blockgröße und der Zugriffsmethode.
>
> Hmm, versteh ich nicht. ;-)
> Die Blockgrösse auf der Platte ist für beide gleich und bei 'ner
> Datenbank gibt es bestimmt genauso viel 'Random-Access' wie beim Swappen.

Wenn das Datenbanksystem geschickt arbeitet sicherlich nicht. Schau Dir mal 
an, wie viel Aufwand das Postgres-Team in die Optimierung ihrer 
Datenstrukturen steckt. In diesem Fall bemüht man sich, zusammenhängende 
Daten der Datenbank (und das wird durchaus auch zur Laufzeit optimiert) auch 
an nahe zusammenliegenden Stellen des Dateisystems zu speichern. Dadurch kann 
das Datenbanksystem, das ja zumindest alle Adressen des aktuellen Queries 
kennt, diese Lesezugriffe zusammenfassen.

> Und eine Swap-Partition ist unter Unix sowieso wie alles eine Datei.
> (*duckundweg*)

Das stimmt. Das macht die Sache allerdings nicht besser. Die 
Speicherverwaltung kann (im Gegensatz zu einer Datenbank) die Daten kaum 
zueinander in Relation setzen. Dadurch ist es kaum möglich, eine sinnvolle 
Strukturierung innerhalb des Swapspeichers umzusetzen. Und genau das bricht 
jedem Performancegedanken das Genick ;-)

Max


-- 
Max Trense -- [EMAIL PROTECTED] -- www.trense.info
--
----------------------------------------------------------------------------
PUG - Penguin User Group Wiesbaden - http://www.pug.org

Antwort per Email an