SuSE Linux: Versionen ab 8.2
Voraussetzung ist ein Grundverständnis des Drucksystems und ein sicherer Umgang mit CUPS, Bash-Scripten und den üblichen Kommandozeilentools.
/etc/cups/mime.types
und /etc/cups/mime.convs
und ggf. pro Warteschlange durch *cupsFilter
Einträge in
der PPD Datei festgelegt ist.
/etc/cups/mime.types
den Mime Typ
application/postscript
.application/postscript application/vnd.cups-postscript 66 pstops
/etc/cups/mime.convs
werden Daten vom Mime Typ
application/postscript
mit dem CUPS-Filter pstops
(also mit /usr/lib/cups/filter/pstops
) in Daten vom
Mime Typ application/vnd.cups-postscript
umgewandelt.66
Einheiten.
application/vnd.cups-postscript
werden zum PostScript Drucker geschickt.
/etc/cups/mime.types
den Mime Typ
text/plain
.text/plain application/postscript 33 texttops
/etc/cups/mime.convs
werden Daten vom Mime Typ
text/plain
mit dem CUPS-Filter texttops
(also mit /usr/lib/cups/filter/texttops
) in Daten vom
Mime Typ application/postscript
umgewandelt.33
Einheiten.
application/postscript
mit dem CUPS-Filter /usr/lib/cups/filter/pstops
in Daten vom
Mime Typ application/vnd.cups-postscript
umgewandelt und
die Kosten für diese Umwandlung sind 66
Einheiten.application/vnd.cups-postscript
werden zum PostScript Drucker geschickt.
application/postscript
mit dem CUPS-Filter /usr/lib/cups/filter/pstops
in Daten vom
Mime Typ application/vnd.cups-postscript
umgewandelt.
*cupsFilter
Eintrag in der PPD Datei wie z.B.
bei einer Foomatic PPD Datei:*cupsFilter: "application/vnd.cups-postscript 0 foomatic-rip"
application/vnd.cups-postscript
mit dem Foomatic-Filter /usr/lib/cups/filter/foomatic-rip
in druckerspezifische Daten (z.B. PCL-Daten für einen PCL Drucker)
umgewandelt.
text/plain
mit dem CUPS-Filter /usr/lib/cups/filter/texttops
in Daten vom
Mime Typ application/postscript
umgewandelt.
application/postscript
mit dem CUPS-Filter /usr/lib/cups/filter/pstops
in Daten vom
Mime Typ application/vnd.cups-postscript
umgewandelt.
application/vnd.cups-postscript
mit dem Foomatic-Filter /usr/lib/cups/filter/foomatic-rip
in druckerspezifische Daten umgewandelt.
/usr/lib/cups/filter/texttops
- siehe:/usr/lib/cups/filter/pstops
- siehe:/usr/lib/cups/filter/foomatic-rip
- siehe:Die direkte Lösung ist, im Anwendungsprogramm, was das PostScript Dokument produziert, die Auflösung und die Farbtiefe von eingebetteten Grafiken zu reduzieren.
Problematische PostScript Dokumente können auch vom Drucksystem wie oben
beschrieben in PCL-Daten (ggf. in relativ geringer Auflösung und/oder Farbtiefe)
umgewandelt werden.
PCL-Daten brauchen (je nach Auflösung und/oder Farbtiefe) wesentlich
weniger Speicher im Drucker, um zu Papier gebracht zu werden.
Normalerweise können PostScript Drucker auch via PCL angesprochen werden.
Meist haben PostScript+PCL Drucker eine automatische Erkennung des
Datentyps und schalten automatisch zwischen PostScript- und PCL-Modus um.
Die einfachste Lösung ist, eine zusätzliche Warteschlange für einen PostScript+PCL Drucker anzulegen, die immer PCL-Daten liefert, indem für die zusätzliche Warteschlange eine PPD-Datei für einen kompatiblen PCL Drucker verwendet wird.
Mehrere Warteschlangen für denselben Drucker haben aber den Nachteil,
dass alle Warteschlangen für den Drucker abzufragen sind, um alle
anstehenden bzw. aktiven Druckjobs für den Drucker angezeigt zu bekommen.
Bei einem einzelnen Drucker oder bei einem Einzelplatzsystem ist das kein
Problem, aber wenn mehrere Drucker im Netzwerk von vielen Benutzern verwendet
werden, sind mehrere Warteschlangen pro Drucker zu unübersichtlich.
Daher soll es nur eine einzige Warteschlange pro PostScript+PCL Drucker
geben, die wahlweise auch PCL-Daten liefern kann, um problematische
PostScript Dokumente via PCL (ggf. in relativ geringer Auflösung
und/oder Farbtiefe) drucken zu können.
Die direkte Lösung ist, im Anwendungsprogramm, was das PostScript Dokument
produziert, den PostScript Level entsprechend festzulegen.
Oft gibt es aber keine solche Möglichkeit.
Die einfachste generelle Lösung ist, eine zusätzliche Warteschlange für den
Drucker anzulegen, wobei die generische Foomatic PPD-Datei
/usr/share/cups/model/Generic/PostScript_Printer-Postscript.ppd.gz
verwendet wird, denn hier kann durch eine Vorverarbeitung mit Ghostscript
PostScript Level 1 oder Level 2 erzeugt werden.
Die beste Lösung ist, im Anwendungsprogramm, was das PostScript Dokument
produziert, die notwendingen Fonts in das PostScript Dokument einzubetten.
In gewissen Fällen genügt es, eine zusätzliche Warteschlange mit der obigen
generischen Foomatic PPD-Datei zu verwenden, denn hier können durch die
Vorverarbeitung mit Ghostscript zumindest die Ghostscript Fonts in das
PostScript Dokument eingebettet werden.
/etc/cups/ppd/Warteschlange.ppd
wird direkt unter der Zeile*cupsFilter: "application/vnd.cups-postscript 0 foomatic-rip"
*cupsFilter: "text/plain 0 TextToPrinter"
eingefügt.*cupsFilter
Eintrag in der PPD Datei dient immer
zur Umwandlung in druckerspezifische Daten, die danach direkt zum
Drucker geschickt werden.text/plain
ohne dass andere Filter zwischengeschaltet
werden, mit /usr/lib/cups/filter/TextToPrinter
direkt in
druckerspezifische Daten umgewandelt.text/plain
gedruckt werden, hat
das für diese Warteschlange zur Folge, dass es keine Möglichkeit gibt,
die Druckausgabe individuell anzupassen, weil dazu die entsprechenden
CUPS- und Foomatic-Filter benötigt werden.
/usr/lib/cups/filter/TextToPrinter
ist das selbst zu
erstellende Filter-Script zur druckerspezifischen Umcodierung von
ASCII-Text.
In vielen Fällen haben Nadeldrucker eine zum IBM-PC kompatible
Zeichencodierung eingebaut.
Mit dem Befehl recode "lat1..ibmpc"
erfolgt eine
Umcodierung in die IBM-PC kompatible Zeichencodierung.
Wenn der Drucker an der ersten parallelen Schnittstelle angeschlossen ist,
dann sollte mit einem Befehl der folgenden Art
echo -en "\rZeile 1\nUmlaute: ÄÖÜäöüß\nZeile 3\f" | recode "lat1..ibmpc" >/dev/lp0getestet werden, ob
recode "lat1..ibmpc"
die richtige
druckerspezifische Codierung liefert.recode
noch viele andere Umcodierungen
und im Notfall hilft ein Nachgeschaltetes tr
oder sed
,
um einzelne Zeichen oder Zeichenfolgen individuell umzucodieren.
Das folgende Script gibt die druckbaren Zeichen mit deren oktalen Codes aus:
#! /bin/bash # carriage return before printing echo -en "\r" # print printable 8-bit characters (CR, NL, TAB, BS, 32-126, 128-254) echo -en "the special characters horizontal tab and backspace:\r\n" echo -en "the next line consists of 5 horizontal tabs each followed by I\r\n" echo -en "\tI\tI\tI\tI\tI\r\n" echo -en "the next line consists of C backspace and =\r\n" echo -en "C\b=\r\n" echo -en "the printout of C backspace and = may look like an Euro sign\r\n" echo -en "\nthe printable 7-bit octal codes (040-176) and characters:\r\n" for i in 04 05 06 07 10 11 12 13 14 15 16 do for j in 0 1 2 3 4 5 6 7 do echo -en "${i}${j} \\${i}${j} " done echo -en "\r\n" done for i in 170 171 172 173 174 175 176 do echo -en "${i} \\${i} " done if test "$1" = "7" then # form feed after printing echo -en "\r\f" exit 0 fi echo -en "\r\n" if test "$1" = "a" then echo -en "\nthe 8-bit octal codes (200-237) and characters:\r\n" for i in 20 21 22 23 do for j in 0 1 2 3 4 5 6 7 do echo -en "${i}${j} \\${i}${j} " done echo -en "\r\n" done fi echo -en "\nthe printable 8-bit octal codes (240-376) and characters:\r\n" for i in 24 25 26 27 30 31 32 33 34 35 36 do for j in 0 1 2 3 4 5 6 7 do echo -en "${i}${j} \\${i}${j} " done echo -en "\r\n" done for i in 370 371 372 373 374 375 376 do echo -en "${i} \\${i} " done # form feed after printing echo -en "\r\f"Ohne weitere Parameter werden die normalerweise problemlos druckbaren 8-bit Codes ausgegeben.
7
als Parameter angegeben, werden nur die druckbaren
7-bit ASCII-Codes ausgegeben.a
werden alle evtl. druckbaren 8-bit Codes
ausgegeben. Dadurch werden aber normalerweise die Terminaleinstellungen
zerstört, so dass der Parameter a
nicht für eine Bildschirmausgabe
zu empfehlen ist.Script a >/dev/lp0dazu verwendet werden, dass der Drucker seinen eingebauten Zeichensatz ausgibt.
Falls obiger recode
Befehl die richtige druckerspezifische
Codierung liefert, könnte /usr/lib/cups/filter/TextToPrinter
wie folgt aussehen:
#! /bin/bash # see http://localhost:631/spm.html#WRITING_FILTERS # debug info in /var/log/cups/error_log set -x # have the input at fd0 (stdin) in any case [ -n "$6" ] && exec <"$6" # carriage return before printing echo -en "\r" # printing recode "lat1..ibmpc" # form feed after printing echo -en "\f"
/usr/lib/cups/filter/
haben.
cupsd
ist neu zu laden bzw. neu zu starten.
echo -en "Zeile 1\nUmlaute: ÄÖÜäöüß\nZeile 3" | a2ps -1 -o - | lp -d Warteschlange lp -d Warteschlange /usr/share/doc/packages/ghostscript/examples/colorcir.psPostScript wird wie oben beschrieben vom CUPS-Filtersystem verarbeitet. D.h. in
/var/log/cups/error_log
finden sich die
oben beschrieben CUPS-Filteraufrufe:
I ... Started filter /usr/lib/cups/filter/pstops I ... Started filter /usr/lib/cups/filter/foomatic-rip
echo -en "Zeile 1\nUmlaute: ÄÖÜäöüß\nZeile 3" | lp -d Warteschlange lp -d Warteschlange /usr/lib/cups/filter/TextToPrinterNun findet sich in
/var/log/cups/error_log
nur
der Filteraufruf:
I ... Started filter /usr/lib/cups/filter/TextToPrinterIst
LogLevel debug
in /etc/cups/cupsd.conf
gesetzt, dann sieht man in /var/log/cups/error_log
auch
die Debug-Ausgaben von /usr/lib/cups/filter/TextToPrinter
:
D ... + '[' -n /var/spool/cups/... ']' D ... + exec D ... + echo -en '\r' D ... + recode lat1..ibmpc D ... + echo -en '\f'
text/plain
sind:
Bei dem angenommenen Fall, dass dass ein Nadeldrucker dafür verwendet wird,
Formulare auf Endlospapier mit mehreren Durchschlägen auszufüllen,
indem reiner ASCII-Text in druckerspezifischer Codierung gedruckt wird,
macht es normalerweise keinen Sinn, irgendetwas anderes als Daten
vom Mime Typ text/plain
anzunehmen.
Um alle Daten, die nicht vom Mime Typ text/plain
sind
zu ignorieren, kann in der PPD-Datei der *cupsFilter
Eintrag für den Mime Typ application/vnd.cups-postscript
wie folgt geändert werden:
*cupsFilter: "application/vnd.cups-postscript 0 /bin/true"Hierdurch wird für alle Daten, die nicht vom Mime Typ
text/plain
sind, als letzte Filterstufe /bin/true
aufgerufen, was ohne
irgendeine Verarbeitung einen erfolgreichen Abschluss meldet und
darauf hin werden alle zwischengespeicherten Daten gelöscht.
text/plain
,
die nicht die passenden Formulardaten sind:
Bei dem angenommenen Fall, dass ein Nadeldrucker dafür verwendet wird,
Formulare auf Endlospapier mit mehreren Durchschlägen auszufüllen,
macht es normalerweise keinen Sinn, beliebige Daten vom Mime Typ
text/plain
anzunehmen, ausser den passenden Formulardaten.
Um nur noch die Formulardaten anzunehmen, müssen diese identifizierbar
sein, beispielsweise dadurch, dass die Formulardaten immer eine spezielle
Zeichenfolge in der ersten Zeile enthalten.
Enthält die erste Zeile etwa immer das Muster Foo...Bar
, dann
könnte /usr/lib/cups/filter/TextToPrinter
wie folgt aussehen:
#! /bin/bash # see http://localhost:631/spm.html#WRITING_FILTERS # debug info in /var/log/cups/error_log set -x # pattern must match by "egrep -i" in first input line pattern="foo.*bar" # have the input at fd0 (stdin) in any case [ -n "$6" ] && exec <"$6" # testing read -t 1 -r line echo $line | egrep -i -q "$pattern" || exit 0 # carriage return before printing echo -en "\r" # printing echo $line | recode "lat1..ibmpc" recode "lat1..ibmpc" # form feed after printing echo -en "\f"Der Test
echo -en "Zeile 1\nUmlaute: ÄÖÜäöüß\nZeile 3" | lp -d Warteschlangeliefert nun keine Ausgabe mehr und in
/var/log/cups/error_log
findet sich
... D ... + egrep -i -q 'foo.*bar' D ... + exit 0aber der Test
echo -en "Zeile 1: FooBar\nUmlaute: ÄÖÜäöüß\nZeile 3" | lp -d Warteschlangeliefert die erwünschte Ausgabe.
Mit dem passenden Filter-Script genügt es in dem angenommenen Fall (Nadeldrucker druckt nur ASCII-Text), die Warteschlange nicht mit einer PPD-Datei anzulegen, sondern stattdessen obiges Filter-Script als "System V style interface script" zu verwenden:
lpadmin -p Warteschlange -i /usr/lib/cups/filter/TextToPrinter ...Das Filter-Script, was tatsächlich von CUPS aufgerufen wird, ist eine Kopie von
/usr/lib/cups/filter/TextToPrinter
,
die unter /etc/cups/interfaces/Warteschlange
liegt.
Jede Art von Daten wird hierbei nur vom "System V style interface script" verarbeitet. Daher gibt es keine Möglichkeit, die Druckausgabe individuell anzupassen, weil dazu die entsprechenden CUPS- und Foomatic-Filter benötigt werden.
/usr/share/cups/model/Postscript.ppd.gz
oder mit der generischen Foomatic PPD-Datei
/usr/share/cups/model/Generic/PostScript_Printer-Postscript.ppd.gz
.
/etc/cups/ppd/Warteschlange.ppd
wie folgt verändert:
*cupsFilter: "application/postscript-problematic 0 PsToPCL" *cupsFilter: "application/vnd.cups-postscript 0 foomatic-rip"ansonsten werden in
/etc/cups/ppd/Warteschlange.ppd
analog zur
generischen Foomatic PPD-Datei folgende Zeilen eingefügt:
*cupsFilter: "application/postscript-problematic 0 PsToPCL" *cupsFilter: "application/vnd.cups-postscript 0 ToPrinter"Ein
*cupsFilter
Eintrag in der PPD Datei dient immer
zur Umwandlung in druckerspezifische Daten, die danach direkt zum
Drucker geschickt werden.application/postscript-problematic
ohne dass andere Filter
zwischengeschaltet werden, mit /usr/lib/cups/filter/PsToPCL
direkt in druckerspezifische Daten umgewandelt.application/postscript-problematic
gedruckt werden, hat das für diese Warteschlange zur Folge, dass es keine
Möglichkeit gibt, die Druckausgabe individuell anzupassen, weil dazu die
entsprechenden CUPS- und Foomatic-Filter benötigt werden.
application/postscript-problematic
wird in /etc/cups/mime.types
als zusätzliche Zeile
application/postscript-problematiceingetragen, denn sonst akzeptiert CUPS diesen Mime Typ nicht.
/usr/lib/cups/filter/PsToPCL
ist das selbst zu
erstellende Filter-Script zur Umwandlung von PostScript nach PCL.
In den meisten Fällen verstehen PostScript+PCL Drucker die Druckersprache
PCL5e, die von den Ghostscript-Treibern ljet4
und
lj4dith
für Floyd-Steinberg Dithering und ljet4d
für Duplexdruck mit Auflösungen bis zu 600 dpi geliefert werden.
Wenn der Drucker an der ersten parallelen Schnittstelle angeschlossen ist,
dann sollte mit einem Ghostscript-Aufruf der folgenden Art
gs -q -dBATCH -dNOPAUSE -sDEVICE=ljet4 -sOutputFile=/dev/lp0 /usr/share/doc/packages/ghostscript/examples/colorcir.psgetestet werden, ob
ljet4
(bzw. die anderen PCL5e-Treiber) die
richtigen druckerspezifischen Daten liefert.
Falls mit obigem gs
Befehl die Farbellipse korrekt ausgedruckt
wurde, könnte /usr/lib/cups/filter/PsToPCL
wie folgt aussehen,
um Daten vom Mime Typ application/postscript-problematic
mit ljet4
nach PCL5e in 300 dpi Auflösung umzuwandeln:
#! /bin/bash # see http://localhost:631/spm.html#WRITING_FILTERS # debug info in /var/log/cups/error_log set -x # have the input at fd0 (stdin) in any case [ -n "$6" ] && exec <"$6" # printing gs -q -dBATCH -dPARANOIDSAFER -dNOPAUSE -sDEVICE=ljet4 -r300 -sOutputFile=- -
application/vnd.cups-postscript
und diese werden entweder von /usr/lib/cups/filter/foomatic-rip
weiterverarbeitet, oder von /usr/lib/cups/filter/ToPrinter
direkt an den Drucker geschickt./usr/lib/cups/filter/ToPrinter
sieht z.B. so aus:
#! /bin/bash # see http://localhost:631/spm.html#WRITING_FILTERS # debug info in /var/log/cups/error_log set -x # have the input at fd0 (stdin) in any case [ -n "$6" ] && exec <"$6" # printing cat -
/usr/lib/cups/filter/
haben.
cupsd
ist neu zu laden bzw. neu zu starten.
-o document-format=application/postscript-problematickann auf der Kommandozeile der Mime Typ des zu druckenden PostScript Dokuments auf
application/postscript-problematic
festgelegt werden./usr/lib/cups/filter/PsToPCL
oder es
erfolgt die übliche CUPS-Filterung.application/postscript-problematic
nur bei PostScript Dokumenten verwendet werden.
Testdruck von PostScript mit /usr/lib/cups/filter/PsToPCL
:
lp -d Warteschlange -o document-format=application/postscript-problematic /usr/share/doc/packages/ghostscript/examples/colorcir.psIn
/var/log/cups/error_log
findet sich dann:
I ... Started filter /usr/lib/cups/filter/PsToPCL ... D ... + '[' -n /var/spool/cups/... ']' D ... + exec D ... + gs -q -dBATCH -dPARANOIDSAFER -dNOPAUSE -sDEVICE=ljet4 -r300 -sOutputFile=- -
-o document-format=application/postscript-problematicvoreingestellt ist:
lpoptions -o document-format=application/postscript-problematic -p Warteschlange/problematicDadurch muss die komplizierte Option nicht jedes Mal via Kommandozeile eingegeben werden, sondern es genügt die Instanz der Warteschlange anzugeben:
lp -d Warteschlange/problematic /usr/share/doc/packages/ghostscript/examples/colorcir.ps
application/postscript-problematic
nur auf dem lokalen Rechner gültig und nicht via Netzwerk allgemein verfügbar.
Beim Drucken von entfernten Clients aus, auf denen ein lokaler cupsd
läuft, ist daher
/etc/cups/mime.types
auf dem Client-Rechner einzutragen
lp -d Warteschlange -h CUPS-Server -o document-format=application/postscript-problematic
cupsd
und stattdessen einen ServerName
Eintrag in /etc/cups/client.conf
).
Beim Drucken von entfernten Clients aus ist daher
Ghostscript kann auch PDF direkt verarbeiten, aber dann ist Voraussetzung, dass Ghostscript die PDF-Daten nicht via stdin bekommt, sondern als reguläre Datei.
Da gemäss
CUPS Software Programmers Manual: Writing Filters: Command-Line Arguments
nur der erste Filter in der Kette seine Eingabe aus der CUPS-Spooldatei bekommt
und da /usr/lib/cups/filter/PsToPCL
der einzige Filter ist,
kann dieser wie folgt verändert werden, damit Ghostscript den Input direkt aus
der CUPS-Spooldatei bekommt:
#! /bin/bash # see http://localhost:631/spm.html#WRITING_FILTERS # debug info in /var/log/cups/error_log set -x # set inputfile to where the input comes from inputfile="-" [ -n "$6" ] && inputfile="$6" # printing gs -q -dBATCH -dPARANOIDSAFER -dNOPAUSE -sDEVICE=ljet4 -r300 -sOutputFile=- $inputfile
Viele PostScript+PCL Drucker verstehen auch die Job-Control-Sprache PJL.
Wenn der Drucker nicht automatisch von PostScript nach PCL umschaltet,
aber PJL versteht, dann kann mit PJL-Kommandos die Umschaltung explizit
erzwungen werden.
Dazu kann /usr/lib/cups/filter/PsToPCL
so erweitert werden,
dass die passenden PJL-Kommandos vor und nach den PCL-Daten gesendet
werden:
#! /bin/bash # see http://localhost:631/spm.html#WRITING_FILTERS # debug info in /var/log/cups/error_log set -x # set inputfile to where the input comes from inputfile="-" [ -n "$6" ] && inputfile="$6" # switch to PCL and do a PCL reset echo -en "\033%-12345X@PJL ENTER LANGUAGE = PCL\n\033E" # printing gs -q -dBATCH -dPARANOIDSAFER -dNOPAUSE -sDEVICE=ljet4 -r300 -sOutputFile=- $inputfile # PCL reset and PJL end of job echo -en "\033E\033%-12345X\n"Statt PJL können auf analoge Weise auch Steuerkommandos anderere Job-Control-Sprachen an den Drucker gesendet werden.
Nach obigem Umschalten von PostScript auf PCL mit PJL-Kommandos sollte
durch die abschliessende PJL-Sequenz \033%-12345X
der
Drucker wieder im ursprünglichen PostScript-Modus sein.
Um ein Umschalten von PCL nach PostScript mit PJL-Kommandos zu erzwingen
kann /usr/lib/cups/filter/ToPrinter
wie folgt erweitert werden:
#! /bin/bash # see http://localhost:631/spm.html#WRITING_FILTERS # debug info in /var/log/cups/error_log set -x # have the input at fd0 (stdin) in any case [ -n "$6" ] && exec <"$6" # switch to PostScript echo -en "\033%-12345X@PJL ENTER LANGUAGE = POSTSCRIPT\n" # printing cat - # PostScript end of transmission and PJL end of job echo -en "\004\033%-12345X\n"Wurde die Warteschlange mit der PPD-Datei des Herstellers für das spezielle Druckermodell angelegt, so sollten die passenden Job-Control-Kommandos in der PPD-Datei (als
*JCL...
Einträge) stehen.
Diese werden von CUPS automatisch an den Drucker geschickt, so dass keine
zusätzlichen Job-Control-Kommandos notwendig sein sollten.
Wenn der Drucker PCL und PJL versteht, können gewisse Druckeroptionen mit PJL-Kommandos eingeschaltet werden.
Ein PJL+PCL-Druckauftrag hat folgende Syntax:
\033%-12345X@PJL SET Option-1 = Wert-1 @PJL SET Option-2 = Wert-2 ... @PJL SET Option-n = Wert-n @PJL ENTER LANGUAGE = PCL PCL-Kommandos+Daten\033%-12345XJeder PJL-Druckauftrag muss mit genau einem "Universal Exit Language" Kommando
\033%-12345X
beginnen und mit genau einem solchen
Kommando enden.\n
beendet werden.
Wenn der Drucker an der ersten parallelen Schnittstelle angeschlossen ist,
dann sollte mit Befehlen der folgenden Art getestet werden, ob die
PJL-Kommandos wie gewünscht funktionieren.
Hier wird beispielsweise der Tonersparmodus und die manuelle Bestätigung
vor Beginn des Ausdrucks (z.B. um vorher Spezialpapier einlegen zu können)
eingeschaltet:
echo -en "\033%-12345X@PJL SET ECONOMODE = ON\n@PJL SET MANUALFEED = ON\n@PJL ENTER LANGUAGE = PCL\n" >/dev/lp0 gs -q -dBATCH -dNOPAUSE -sDEVICE=ljet4 -sOutputFile=/dev/lp0 /usr/share/doc/packages/ghostscript/examples/colorcir.ps echo -en "\033%-12345X\n" >/dev/lp0Um die passenden PJL-Kommandos zu senden, kann
/usr/lib/cups/filter/PsToPCL
etwa wie folgt erweitert werden:
#! /bin/bash # see http://localhost:631/spm.html#WRITING_FILTERS # debug info in /var/log/cups/error_log set -x # set inputfile to where the input comes from inputfile="-" [ -n "$6" ] && inputfile="$6" # PJL printer setup echo -en "\033%-12345X@PJL SET ECONOMODE = ON\n@PJL SET MANUALFEED = ON\n" # switch to PCL and do a PCL reset echo -en "@PJL ENTER LANGUAGE = PCL\n\033E" # printing gs -q -dBATCH -dPARANOIDSAFER -dNOPAUSE -sDEVICE=ljet4 -r300 -sOutputFile=- $inputfile # PCL reset and PJL end of job echo -en "\033E\033%-12345X\n"
application/postscript-pswrite
wird in /etc/cups/mime.types
als zusätzliche Zeile
application/postscript-pswriteeingetragen.
/etc/cups/mime.convs
wird eine zusätzliche Zeile
application/postscript-pswrite application/postscript 33 PsWriteeingetragen.
Somit werden nun alle Daten vom Mime Typ application/postscript-pswrite
mit /usr/lib/cups/filter/PsWrite
in Daten vom Mime Typ
application/postscript
umgewandelt.
Diese Filterung ist für alle Warteschlangen verfügbar.
Wenn Daten vom Mime Typ application/postscript-pswrite
gedruckt werden, hat das zur Folge, dass die meisten Möglichkeiten, die
Druckausgabe individuell anzupassen, erhalten bleiben, weil Daten vom Mime Typ
application/postscript
die üblichen CUPS- und ggf. Foomatic-Filter
durchlaufen. Oft funktionieren jedoch die Möglichkeiten von
/usr/lib/cups/filter/pstops
gemäss
CUPS Software Users Manual: Document Options
nicht zusammen mit der PostScript Vorverarbeitung, aber zumindest die
druckerspezifischen Optionen gemäss der PPD-Datei sollten auch zusammen
mit der PostScript Vorverarbeitung funktionieren.
pswrite
verwendet.gs -q -dBATCH -dNOPAUSE -sDEVICE=pswrite -sOutputFile=/dev/lp0 /usr/share/doc/packages/ghostscript/examples/colorcir.ps gs -q -dBATCH -dNOPAUSE -sDEVICE=pswrite -dLanguageLevel=2 -sOutputFile=/dev/lp0 /usr/share/doc/packages/ghostscript/examples/colorcir.ps gs -q -dBATCH -dNOPAUSE -sDEVICE=pswrite -dLanguageLevel=1 -sOutputFile=/dev/lp0 /usr/share/doc/packages/ghostscript/examples/colorcir.psgetestet werden, ob bzw. welcher
LanguageLevel
die
richtigen druckerspezifischen Daten liefert./usr/lib/cups/filter/PsWrite
wie folgt aussehen
#! /bin/bash # see http://localhost:631/spm.html#WRITING_FILTERS # debug info in /var/log/cups/error_log set -x # set inputfile to where the input comes from inputfile="-" [ -n "$6" ] && inputfile="$6" # printing gs -q -dBATCH -dPARANOIDSAFER -dNOPAUSE -sDEVICE=pswrite -dLanguageLevel=1 -sOutputFile=- $inputfile
/usr/lib/cups/filter/
haben.
cupsd
ist neu zu laden bzw. neu zu starten.
-o document-format=application/postscript-pswritekann auf der Kommandozeile der Mime Typ des zu druckenden PostScript Dokuments auf
application/postscript-pswrite
festgelegt werden./usr/lib/cups/filter/PsWrite
oder es
erfolgt nur die übliche CUPS-Filterung./usr/lib/cups/filter/PsWrite
der erste Filter in der Kette ist
erhält er gemäss
CUPS Software Programmers Manual: Writing Filters: Command-Line Arguments
den Input direkt aus der CUPS-Spooldatei, so dass die Vorverarbeitung auch
für PDF Dokumente möglich ist.
Testdruck von PostScript mit /usr/lib/cups/filter/PsWrite
:
lp -d Warteschlange -o document-format=application/postscript-pswrite /usr/share/doc/packages/ghostscript/examples/colorcir.psIn
/var/log/cups/error_log
findet sich dann:
I ... Started filter /usr/lib/cups/filter/PsWrite I ... Started filter /usr/lib/cups/filter/pstops ... D ... + gs -q -dBATCH -dPARANOIDSAFER -dNOPAUSE -sDEVICE=pswrite -dLanguageLevel=1 -sOutputFile=- /var/spool/cups/...
-o document-format=application/postscript-pswritevoreingestellt ist erfolgt analog zum obigen Abschnitt "Wahlweise PCL-Druck bei einem PostScript+PCL Drucker".
application/postscript-prefiltered
wird in /etc/cups/mime.types
als zusätzliche Zeile
application/postscript-prefilteredeingetragen.
/etc/cups/mime.convs
wird eine zusätzliche Zeile
eingetragen und die pstops
Zeile wird wie folgt geändert:
application/postscript application/postscript-prefiltered 10 PsPrefilter application/postscript-prefiltered application/vnd.cups-postscript 66 pstopsVergl. dazu aber auch CUPS Software Administrators Manual: Adding Filetypes and Filters.
Somit werden nun alle Daten vom Mime Typ application/postscript
mit /usr/lib/cups/filter/PsPrefilter
vorgefiltert und in Daten
vom Mime Typ application/postscript-prefiltered
umgewandelt und
diese Daten werden dann von standardmässigen CUPS-Filter
/usr/lib/cups/filter/pstops
weiterverarbeitet.
Alle Möglichkeiten, die Druckausgabe individuell anzupassen, sollten hierbei
erhalten bleiben, weil die Daten die üblichen CUPS- und ggf. Foomatic-Filter
durchlaufen.
Voraussetzung ist, dass /usr/lib/cups/filter/PsPrefilter
für
jegliche Daten vom Mime Typ application/postscript
korrekt
arbeitet.
/usr/lib/cups/filter/PsPrefilter
ist das selbst zu
erstellende Filter-Script zur Vorverarbeitung von PostScript-Daten.
Angenommen, es ist CUPS Version 1.1.15 im Einsatz und das Problem,
was im Supportdatenbank-Artikel "Kein Landscape Druck mit CUPS" (http://sdb.suse.de/de/sdb/html/jsmeix_print-cups-landscape-81.html)
beschrieben ist, soll mit einem PostScript Prefilter-Script behoben werden,
dann könnte /usr/lib/cups/filter/PsPrefilter
wie folgt aussehen:
#! /bin/bash # see http://localhost:631/spm.html#WRITING_FILTERS # debug info in /var/log/cups/error_log set -x # have the input at fd0 (stdin) in any case [ -n "$6" ] && exec <"$6" # prefiltering sed -e 's/Orientation: Landscape/Orientation: Portrait/'In den folgenden Schritten wird an diesem Beispiel demonstriert, wie wichtig gründliche Tests sind, damit durch das Korrekturscript nicht mehr Probleme im standardmässigen CUPS-Filtersystem entstehen, als gelöst werden.
/usr/lib/cups/filter/
haben.
cupsd
ist neu zu laden bzw. neu zu starten.
echo -en "Zeile 1\nUmlaute: ÄÖÜäöüß\nZeile 3" | a2ps -1 -o - | lp -d Warteschlange lp -d Warteschlange /usr/share/doc/packages/ghostscript/examples/colorcir.psIn
/var/log/cups/error_log
finden sich nun die Filteraufrufe:
I ... Started filter /usr/lib/cups/filter/PsPrefilter I ... Started filter /usr/lib/cups/filter/pstops
echo -en "Zeile 1\nUmlaute: ÄÖÜäöüß\nZeile 3" | lp -d Warteschlange lp -d Warteschlange /usr/lib/cups/filter/PsPrefilterIn
/var/log/cups/error_log
finden sich nun die Filteraufrufe:
I ... Started filter /usr/lib/cups/filter/texttops I ... Started filter /usr/lib/cups/filter/PsPrefilter I ... Started filter /usr/lib/cups/filter/pstops
sed -e 's/Orientation: Portrait/Orientation: Portrait/'Der Grund ist, dass die PostScript Ausgabe von
/usr/lib/cups/filter/texttops
die Zeichenfolge
"Orientation: Landscape" aus /usr/lib/cups/filter/PsPrefilter
enthält, die aber im folgenden Filterschritt mit eben diesem
/usr/lib/cups/filter/PsPrefilter
in die Zeichenfolge
"Orientation: Portrait" umgewandelt wird, was dann auch so gedruckt wird.
/usr/lib/cups/filter/PsPrefilter
kann verbessert werden,
indem die zu ersetztende Zeichenfolge möglichst genau angegeben wird:
#! /bin/bash # see http://localhost:631/spm.html#WRITING_FILTERS # debug info in /var/log/cups/error_log set -x # have the input at fd0 (stdin) in any case [ -n "$6" ] && exec <"$6" # prefiltering sed -e 's/^%%Orientation: Landscape$/%%Orientation: Portrait/'
Nun sollte sowohl der fehlgeschlagene Test oben, als auch
echo '%%Orientation: Landscape' | a2ps -1 -r -o - | lp -d Warteschlangekorrekt gedruckt werden, aber
lp -d Warteschlange -o landscape /usr/lib/cups/filter/PsPrefilterwird bei CUPS Version 1.1.15 nicht im Landscape-Modus gedruckt, sondern im Portrait-Modus wobei aber der Text schon passend für den Landscape-Modus positioniert ist. Ab CUPS Version 1.1.18 funktioniert es korrekt.
Der Grund für den fehlerhaften Ausdruck bei CUPS Version 1.1.15 ist,
dass durch die Option -o landscape
die Zeile
%%Orientation: Landscape
in der PostScript Ausgabe von /usr/lib/cups/filter/texttops
steht, die den folgenden Filter /usr/lib/cups/filter/pstops
veranlasst, die Darstellung um 90 Grad zu drehen, damit es im
Landscape-Modus gedruckt wird.
Durch /usr/lib/cups/filter/PsPrefilter
wird aber genau das
verhindert.
Bei CUPS Version 1.1.18 wird statt des %%Orientation
Eintrags
die CUPS spezifische Zeile
%cupsRotation: 90
verwendet, um das CUPS Filtersystem zu einer Drehung der Darstellung um 90 Grad
zu veranlassen.
Das Verhindern der 90 Grad Drehung muss bei CUPS Version 1.1.15 abhängig davon
erfolgen, welches Programm die PostScript Daten erzeugt hat.
Das erzeugende Programm steht normalerweise in der %%Creator
Zeile wie z.B. bei /usr/lib/cups/filter/texttops
,
a2ps
, NetScape
und Mozilla
:
%%Creator: texttops/CUPS ... %%Creator: a2ps version ... %%Creator: Mozilla (NetScape) ... %%Creator: Mozilla PostScript module ...Dementsprechend kann
/usr/lib/cups/filter/PsPrefilter
verbessert
werden, indem die 90 Grad Drehung nur in den bekannten Problemfällen verhindert
wird und ansonsten bleiben die PostScript Daten unverändert:
#! /bin/bash # see http://localhost:631/spm.html#WRITING_FILTERS # debug info in /var/log/cups/error_log set -x # have the input at fd0 (stdin) in any case [ -n "$6" ] && exec <"$6" # for simple testing with "egrep" have the input as regular file cleanup() { EXIT_CODE=$? ; rm -f $INPUT &>/dev/null ; exit $EXIT_CODE ; } trap 'cleanup' 0 1 2 3 15 MY_NAME=${0##*/} INPUT=$( mktemp /var/spool/cups/tmp/$MY_NAME.XXXXXX ) || exit 1 cat - >$INPUT # prefiltering only for particular PostScript "Creator" patterns if egrep -q '^%%Creator: a2ps|^%%Creator: Mozilla' $INPUT then sed -e 's/^%%Orientation: Landscape$/%%Orientation: Portrait/' $INPUT exit $? fi # otherwise no prefiltering cat $INPUT
Analog zum Punkt 6. wird nun auch die Zeile "%%Creator: a2ps
"
getestet, um zu prüfen, dass das "sed" Kommando nicht fälschlicherweise
ausgeführt wird, wenn /usr/lib/cups/filter/texttops
die
PostScript Daten erzeugt hat:
echo -e '%%Orientation: Landscape\n%%Creator: a2ps' | lp -d Warteschlange echo -e '%%Orientation: Landscape\n%%Creator: a2ps' | lp -d Warteschlange -o landscape echo -e '%%Orientation: Landscape\n%%Creator: a2ps' | a2ps -1 -o - | lp -d Warteschlange echo -e '%%Orientation: Landscape\n%%Creator: a2ps' | a2ps -1 -r -o - | lp -d Warteschlange Ausdruck aus Netscape und Mozilla im Portrait-Modus und im Landscape-ModusDer Ausdruck aus Mozilla im Landscape-Modus funktioniert bei älteren Mozilla Versionen (z.B. bei Version 1.0) seitens Mozilla nicht, da die Auswahl "Landscape" nicht gespeichert wird - d.h. Mozilla erzeugt die Druckausgabe immer für den standardmässigen Portrait-Modus.
In beiden Fällen muss zumindest Ghostscript das PostScript und/oder
PDF Dokument verarbeiten können.
Wenn sowohl der PostScript-Interpreter im Drucker, als auch Ghostscript
an dem Dokument scheitern, dann ist dieses Dokument in der Regel so kaputt,
dass es keine Möglichkeit gibt, es zu Papier zu bringen.
Gelingt ein bestimmter Ausdruck aus einem Anwendungsprogramm nicht,
so kann evtl. die PostScript-Ausgabe des Anwendungsprogramms
nicht oder nicht vollständig vom Drucksystem verarbeitet
werden.
Zum Test druckt man aus dem Anwendungsprogramm, was das problematische
PostScript und/oder PDF Dokument erstellt hat, in eine PostScript-Datei
bzw. man nimmt das schon vorhandene PostScript und/oder PDF Dokument,
das dann unter der grafischen Oberfläche mit
gs -r60 DateinameSeite für Seite angezeigt werden kann.
SDB-jsmeix_print-cups-filters
)