% Copyright (C) 2001-2023 Artifex Software, Inc.
% All Rights Reserved.
%
% This software is provided AS-IS with no warranty, either express or
% implied.
%
% This software is distributed under license and may not be copied,
% modified or distributed except as expressly authorized under the terms
% of the license contained in the file LICENSE in this distribution.
%
% Refer to licensing information at http://www.artifex.com or contact
% Artifex Software, Inc.,  39 Mesa Street, Suite 108A, San Francisco,
% CA 94129, USA, for further information.
%

% Initialization file for most of the Display PostScript functions
% that are also included in Level 2.

level2dict begin

% ------ Virtual memory ------ %

/currentshared /.currentglobal load def
/scheck {.gcheck} .internalbind odef
%****** FOLLOWING IS WRONG ******
/shareddict currentdict /globaldict .knownget not { 20 dict } if def

% Global and LocalFontDirectory must remain in systemdict
% even if we temporarily exit Level 2 mode.

end				% level2dict
systemdict begin

/SharedFontDirectory .FontDirectory .gcheck
 { .currentglobal //false .setglobal
   currentdict
   /LocalFontDirectory .FontDirectory dup maxlength dict copy
   .forceput	% LocalFontDirectory is local, systemdict is global
   .setglobal .FontDirectory
 } executeonly
 {
   currentdict
   /LocalFontDirectory .FontDirectory
   .forceput	% LocalFontDirectory is local, systemdict is global
   50 dict
 }executeonly
ifelse def

end				% systemdict
level2dict begin

% setshared must rebind FontDirectory to the appropriate one of
% Local or SharedFontDirectory.

/.setglobal		% <bool> .setglobal -
 { dup .setglobal
   //systemdict /FontDirectory .currentglobal
    { //SharedFontDirectory }
    { /LocalFontDirectory .systemvar }	% can't embed ref to local VM
   ifelse .forceput pop	% LocalFontDirectory is local, systemdict is global
 } .forcebind odef
% Don't just copy (load) the definition of .setglobal:
% it gets redefined for LL3.
/setshared { /.setglobal .systemvar exec } odef
.currentglobal setshared

% See below for changes in save and restore.

% ------ Fonts ------ %

/selectfont		% <fontname> <size> selectfont -
 {
   {
     1 .argindex findfont
     1 index dup type /arraytype eq { makefont } { scalefont } ifelse
     setfont pop pop
   } stopped { /selectfont .systemvar $error /errorname get signalerror } if
 } odef
% undefinefont has to take local/global VM into account.
/undefinefont		% <fontname> undefinefont -
 { //.FontDirectory 1 .argindex .forceundef	% FontDirectory is readonly
   .currentglobal
    {		% Current mode is global; delete from local directory too.
      //systemdict /LocalFontDirectory .knownget
       { 1 index .forceundef } executeonly		% LocalFontDirectory is readonly
      if
    }
    {		% Current mode is local; if there was a shadowed global
                % definition, copy it into the local directory.
      //systemdict /SharedFontDirectory .knownget
       { 1 index .knownget
          { //.FontDirectory 2 index 3 -1 roll .forceput } % readonly
         if
       }
      if
    }
   ifelse pop
 } .forcebind odef

% If we load a font into global VM within an inner save, the restore
% will delete it from FontDirectory but not from SharedFontDirectory.
% We have to handle this by making restore copy missing entries from
% SharedFontDirectory to FontDirectory.  Since this could slow down restore
% considerably, we define a new operator .forcecopynew for this purpose.
% Furthermore, if FAKEFONTS is in effect, we want global real fonts to
% override fake local ones.  We handle this by brute force.
/restore		% <save> restore -
 { dup //restore
   /LocalFontDirectory .systemvar
   FAKEFONTS
    { mark
                % We want to delete a fake font from the local directory
                % iff the global directory now has no definition for it,
                % or a non-fake definition.
      1 index dup
       {		% Stack: lfd mark lfd key ... lfd key value
         length 1 gt
          {		% This is a real local definition; don't do anything.
            pop
          }
          {		% This is a fake local definition, check for global.
            //SharedFontDirectory 1 index .knownget
             {		% A global definition exists, check for fake.
               length 1 eq { pop } { 1 index } ifelse
             }
             {		% No global definition, delete the local one.
               1 index
             }
            ifelse
          }
         ifelse
       } forall
      pop counttomark 2 idiv { .forceundef } executeonly repeat pop		% readonly
    }
   if
   //SharedFontDirectory exch .forcecopynew pop
   .currentglobal .setglobal	% Rebind FontDirectory according to current VM.
   pop
 } .forcebind odef

end				% level2dict
