Re: Kodierung von Datei- und Verzeichnisnamen

From: Marc Santhoff <M.Santhoff(at)web.de>
Date: Sun, 26 May 2013 12:13:21 +0200

Am Freitag, den 24.05.2013, 14:32 +0200 schrieb Oliver Fromme:
> Marc Santhoff wrote:
> > wie kann ich rausfinden, in welcher Kodierung die Buchstaben von Datei-
> > und verzeichnisnamen geschrieben sind?
> >
> > Ich habe mit "neueren" Namen Probleme mit Umlauten und Sonderzeichen -
> > das heißt natürlich nicht ich sondern ein Programm, daß ich benutze ;) -
> > und nun zufällig gesehen, daß ältere Einträge mit eben denselben Zeichen
> > korrekt dargestellt werden.
>
> Das ist das typische Symptom, wenn ein Programm ISO8859-*
> mit UTF-8 (oder UCS-2 o.ä.) verwechselt. Bei manchen
> Programmen kann man das konfigurieren, manche halten sich
> auch einfach an die locale-Variablen, siehe unten ...

So ist es tatsächlich.

> Wenn Du wissen möchtest, mit welchen Bytes Dateinamen in
> einem Verzeichnis codiert sind, kannst Du einfach hd(1) auf
> das Verzeichnis machen, z.B. »hd /usr/bin«. Damit bekommst
> Du einen Hexdump des Verzeichnisinhalts, wo neben einigen
> Binärdaten auch die Dateinamen enthalten sind.

Ah, schön. Ich hab bestimmt länger als ein Jahrzent keinen Hexdump
benötigt, deswegen war mir auch hd nicht geläufig.

> UTF-8 erkennt man ganz einfach daran, dass bei Umlauten
> mehrere Bytes codiert sind, bei ISO8859-* ist es nur eines.
> Bei UCS-2 wiederum wird _jedes_ Zeichen mit zwei Bytes
> codiert.

Ersteres ist der Fall, und diese Umlaute werden korrekt dargestellt. Also ist
das betreffende Programm auf UTF-8 eingestellt.

Jetzt fragt sich nur noch, warum ein Tcl/Tk-Programm einfach so "exotisch
kodiert"[tm] daherkommt, entweder der Interpreter ist modernisiert und mag
$LANG nicht oder das Programm macht Murks oder nichts.

Es ist übrigens das von mir schon ewig benutzte TkDesk (x11-fm/tkdesk),
das mittlerweile sogar ganz aus den Ports rausgeflogen ist, weil es
nicht nur keinen Maintainer sondern noch nicht mal mehr einen
Programmierer gibt, der es noch pflegt. :P

> (Der Trick mit hd(1) funktioniert allerdings nicht bei allen
> Dateisystemen. Bei UFS geht es, bei TMPFS dagegen nicht.)
>
> Beispiel:
>
> $ echo $LC_CTYPE
> de_DE.ISO8859-15
> $ mkdir /var/tmp/testdir
> $ touch /var/tmp/testdir/fööbär

LOL, schöner Verzeichnisname.

> $ hd /var/tmp/testdir
> 00000000 36 00 00 00 0c 00 04 01 2e 00 00 00 71 0e 01 00 |6...........q...|
> 00000010 0c 00 04 02 2e 2e 00 00 3a 00 00 00 e8 01 08 06 |........:...è...|
> 00000020 66 f6 f6 62 e4 72 00 ff 00 00 00 00 00 00 00 00 |fööbär.ÿ........|
> 00000030 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 |................|
> *
> 00000200
>
> Hier kann man sehen, dass die Umlaute durch einzelne Bytes
> repräsentiert werden (f6 = 'ö', e4 = 'ä'), also handelt es
> sich um ISO8859-*.

Lange Suche brachte ein 'ü' als $c3 $bc hervor. Alle ISO8859-Kodierungen
werden falsch dargestellt. Die benutze ich aber eigentlich.

$ hd . | grep -C2 System_
000001e0 65 69 74 65 72 2e 68 74 6d 6c 00 ff 00 00 00 00 |eiter.html.ÿ....|
000001f0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 |................|
00000200 12 19 1f 00 30 00 04 27 53 79 73 74 65 6d 5f 76 |....0..'System_v|
00000210 65 72 73 63 68 6c c3 bc 73 73 65 6c 6e 5f 6d 69 |erschlüsseln_mi|
00000220 74 5f 67 65 6c 69 28 38 29 5f 66 69 6c 65 73 00 |t_geli(8)_files.|
00000230 47 68 1e 00 30 00 08 26 53 79 73 74 65 6d 5f 76 |Gh..0..&System_v

> Die Hex-Codes für ISO8859-1 (das weitgehend identisch ist
> mit ISO8859-15) kann man übrigens auch in der Datei
> /usr/share/misc/latin1 nachschlagen. Oder bei Google.

Klar.

> > Und was beeinflußt die Auswahl der Codepage, sind das LANG und LC_*?
>
> Siehe die Manpages environ(7) und setlocale(3).

Ah ja.

> Für die Zeichenkodierung ist LC_CTYPE zuständig. Auf welche
> Werte man das setzen kann, sagt »ls /usr/share/locale«.
> Ist es nicht gesetzt, gibt LANG den Default vor (ebenso für
> alle andern LC_*-Variablen). LC_ALL wiederum hat Priorität
> vor allen anderen Variablen.
>
> Das Locale-System schaut also in der folgenden Reihenfolge
> nach, bis es einen gesetzten Wert findet:
> - LC_ALL
> - LC_* (LC_CTYPE usw.)
> - LANG
>
> Ich persönlich halte es so, dass ich LANG und LC_ALL *nicht*
> setze, sondern die einzelnen Variablen dediziert. Das hat
> den Vorteil, dass ich mit LC_CTYPE und LC_COLLATE ein Locale
> mit deutschen Umlauten und Sortierung verwenden kann,
> während z.B. Meldungen und Zahlen (LC_MESSAGES, LC_NUMERIC)
> auf englisch ausgegeben und formatiert werden.

Mir sind die Nebenwirkungen bekannt, aber zuletzt habe ich faul immer
$LANG gesetzt. Bei aus meiner Sicht wirklich kritischen Fällen sind
immer nur Dokumenteninhalte oder Datenbanken betroffen, beides jeweils
gut zu handhaben, deswegen hat's mich nicht intressiert.

Nun werde ich mir aber mal Zeit nehmen, einmalig den Satz LC_-Variablen
zu setzen, ist ja nicht so schwer. ;)

Vielen Dank, jetzt bin ich mit einer konkreten Diagnose schonmal auf der
richtigen Spur.

-- 
Marc Santhoff <M.Santhoff(at)web.de>
To Unsubscribe: send mail to majordomo(at)de.FreeBSD.org
with "unsubscribe de-bsd-questions" in the body of the message
Received on Sun 26 May 2013 - 12:15:52 CEST

search this site