UNIXwork

Tags

c unix dav shell linux xattr solaris links x11 java rant webdav fun gnome apple sync wtf oracle ldap network xnedit windows analytics macos benchmark curl apache bsd graalvm mac virtualbox arm zfs rhel microsoft tomcat freebsd hardware sparc

Memory-Alignment ist kein Mythos

19. März 2016

Vor kurzem hab ich versucht ein kleines Stück Software auf einer exotischen RISC-Plattform zum Laufen zu bringen, doch bei der Ausführung crashte das Programm. Der Grund war Code der in etwa das machte:

int *intptr = (int*)(str + 15);

Um von einer bestimmten Stelle aus einem Speicherbereich ein int zu lesen wurde ein char* verschoben und zu einem Integer-Pointer gecasted. Beim anschließenden Zugriff auf diesen Pointer stürzte das Programm ab. Der Grund ist, dass nicht alle CPU-Architekturen beliebig wahllose Speicherzugriffe erlauben, sondern nur auf richtig ausgerichtete Adressen, die ein Vielfaches von n (meistens 4) sind. Siehe Data structure alignment

Jetzt sind allerdings die verbreitetsten CPU-Architekturen x86 und ARM, und die kommen auch mit misaligned Memory klar. Warum sollte man das dann überhaupt beachten? Weil auch wenn es auf diesen CPUs fehlerfrei funktioniert, hat es zumindestens Performance-Auswirkungen. Es werden dann nämlich einfach 2 Speicherzugriffe gemacht. Ich habe ein interessanten Blogpost zu dem Thema gefunden, in dem jemand ein Performance-Test gemacht hat. Das Ergebnis ist, dass im schlimmsten Fall die Speicherzugriffe doppelt so lange dauern.

Wenn man jetzt aber doch auf nicht-ausgerichteten Speicher zugreifen will, kann man immer noch memcpy nutzen, denn das kann die Adresse berichtigen und dann größtenteils optimierte Speicherzugriffe machen.

2,5 und 5 GBit Ethernet

18. März 2016

Gigabit-Ethernet gibt es jetzt schon lange (der Standard für 1000BASE-T ist von 1999) und lange Zeit war es ausreichend, zumindestens im Consumerbereich. Mit einzelnen Festplatten hat man selbst bei sequenziellen Schreib- und Leseoperationen weniger als 100 Mb/s geschafft. Seit ein paar Jahren sieht das jedoch schon anders aus. SSDs sind weit verbreitet und selbst gammelige Festplatten lasten GbE voll aus. Da bald selbst WLAN schneller als 1 Gbit/s ist, wäre es eigentlich an der Zeit, dass sich 10 GbE auch im Consumerbereich durchsetzt.

Aber nein, das passiert wohl nicht. Stattdessen kommt Ethernet mit 2,5 und 5 Gbit/s. Wie heise berichtet gibt es sogar schon ein Switch dafür (allerdings auch nicht Consumertauglich). Der Standard für diese Ethernet-Varianten soll Mitte 2016 fertig sein. Wann es dann noch mehr Hardware gibt, vor allem passende NICs, PCs, Notebooks und Mainboards mit 5 GbE, wird natürlich spannend. Ich vermute erst dann, wenn jeder PCIe-basierte SSDs hat, die locker 1 Gb/s schreiben können und damit schon langsam 10 GbE auslasten.

Aber ich gebe zu, es ist zumindestens ein wenig Fortschritt. Lieber das, als 10 weitere Jahre mit 1 GbE.

Standardausgabe in die Zwischenablage umleiten mit xclip

16. Februar 2016

Mit xclip kann man von der Kommandozeile aus mit der X11-Zwischenablage interagieren. Das Tool kann seine Eingabe von stdin in die Zwischenablage speichern oder die Zwischenablage auf stdout ausgeben.

Folgendes Beispiel speichert die Ausgabe von ls in der Zwischenablage ls | xclip -selection clipboard

Die Zwischenablage auf stdout ausgeben kann man mit xclip -selection clipboard -o

stat Benchmark

09. Februar 2016

Der Syscall stat wird benutzt um an Informationen wie Dateigröße oder Änderungsdatum einer Datei zu gelangen. Die Funktion erwartet als Argumente nur einen Dateipfad und einen Buffer. Daneben gibt es noch die Variante fstat, die statt eines Dateipfades einen Filedescriptor erwartet, und fstatat, die den Filedescriptor eines geöffneten Verzeichnisses und einen Pfad relativ zu dem Verzeichnis erwartet.

int stat(const char *restrict path, struct stat *restrict buf);
int fstat(int fildes, struct stat *buf);
int fstatat(int fd, const char *restrict path,
    struct stat *restrict buf, int flag);

Mich hat jetzt ein Performancevergleich zwischen den Funktionen interessiert. Zum einen für den Fall, dass man für jede Datei in einem Verzeichnis stat aufrufen will. Hier würde sich der Einsatz von fstatat anbieten. Der andere Fall wäre, wenn man eine Datei öffnen und stat-en will. Um dies zu testen hab ich ein primitives Programm geschrieben, dass man hier findet. Das Programm erwartet als Argument einen Pfad zu einem Verzeichnis, welches es zunächst ließt. Danach führt es 4 Tests durch und misst für jeden die Zeit:

  • test_stat: Für jede Datei des Verzeichnisses wird stat aufgerufen.
  • test_fstatat: Für jede Datei wird fstatat aufgerufen.
  • test_open_stat: Jede Datei wird mit open geöffnet und danach noch stat aufgerufen.
  • test_fstat: Jede Datei wird geöffnet und fstat aufgerufen.

Ein kleiner Test unter Linux ergab:

test 195 files:

test_stat
time: 496386 ns

test_fstatat
time: 246039 ns

----------------------------------------

test_open_stat
time: 1106593 ns

test_open_fstat
time: 885549 ns

Ähnliche Ergebnisse konnte ich auch unter FreeBSD und Solaris, mit Festplatten und SSDs, reproduzieren. Der Vergleich zwischen test_stat und test_fstatat zeigt, dass fstatat deutlich schneller ist. In beiden Tests wird auch nur pro Datei jeweils ein Syscall aufgerufen. Bei test_open_stat und test_open_fstat wird in beiden Fällen zunächst open benutzt um die Datei zu öffnen und es zeigt sich, dass in diesem Fall fstat auch schneller ist als stat, allerdings fällt der Unterschied hier nicht so sehr ins Gewicht.

Shell-Session im Hintergrund mit GNU Screen

07. Oktober 2015

GNU Screen ist eine Art Fenstermanager für die Konsole, der es erlaubt, mehrere getrennte Sitzungen innerhalb eines Terminals zu benutzen. In Zeiten grafischer Terminal-Emulatoren wird dies vielleicht nicht so oft gebraucht, ein weiteres sehr nützliches Feature ist jedoch, dass man eine Screen-Session unterbrechen, und später wieder fortsetzen kann. Die unterbrochenen Sessions laufen im Hintergrund weiter, auch wenn die Shell, von der aus man ursprünglich screen gestartet hat, beendet wird. Dies ist sehr praktisch, wenn man z.B. per ssh auf einem entfernten Rechner ein Programm längere Zeit laufen lassen will.

Nach dem Start von screen erhält man eine Shell die in einer Screen-Session läuft. Diese kann mit Strg+A gefolgt von D getrennt werden und später mit screen -r wieder hergestellt werden.

Zurück Weiter