|
@@ -0,0 +1,295 @@
|
|
|
+From 4203e04ef9e6ca22ed68a1ab10a878aa9ceaeedc Mon Sep 17 00:00:00 2001
|
|
|
+From: Ray Johnston <ray.johnston@artifex.com>
|
|
|
+Date: Thu, 14 Feb 2019 10:20:03 -0800
|
|
|
+Subject: [PATCH] Fix bug 700585: Restrict superexec and remove it from
|
|
|
+ internals and gs_cet.ps
|
|
|
+
|
|
|
+Also while changing things, restructure the CETMODE so that it will
|
|
|
+work with -dSAFER. The gs_cet.ps is now run when we are still at save
|
|
|
+level 0 with systemdict writeable. Allows us to undefine .makeoperator
|
|
|
+and .setCPSImode internal operators after CETMODE is handled.
|
|
|
+
|
|
|
+Change previous uses of superexec to using .forceput (with the usual
|
|
|
+.bind executeonly to hide it).
|
|
|
+
|
|
|
+CVE: CVE-2019-3835
|
|
|
+Upstream-Status: Backport [git://git.ghostscript.com/ghostpdl.git]
|
|
|
+
|
|
|
+Signed-off-by: Ovidiu Panait <ovidiu.panait@windriver.com>
|
|
|
+---
|
|
|
+ Resource/Init/gs_cet.ps | 38 ++++++++++++++------------------------
|
|
|
+ Resource/Init/gs_dps1.ps | 2 +-
|
|
|
+ Resource/Init/gs_fonts.ps | 8 ++++----
|
|
|
+ Resource/Init/gs_init.ps | 38 +++++++++++++++++++++++++++-----------
|
|
|
+ Resource/Init/gs_ttf.ps | 8 ++++----
|
|
|
+ Resource/Init/gs_type1.ps | 6 +++---
|
|
|
+ 6 files changed, 53 insertions(+), 47 deletions(-)
|
|
|
+
|
|
|
+diff --git a/Resource/Init/gs_cet.ps b/Resource/Init/gs_cet.ps
|
|
|
+index dbc5c4e..3cc6883 100644
|
|
|
+--- a/Resource/Init/gs_cet.ps
|
|
|
++++ b/Resource/Init/gs_cet.ps
|
|
|
+@@ -1,37 +1,29 @@
|
|
|
+ %!PS
|
|
|
+ % Set defaults for Ghostscript to match Adobe CPSI behaviour for CET
|
|
|
+
|
|
|
+-/.odef { % <name> <proc> odef -
|
|
|
+- 1 index exch .makeoperator def
|
|
|
+-} bind def
|
|
|
+-
|
|
|
++% skip if we've already run this -- based on fake "product"
|
|
|
+ systemdict /product get (PhotoPRINT SE 5.0v2) readonly eq
|
|
|
+ {
|
|
|
+ (%END GS_CET) .skipeof
|
|
|
+ } if
|
|
|
+
|
|
|
+-% do this in the server level so it is persistent across jobs
|
|
|
+-//true 0 startjob not {
|
|
|
+- (*** Warning: CET startup is not in server default) = flush
|
|
|
+-} if
|
|
|
++% Note: this must be run at save level 0 and when systemdict is writeable
|
|
|
++currentglobal //true setglobal
|
|
|
++systemdict dup dup dup
|
|
|
++/version (3017.102) readonly .forceput % match CPSI 3017.102
|
|
|
++/product (PhotoPRINT SE 5.0v2) readonly .forceput % match CPSI 3017.102
|
|
|
++/revision 0 put % match CPSI 3017.103 Tek shows revision 5
|
|
|
++/serialnumber dup {233640} readonly .makeoperator .forceput % match CPSI 3017.102 Tek shows serialnumber 1401788461
|
|
|
++
|
|
|
++systemdict /.odef { % <name> <proc> odef -
|
|
|
++ 1 index exch //.makeoperator def
|
|
|
++} .bind .forceput % this will be undefined at the end
|
|
|
+
|
|
|
+ 300 .sethiresscreen % needed for language switch build since it
|
|
|
+ % processes gs_init.ps BEFORE setting the resolution
|
|
|
+
|
|
|
+ 0 array 0 setdash % CET 09-08 wants local setdash
|
|
|
+
|
|
|
+-currentglobal //true setglobal
|
|
|
+-
|
|
|
+-{
|
|
|
+- systemdict dup dup dup
|
|
|
+- /version (3017.102) readonly put % match CPSI 3017.102
|
|
|
+- /product (PhotoPRINT SE 5.0v2) readonly put % match CPSI 3017.102
|
|
|
+- /revision 0 put % match CPSI 3017.103 Tek shows revision 5
|
|
|
+- /serialnumber dup {233640} readonly .makeoperator put % match CPSI 3017.102 Tek shows serialnumber 1401788461
|
|
|
+- systemdict /deviceinfo undef % for CET 20-23-1
|
|
|
+-% /UNROLLFORMS true put % CET files do unreasonable things inside forms
|
|
|
+-} 1183615869 internaldict /superexec get exec
|
|
|
+-
|
|
|
+ /UNROLLFORMS true def
|
|
|
+
|
|
|
+ (%.defaultbgrucrproc) cvn { } bind def
|
|
|
+@@ -118,9 +110,7 @@ userdict /.smoothness currentsmoothness put
|
|
|
+ ofnfa
|
|
|
+ } bind def
|
|
|
+
|
|
|
+-currentdict /.odef undef
|
|
|
+-% end of slightly nasty hack to give consistent cluster results
|
|
|
+-
|
|
|
+-//false 0 startjob pop % re-enter encapsulated mode
|
|
|
++systemdict /.odef .undef
|
|
|
+
|
|
|
++% end of slightly nasty hack to give consistent cluster results
|
|
|
+ %END GS_CET
|
|
|
+diff --git a/Resource/Init/gs_dps1.ps b/Resource/Init/gs_dps1.ps
|
|
|
+index 3d2cf7a..c4fd839 100644
|
|
|
+--- a/Resource/Init/gs_dps1.ps
|
|
|
++++ b/Resource/Init/gs_dps1.ps
|
|
|
+@@ -89,7 +89,7 @@ level2dict begin
|
|
|
+ % definition, copy it into the local directory.
|
|
|
+ //systemdict /SharedFontDirectory .knownget
|
|
|
+ { 1 index .knownget
|
|
|
+- { //.FontDirectory 2 index 3 -1 roll { put } systemdict /superexec known {//superexec}{1183615869 internaldict /superexec get exec} ifelse } % readonly
|
|
|
++ { //.FontDirectory 2 index 3 -1 roll .forceput } % readonly
|
|
|
+ if
|
|
|
+ }
|
|
|
+ if
|
|
|
+diff --git a/Resource/Init/gs_fonts.ps b/Resource/Init/gs_fonts.ps
|
|
|
+index 0562235..f2b4e19 100644
|
|
|
+--- a/Resource/Init/gs_fonts.ps
|
|
|
++++ b/Resource/Init/gs_fonts.ps
|
|
|
+@@ -519,11 +519,11 @@ buildfontdict 3 /.buildfont3 cvx put
|
|
|
+ % the font in LocalFontDirectory.
|
|
|
+ .currentglobal
|
|
|
+ { //systemdict /LocalFontDirectory .knownget
|
|
|
+- { 2 index 2 index { .growput } systemdict /superexec known {//superexec}{1183615869 internaldict /superexec get exec} ifelse } % readonly
|
|
|
++ { 2 index 2 index .forceput } % readonly
|
|
|
+ if
|
|
|
+ }
|
|
|
+ if
|
|
|
+- dup //.FontDirectory 4 -2 roll { .growput } systemdict /superexec known {//superexec}{1183615869 internaldict /superexec get exec} ifelse % readonly
|
|
|
++ dup //.FontDirectory 4 -2 roll .forceput % readonly
|
|
|
+ % If the font originated as a resource, register it.
|
|
|
+ currentfile .currentresourcefile eq { dup .registerfont } if
|
|
|
+ readonly
|
|
|
+@@ -1191,13 +1191,13 @@ $error /SubstituteFont { } put
|
|
|
+ //.FontDirectory 1 index known not {
|
|
|
+ 2 dict dup /FontName 3 index put
|
|
|
+ dup /FontType 1 put
|
|
|
+- //.FontDirectory 3 1 roll { put } systemdict /superexec known {//superexec}{1183615869 internaldict /superexec get exec} ifelse % readonly
|
|
|
++ //.FontDirectory 3 1 roll //.forceput exec % readonly
|
|
|
+ } {
|
|
|
+ pop
|
|
|
+ } ifelse
|
|
|
+ } forall
|
|
|
+ } forall
|
|
|
+- }
|
|
|
++ } executeonly % hide .forceput
|
|
|
+ FAKEFONTS { exch } if pop def % don't bind, .current/setglobal get redefined
|
|
|
+
|
|
|
+ % Install initial fonts from Fontmap.
|
|
|
+diff --git a/Resource/Init/gs_init.ps b/Resource/Init/gs_init.ps
|
|
|
+index 80d9585..0d5c4f7 100644
|
|
|
+--- a/Resource/Init/gs_init.ps
|
|
|
++++ b/Resource/Init/gs_init.ps
|
|
|
+@@ -2188,9 +2188,6 @@ SAFER { .setsafeglobal } if
|
|
|
+ /.endtransparencygroup % transparency-example.ps
|
|
|
+ /.setdotlength % Bug687720.ps
|
|
|
+ /.sort /.setdebug /.mementolistnewblocks /getenv
|
|
|
+-
|
|
|
+- /.makeoperator /.setCPSImode % gs_cet.ps, this won't work on cluster with -dSAFER
|
|
|
+-
|
|
|
+ /unread
|
|
|
+ ]
|
|
|
+ {systemdict exch .forceundef} forall
|
|
|
+@@ -2270,7 +2267,6 @@ SAFER { .setsafeglobal } if
|
|
|
+
|
|
|
+ % Used by our own test suite files
|
|
|
+ %/.fileposition %image-qa.ps
|
|
|
+- %/.makeoperator /.setCPSImode % gs_cet.ps
|
|
|
+
|
|
|
+ % Either our code uses these in ways which mean they can't be undefined, or they are used directly by
|
|
|
+ % test files/utilities, or engineers expressed a desire to keep them visible.
|
|
|
+@@ -2457,6 +2453,16 @@ end
|
|
|
+ /vmreclaim where
|
|
|
+ { pop NOGC not { 2 .vmreclaim 0 vmreclaim } if
|
|
|
+ } if
|
|
|
++
|
|
|
++% Do this before systemdict is locked (see below for additional CETMODE setup using gs_cet.ps)
|
|
|
++systemdict /CETMODE .knownget {
|
|
|
++ {
|
|
|
++ (gs_cet.ps) runlibfile
|
|
|
++ } if
|
|
|
++} if
|
|
|
++systemdict /.makeoperator .undef % must be after gs_cet.ps
|
|
|
++systemdict /.setCPSImode .undef % must be after gs_cet.ps
|
|
|
++
|
|
|
+ DELAYBIND not {
|
|
|
+ systemdict /.bindnow .undef % We only need this for DELAYBIND
|
|
|
+ systemdict /.forcecopynew .undef % remove temptation
|
|
|
+@@ -2464,16 +2470,29 @@ DELAYBIND not {
|
|
|
+ systemdict /.forceundef .undef % ditto
|
|
|
+ } if
|
|
|
+
|
|
|
+-% Move superexec to internaldict if superexec is defined.
|
|
|
+-systemdict /superexec .knownget {
|
|
|
+- 1183615869 internaldict /superexec 3 -1 roll put
|
|
|
+- systemdict /superexec .undef
|
|
|
++% Move superexec to internaldict if superexec is defined. (Level 2 or later)
|
|
|
++systemdict /superexec known {
|
|
|
++ % restrict superexec to single known use by PScript5.dll
|
|
|
++ % We could do this only for SAFER mode, but internaldict and superexec are
|
|
|
++ % not very well documented, and we don't want them to be used.
|
|
|
++ 1183615869 internaldict /superexec {
|
|
|
++ 2 index /Private eq % first check for typical use in PScript5.dll
|
|
|
++ 1 index length 1 eq and % expected usage is: dict /Private <value> {put} superexec
|
|
|
++ 1 index 0 get systemdict /put get eq and
|
|
|
++ {
|
|
|
++ //superexec exec % the only usage we allow
|
|
|
++ } {
|
|
|
++ /superexec load /invalidaccess signalerror
|
|
|
++ } ifelse
|
|
|
++ } bind cvx executeonly put
|
|
|
++ systemdict /superexec .undef % get rid of the dangerous (unrestricted) operator
|
|
|
+ } if
|
|
|
+
|
|
|
+ % Can't remove this one until the last minute :-)
|
|
|
+ DELAYBIND not {
|
|
|
+ systemdict /.undef .undef
|
|
|
+ } if
|
|
|
++
|
|
|
+ WRITESYSTEMDICT {
|
|
|
+ SAFER {
|
|
|
+ (\n *** WARNING - you have selected SAFER, indicating you want Ghostscript\n) print
|
|
|
+@@ -2500,7 +2519,4 @@ WRITESYSTEMDICT {
|
|
|
+ % be 'true' in some cases.
|
|
|
+ userdict /AGM_preserve_spots //false put
|
|
|
+
|
|
|
+-systemdict /CETMODE .knownget
|
|
|
+-{ { (gs_cet.ps) runlibfile } if } if
|
|
|
+-
|
|
|
+ % The interpreter will run the initial procedure (start).
|
|
|
+diff --git a/Resource/Init/gs_ttf.ps b/Resource/Init/gs_ttf.ps
|
|
|
+index 05943c5..da97afa 100644
|
|
|
+--- a/Resource/Init/gs_ttf.ps
|
|
|
++++ b/Resource/Init/gs_ttf.ps
|
|
|
+@@ -1421,7 +1421,7 @@ mark
|
|
|
+ TTFDEBUG { (\n1 setting alias: ) print dup ==only
|
|
|
+ ( to be the same as ) print 2 index //== exec } if
|
|
|
+
|
|
|
+- 7 index 2 index 3 -1 roll exch //.growput systemdict /superexec known {//superexec}{1183615869 internaldict /superexec get exec} ifelse
|
|
|
++ 7 index 2 index 3 -1 roll exch .forceput
|
|
|
+ } forall
|
|
|
+ pop pop pop
|
|
|
+ }
|
|
|
+@@ -1439,7 +1439,7 @@ mark
|
|
|
+ exch pop
|
|
|
+ TTFDEBUG { (\n2 setting alias: ) print 1 index ==only
|
|
|
+ ( to use glyph index: ) print dup //== exec } if
|
|
|
+- 5 index 3 1 roll //.growput systemdict /superexec known {//superexec}{1183615869 internaldict /superexec get exec} ifelse
|
|
|
++ 5 index 3 1 roll .forceput
|
|
|
+ //false
|
|
|
+ }
|
|
|
+ {
|
|
|
+@@ -1456,7 +1456,7 @@ mark
|
|
|
+ { % CharStrings(dict) isunicode(boolean) cmap(dict) RAGL(dict) gname(name) codep(integer) gindex(integer)
|
|
|
+ TTFDEBUG { (\3 nsetting alias: ) print 1 index ==only
|
|
|
+ ( to be index: ) print dup //== exec } if
|
|
|
+- exch pop 5 index 3 1 roll //.growput systemdict /superexec known {//superexec}{1183615869 internaldict /superexec get exec} ifelse
|
|
|
++ exch pop 5 index 3 1 roll .forceput
|
|
|
+ }
|
|
|
+ {
|
|
|
+ pop pop
|
|
|
+@@ -1486,7 +1486,7 @@ mark
|
|
|
+ } ifelse
|
|
|
+ ]
|
|
|
+ TTFDEBUG { (Encoding: ) print dup === flush } if
|
|
|
+-} bind def
|
|
|
++} .bind executeonly odef % hides .forceput
|
|
|
+
|
|
|
+ % to be removed 9.09......
|
|
|
+ currentdict /postalias undef
|
|
|
+diff --git a/Resource/Init/gs_type1.ps b/Resource/Init/gs_type1.ps
|
|
|
+index 96e1ced..61f5269 100644
|
|
|
+--- a/Resource/Init/gs_type1.ps
|
|
|
++++ b/Resource/Init/gs_type1.ps
|
|
|
+@@ -116,7 +116,7 @@
|
|
|
+ { % scratch(string) RAGL(dict) AGL(dict) CharStrings(dict) cstring gname aglname
|
|
|
+ CFFDEBUG { (\nsetting alias: ) print dup ==only
|
|
|
+ ( to be the same as glyph: ) print 1 index //== exec } if
|
|
|
+- 3 index exch 3 index //.growput systemdict /superexec known {//superexec}{1183615869 internaldict /superexec get exec} ifelse
|
|
|
++ 3 index exch 3 index .forceput
|
|
|
+ % scratch(string) RAGL(dict) AGL(dict) CharStrings(dict) cstring gname
|
|
|
+ }
|
|
|
+ {pop} ifelse
|
|
|
+@@ -135,7 +135,7 @@
|
|
|
+ 3 1 roll pop pop
|
|
|
+ } if
|
|
|
+ pop
|
|
|
+- dup /.AGLprocessed~GS //true //.growput systemdict /superexec known {//superexec}{1183615869 internaldict /superexec get exec} ifelse
|
|
|
++ dup /.AGLprocessed~GS //true .forceput
|
|
|
+ } if
|
|
|
+
|
|
|
+ %% We need to excute the C .buildfont1 in a stopped context so that, if there
|
|
|
+@@ -148,7 +148,7 @@
|
|
|
+ {//.buildfont1} stopped
|
|
|
+ 4 3 roll .setglobal
|
|
|
+ {//.buildfont1 $error /errorname get signalerror} if
|
|
|
+- } bind def
|
|
|
++ } .bind executeonly def % hide .forceput
|
|
|
+
|
|
|
+ % If the diskfont feature isn't included, define a dummy .loadfontdict.
|
|
|
+ /.loadfontdict where
|
|
|
+--
|
|
|
+2.20.1
|
|
|
+
|