src/Pure/sign.ML
changeset 251 c9b984c0a674
parent 229 4002c4cd450c
child 266 3fe01df1a614
equal deleted inserted replaced
250:9b5a069285ce 251:c9b984c0a674
     1 (*  Title:      Pure/sign.ML
     1 (*  Title:      Pure/sign.ML
     2     ID:         $Id$
     2     ID:         $Id$
     3     Author:     Lawrence C Paulson, Cambridge University Computer Laboratory
     3     Author:     Lawrence C Paulson and Markus Wenzel
     4     Copyright   1994  University of Cambridge
     4 
     5 
     5 The abstract type "sg" of signatures.
     6 The abstract types "sg" of signatures
     6 
       
     7 TODO:
       
     8   a clean modular sequential Sign.extend (using sg_ext list);
     7 *)
     9 *)
     8 
    10 
     9 signature SIGN =
    11 signature SIGN =
    10 sig
    12 sig
    11   structure Type: TYPE
       
    12   structure Symtab: SYMTAB
    13   structure Symtab: SYMTAB
    13   structure Syntax: SYNTAX
    14   structure Syntax: SYNTAX
       
    15   structure Type: TYPE
    14   sharing Symtab = Type.Symtab
    16   sharing Symtab = Type.Symtab
    15   type sg
    17   local open Type in
    16   val extend: sg -> string ->
    18     type sg
    17         (class * class list) list * class list *
    19     val rep_sg: sg ->
    18         (string list * int) list *
    20       {tsig: type_sig,
    19         (string * indexname list * string) list *
    21        const_tab: typ Symtab.table,
    20         (string list * (sort list * class)) list *
    22        syn: Syntax.syntax,
    21         (string list * string)list * Syntax.sext option -> sg
    23        stamps: string ref list}
    22   val merge: sg * sg -> sg
    24     val subsig: sg * sg -> bool
    23   val pure: sg
    25     val eq_sg: sg * sg -> bool
    24   val read_typ: sg * (indexname -> sort option) -> string -> typ
    26     val print_sg: sg -> unit
    25   val rep_sg: sg -> {tsig: Type.type_sig,
    27     val pprint_sg: sg -> pprint_args -> unit
    26                      const_tab: typ Symtab.table,
    28     val pretty_term: sg -> term -> Syntax.Pretty.T
    27                      syn: Syntax.syntax,
    29     val pretty_typ: sg -> typ -> Syntax.Pretty.T
    28                      stamps: string ref list}
    30     val string_of_term: sg -> term -> string
    29   val string_of_term: sg -> term -> string
    31     val string_of_typ: sg -> typ -> string
    30   val string_of_typ: sg -> typ -> string
    32     val pprint_term: sg -> term -> pprint_args -> unit
    31   val subsig: sg * sg -> bool
    33     val pprint_typ: sg -> typ -> pprint_args -> unit
    32   val pprint_term: sg -> term -> pprint_args -> unit
    34     val certify_typ: sg -> typ -> typ
    33   val pprint_typ: sg -> typ -> pprint_args -> unit
    35     val certify_term: sg -> term -> term * typ * int
    34   val pretty_term: sg -> term -> Syntax.Pretty.T
    36     val read_typ: sg * (indexname -> sort option) -> string -> typ
    35   val term_errors: sg -> term -> string list
    37     val extend: sg -> string ->
       
    38       (class * class list) list * class list *
       
    39       (string list * int) list *
       
    40       (string * string list * string) list *
       
    41       (string list * (sort list * class)) list *
       
    42       (string list * string) list * Syntax.sext option -> sg
       
    43     val merge: sg * sg -> sg
       
    44     val pure: sg
       
    45   end
    36 end;
    46 end;
    37 
    47 
    38 functor SignFun(structure Type: TYPE and Syntax: SYNTAX) : SIGN =
    48 functor SignFun(structure Syntax: SYNTAX and Type: TYPE): SIGN =
    39 struct
    49 struct
    40 
    50 
    41 structure Type = Type;
       
    42 structure Symtab = Type.Symtab;
    51 structure Symtab = Type.Symtab;
    43 structure Syntax = Syntax;
    52 structure Syntax = Syntax;
    44 structure Pretty = Syntax.Pretty
    53 structure Pretty = Syntax.Pretty;
    45 
    54 structure Type = Type;
    46 
    55 open Type;
    47 (* Signatures of theories. *)
    56 
       
    57 
       
    58 (** datatype sg **)
       
    59 
       
    60 (*the "ref" in stamps ensures that no two signatures are identical -- it is
       
    61   impossible to forge a signature*)
    48 
    62 
    49 datatype sg =
    63 datatype sg =
    50   Sg of {
    64   Sg of {
    51     tsig: Type.type_sig,            (*order-sorted signature of types*)
    65     tsig: type_sig,                 (*order-sorted signature of types*)
    52     const_tab: typ Symtab.table,    (*types of constants*)
    66     const_tab: typ Symtab.table,    (*types of constants*)
    53     syn: Syntax.syntax,             (*syntax for parsing and printing*)
    67     syn: Syntax.syntax,             (*syntax for parsing and printing*)
    54     stamps: string ref list};       (*unique theory indentifier*)
    68     stamps: string ref list};       (*unique theory indentifier*)
    55 
    69 
    56 
       
    57 fun rep_sg (Sg args) = args;
    70 fun rep_sg (Sg args) = args;
    58 
    71 
    59 fun subsig(Sg{stamps=s1,...},Sg{stamps=s2,...}) = s1 subset s2;
    72 
    60 
    73 fun subsig (Sg {stamps = s1, ...}, Sg {stamps = s2, ...}) = s1 subset s2;
    61 fun string_of_typ(Sg{tsig,syn,...}) = Syntax.string_of_typ syn;
    74 
    62 
    75 fun eq_sg (sg1, sg2) = subsig (sg1, sg2) andalso subsig (sg2, sg1);
    63 fun pprint_typ(Sg{syn,...}) = Pretty.pprint o Pretty.quote o (Syntax.pretty_typ syn);
    76 
    64 
    77 
    65 (*Is constant present in table with more generic type?*)
    78 
    66 fun valid_const tsig ctab (a,T) = case Symtab.lookup(ctab, a) of
    79 (** print signature **)
    67         Some U => Type.typ_instance(tsig,T,U) | _ => false;
    80 
    68 
    81 fun print_sg sg =
    69 
       
    70 (*Check a term for errors.  Are all constants and types valid in signature?
       
    71   Does not check that term is well-typed!*)
       
    72 fun term_errors (sign as Sg{tsig,const_tab,...}) =
       
    73   let val showtyp = string_of_typ sign
       
    74       fun terrs (Const (a,T), errs) =
       
    75 	  if valid_const tsig const_tab (a,T)
       
    76 	  then Type.type_errors tsig (T,errs)
       
    77 	  else ("Illegal type for constant: " ^ a ^ ": " ^ showtyp T) :: errs
       
    78 	| terrs (Free (_,T), errs) = Type.type_errors tsig (T,errs)
       
    79 	| terrs (Var  ((a,i),T), errs) =
       
    80 	  if  i>=0  then  Type.type_errors tsig (T,errs)
       
    81 	  else  ("Negative index for Var: " ^ a) :: errs
       
    82 	| terrs (Bound _, errs) = errs (*loose bvars detected by type_of*)
       
    83 	| terrs (Abs (_,T,t), errs) =
       
    84 	      Type.type_errors tsig (T,terrs(t,errs))
       
    85 	| terrs (f$t, errs) = terrs(f, terrs (t,errs))
       
    86   in  fn t => terrs(t,[])  end;
       
    87 
       
    88 
       
    89 
       
    90 (** The Extend operation **)
       
    91 
       
    92 (* Extend a signature: may add classes, types and constants. The "ref" in
       
    93    stamps ensures that no two signatures are identical -- it is impossible to
       
    94    forge a signature. *)
       
    95 
       
    96 fun extend (Sg {tsig, const_tab, syn, stamps}) name
       
    97   (classes, default, types, abbr, arities, const_decs, opt_sext) =
       
    98   let
    82   let
    99     fun err_in_typ s = error ("The error(s) above occurred in type " ^ quote s);
    83     fun prt_typ syn ty = Pretty.quote (Syntax.pretty_typ syn ty);
   100 
    84 
   101     fun read_typ tsg sy s =
    85     fun pretty_sort [cl] = Pretty.str cl
   102       Syntax.read_typ sy (K (Type.defaultS tsg)) s handle ERROR => err_in_typ s;
    86       | pretty_sort cls = Pretty.str_list "{" "}" cls;
   103 
    87 
   104     fun check_typ tsg sy ty =
    88     fun pretty_subclass (cl, cls) = Pretty.block
   105       (case Type.type_errors tsg (ty, []) of
    89       [Pretty.str (cl ^ " <"), Pretty.brk 1, pretty_sort cls];
   106         [] => ty
    90 
   107       | errs => (prs (cat_lines errs); err_in_typ (Syntax.string_of_typ sy ty)));
    91     fun pretty_default cls = Pretty.block
   108 
    92       [Pretty.str "default:", Pretty.brk 1, pretty_sort cls];
   109     (*reset TVar indices to zero, renaming to preserve distinctness*)
    93 
   110     fun zero_tvar_indices T =
    94     fun pretty_arg (ty, n) = Pretty.str (ty ^ " " ^ string_of_int n);
       
    95 
       
    96     fun pretty_abbr syn (ty, (vs, rhs)) = Pretty.block
       
    97       [prt_typ syn (Type (ty, map (fn v => TVar (v, [])) vs)),
       
    98         Pretty.str " =", Pretty.brk 1, prt_typ syn rhs];
       
    99 
       
   100     fun pretty_arity ty (cl, []) = Pretty.block
       
   101           [Pretty.str (ty ^ " ::"), Pretty.brk 1, Pretty.str cl]
       
   102       | pretty_arity ty (cl, srts) = Pretty.block
       
   103           [Pretty.str (ty ^ " ::"), Pretty.brk 1,
       
   104             Pretty.list "(" ")" (map pretty_sort srts),
       
   105             Pretty.brk 1, Pretty.str cl];
       
   106 
       
   107     fun pretty_coreg (ty, ars) = map (pretty_arity ty) ars;
       
   108 
       
   109     fun pretty_const syn (c, ty) = Pretty.block
       
   110       [Pretty.str (c ^ " ::"), Pretty.brk 1, prt_typ syn ty];
       
   111 
       
   112 
       
   113     val Sg {tsig, const_tab, syn, stamps} = sg;
       
   114     val {classes, subclass, default, args, abbrs, coreg} = rep_tsig tsig;
       
   115   in
       
   116     Pretty.writeln (Pretty.strs ("stamps:" :: map ! stamps));
       
   117     Pretty.writeln (Pretty.strs ("classes:" :: classes));
       
   118     Pretty.writeln (Pretty.big_list "subclass:" (map pretty_subclass subclass));
       
   119     Pretty.writeln (pretty_default default);
       
   120     Pretty.writeln (Pretty.big_list "types:" (map pretty_arg args));
       
   121     Pretty.writeln (Pretty.big_list "abbrs:" (map (pretty_abbr syn) abbrs));
       
   122     Pretty.writeln (Pretty.big_list "coreg:" (flat (map pretty_coreg coreg)));
       
   123     Pretty.writeln (Pretty.big_list "consts:"
       
   124       (map (pretty_const syn) (Symtab.alist_of const_tab)))
       
   125   end;
       
   126 
       
   127 
       
   128 fun pprint_sg (Sg {stamps, ...}) =
       
   129   Pretty.pprint (Pretty.str_list "{" "}" (map ! stamps));
       
   130 
       
   131 
       
   132 
       
   133 (** pretty printing of terms and types **)
       
   134 
       
   135 fun pretty_term (Sg {syn, ...}) = Syntax.pretty_term syn;
       
   136 fun pretty_typ (Sg {syn, ...}) = Syntax.pretty_typ syn;
       
   137 
       
   138 fun string_of_term (Sg {syn, ...}) = Syntax.string_of_term syn;
       
   139 fun string_of_typ (Sg {syn, ...}) = Syntax.string_of_typ syn;
       
   140 
       
   141 fun pprint_term sg = Pretty.pprint o Pretty.quote o (pretty_term sg);
       
   142 fun pprint_typ sg = Pretty.pprint o Pretty.quote o (pretty_typ sg);
       
   143 
       
   144 
       
   145 
       
   146 (** certify types and terms **)
       
   147 
       
   148 (*errors are indicated by exception TYPE*)
       
   149 
       
   150 fun certify_typ (Sg {tsig, ...}) ty = cert_typ tsig ty;
       
   151 
       
   152 
       
   153 (* FIXME -> term.ML (?) *)
       
   154 fun mapfilter_atoms f (Abs (_, _, t)) = mapfilter_atoms f t
       
   155   | mapfilter_atoms f (t $ u) = mapfilter_atoms f t @ mapfilter_atoms f u
       
   156   | mapfilter_atoms f a = (case f a of Some y => [y] | None => []);
       
   157 
       
   158 fun certify_term (sg as Sg {tsig, const_tab, ...}) tm =
       
   159   let
       
   160     fun valid_const a T =
       
   161       (case Symtab.lookup (const_tab, a) of
       
   162         Some U => typ_instance (tsig, T, U)
       
   163       | _ => false);
       
   164 
       
   165     fun atom_err (Const (a, T)) =
       
   166           if valid_const a T then None
       
   167           else Some ("Illegal type for constant " ^ quote a ^ " :: " ^
       
   168             quote (string_of_typ sg T))
       
   169       | atom_err (Var ((x, i), _)) =
       
   170           if i < 0 then Some ("Negative index for Var " ^ quote x) else None
       
   171       | atom_err _ = None;
       
   172 
       
   173 
       
   174     val norm_tm =
       
   175       (case it_term_types (typ_errors tsig) (tm, []) of
       
   176         [] => map_term_types (norm_typ tsig) tm
       
   177       | errs => raise_type (cat_lines errs) [] [tm]);
       
   178   in
       
   179     (case mapfilter_atoms atom_err norm_tm of
       
   180       [] => (norm_tm, type_of norm_tm, maxidx_of_term norm_tm)
       
   181     | errs => raise_type (cat_lines errs) [] [norm_tm])
       
   182   end;
       
   183 
       
   184 
       
   185 
       
   186 (** read types **)
       
   187 
       
   188 (*read and certify typ wrt a signature; errors are indicated by
       
   189   exception ERROR (with messages already printed)*)
       
   190 
       
   191 fun rd_typ tsig syn sort_of s =
       
   192   let
       
   193     val def_sort = defaultS tsig;
       
   194     val raw_ty =        (*this may raise ERROR, too!*)
       
   195       Syntax.read_typ syn (fn x => if_none (sort_of x) def_sort) s;
       
   196   in
       
   197     cert_typ tsig raw_ty
       
   198       handle TYPE (msg, _, _) => error msg
       
   199   end
       
   200   handle ERROR => error ("The error(s) above occurred in type " ^ quote s);
       
   201 
       
   202 fun read_typ (Sg {tsig, syn, ...}, sort_of) s = rd_typ tsig syn sort_of s;
       
   203 
       
   204 
       
   205 
       
   206 (** extend signature **)
       
   207 
       
   208 (*errors are indicated by exception ERROR (with messages already printed)*)
       
   209 
       
   210 fun extend sg name (classes, default, types, abbrs, arities, consts, opt_sext) =
       
   211   let
       
   212     (*reset TVar indices to 0, renaming to preserve distinctness*)
       
   213     fun zero_tvar_idxs T =
   111       let
   214       let
   112         val inxSs = typ_tvars T;
   215         val inxSs = typ_tvars T;
   113         val nms' = variantlist (map (#1 o #1) inxSs, []);
   216         val nms' = variantlist (map (#1 o #1) inxSs, []);
   114         val tye = map (fn ((v, S), a) => (v, TVar ((a, 0), S))) (inxSs ~~ nms');
   217         val tye = map2 (fn ((v, S), a) => (v, TVar ((a, 0), S))) (inxSs, nms');
   115       in typ_subst_TVars tye T end;
   218       in
       
   219         typ_subst_TVars tye T
       
   220       end;
   116 
   221 
   117     (*read and check the type mentioned in a const declaration; zero type var
   222     (*read and check the type mentioned in a const declaration; zero type var
   118       indices because type inference requires it*)
   223       indices because type inference requires it*)
   119 
   224     fun read_const tsig syn (c, s) =
   120     fun read_consts tsg sy (cs, s) =
   225       (c, zero_tvar_idxs (varifyT (rd_typ tsig syn (K None) s)))
   121       let val ty = zero_tvar_indices (Type.varifyT (read_typ tsg sy s));
   226         handle ERROR => error ("in declaration of constant " ^ quote c);
   122       in
   227 
   123         (case Type.type_errors tsg (ty, []) of
   228     fun read_abbr tsig syn (c, vs, rhs_src) =
   124           [] => (cs, ty)
   229       (c, (map (rpair 0) vs, varifyT (rd_typ tsig syn (K None) rhs_src)
   125         | errs => error (cat_lines (("Error in type of constants " ^
   230         handle ERROR => error ("in type abbreviation " ^ quote c)));
   126             space_implode " " (map quote cs)) :: errs)))
   231 
   127       end;
   232 
   128 
   233     val Sg {tsig, const_tab, syn, stamps} = sg;
   129     val tsig' = Type.extend (tsig, classes, default, types, arities);
   234     val xconsts = map #1 classes @ flat (map #1 types) @ map #1 abbrs @
   130 
   235       flat (map #1 consts);
   131     fun read_typ_abbr(a,v,s)=
   236     val sext = if_none opt_sext Syntax.empty_sext;
   132       let val T = Type.varifyT(read_typ tsig' syn s)
   237 
   133       in (a,(v,T)) end handle ERROR => error("This error occured in abbreviation "^ quote a);
   238     val tsig' = extend_tsig tsig (classes, default, types, arities);
   134 
   239     val tsig1 = ext_tsig_abbrs tsig' (map (read_abbr tsig' syn) abbrs);
   135     val abbr' = map read_typ_abbr abbr;
   240 
   136     val tsig'' = Type.add_abbrs(tsig',abbr');
   241     val syn1 = Syntax.extend syn (rd_typ tsig1 syn (K None))
   137 
   242       (logical_types tsig1, xconsts, sext);
   138     val read_ty =
   243 
   139       (Type.expand_typ tsig'') o (check_typ tsig'' syn) o (read_typ tsig'' syn);
   244     val all_consts = flat (map (fn (cs, s) => map (rpair s) cs)
   140     val log_types = Type.logical_types tsig'';
   245       (Syntax.constants sext @ consts));
   141     val xconsts = map #1 classes @ flat (map #1 types) @ flat (map #1 const_decs);
   246 
   142     val sext = case opt_sext of Some sx => sx | None => Syntax.empty_sext;
   247     val const_tab1 =                              (* FIXME bug: vvvv should be syn *)
   143 
   248       Symtab.extend (K false) (const_tab, map (read_const tsig1 syn1) all_consts)
   144     val syn' = Syntax.extend syn read_ty (log_types, xconsts, sext);
   249         handle Symtab.DUPLICATE c
   145 
   250           => error ("Constant " ^ quote c ^ " declared twice");
   146     val const_decs' =
   251 
   147       map (read_consts tsig'' syn') (Syntax.constants sext @ const_decs);
   252     val stamps1 =
       
   253       if exists (equal name o !) stamps then
       
   254         error ("Theory already contains a " ^ quote name ^ " component")
       
   255       else stamps @ [ref name];
   148   in
   256   in
   149     Sg {
   257     Sg {tsig = tsig1, const_tab = const_tab1, syn = syn1, stamps = stamps1}
   150       tsig = tsig'',
       
   151       const_tab = Symtab.st_of_declist (const_decs', const_tab)
       
   152         handle Symtab.DUPLICATE a => error ("Constant " ^ quote a ^ " declared twice"),
       
   153       syn = syn',
       
   154       stamps = ref name :: stamps}
       
   155   end;
   258   end;
   156 
   259 
   157 
   260 
   158 (* The empty signature *)
   261 
   159 
   262 (** merge signatures **)
   160 val sg0 = Sg {tsig = Type.tsig0, const_tab = Symtab.null,
   263 
       
   264 (*errors are indicated by exception TERM*)
       
   265 
       
   266 fun check_stamps stamps =
       
   267   (case duplicates (map ! stamps) of
       
   268     [] => stamps
       
   269   | dups => raise_term ("Attempt to merge different versions of theories " ^
       
   270       commas (map quote dups)) []);
       
   271 
       
   272 fun merge (sg1, sg2) =
       
   273   if subsig (sg2, sg1) then sg1
       
   274   else if subsig (sg1, sg2) then sg2
       
   275   else
       
   276     (*neither is union already; must form union*)
       
   277     let
       
   278       val Sg {tsig = tsig1, const_tab = const_tab1, syn = syn1,
       
   279         stamps = stamps1} = sg1;
       
   280       val Sg {tsig = tsig2, const_tab = const_tab2, syn = syn2,
       
   281         stamps = stamps2} = sg2;
       
   282 
       
   283       val tsig = merge_tsigs (tsig1, tsig2);
       
   284 
       
   285       val const_tab = Symtab.merge (op =) (const_tab1, const_tab2)
       
   286         handle Symtab.DUPLICATE c =>
       
   287           raise_term ("Incompatible types for constant " ^ quote c) [];
       
   288 
       
   289       val syn = Syntax.merge (logical_types tsig) syn1 syn2;
       
   290 
       
   291       val stamps = check_stamps (merge_lists stamps1 stamps2);
       
   292     in
       
   293       Sg {tsig = tsig, const_tab = const_tab, syn = syn, stamps = stamps}
       
   294     end;
       
   295 
       
   296 
       
   297 
       
   298 (** the Pure signature **)
       
   299 
       
   300 val sg0 = Sg {tsig = tsig0, const_tab = Symtab.null,
   161   syn = Syntax.type_syn, stamps = []};
   301   syn = Syntax.type_syn, stamps = []};
   162 
   302 
   163 
       
   164 (* The pure signature *)
       
   165 
       
   166 val pure = extend sg0 "Pure"
   303 val pure = extend sg0 "Pure"
   167 ([("logic", [])],
   304   ([("logic", [])],
   168  ["logic"],
   305    ["logic"],
   169  [(["fun"], 2),
   306    [(["fun"], 2),
   170   (["prop"], 0),
   307     (["prop"], 0),
   171   (Syntax.syntax_types, 0)],
   308     (Syntax.syntax_types, 0)],
   172  [],
   309    [],
   173  [(["fun"],  ([["logic"], ["logic"]], "logic")),
   310    [(["fun"],  ([["logic"], ["logic"]], "logic")),
   174   (["prop"], ([], "logic"))],
   311     (["prop"], ([], "logic"))],
   175  [([Syntax.constrainC], "'a::logic => 'a")],
   312    ([Syntax.constrainC], "'a::{} => 'a") :: Syntax.syntax_consts,
   176  Some Syntax.pure_sext);
   313    Some Syntax.pure_sext);
   177 
   314 
   178 
       
   179 
       
   180 (** The Merge operation **)
       
   181 
       
   182 (*Update table with (a,x) providing any existing asgt to "a" equals x. *)
       
   183 fun update_eq ((a,x),tab) =
       
   184     case Symtab.lookup(tab,a) of
       
   185         None => Symtab.update((a,x), tab)
       
   186       | Some y => if x=y then tab
       
   187             else  raise TERM ("Incompatible types for constant: "^a, []);
       
   188 
       
   189 (*Combine tables, updating tab2 by tab1 and checking.*)
       
   190 fun merge_tabs (tab1,tab2) =
       
   191     Symtab.balance (foldr update_eq (Symtab.alist_of tab1, tab2));
       
   192 
       
   193 (*Combine tables, overwriting tab2 with tab1.*)
       
   194 fun smash_tabs (tab1,tab2) =
       
   195     Symtab.balance (foldr Symtab.update (Symtab.alist_of tab1, tab2));
       
   196 
       
   197 (*Combine stamps, checking that theory names are disjoint. *)
       
   198 fun merge_stamps (stamps1,stamps2) =
       
   199   let val stamps = stamps1 union stamps2 in
       
   200   case findrep (map ! stamps) of
       
   201      a::_ => error ("Attempt to merge different versions of theory: " ^ a)
       
   202    | [] => stamps
       
   203   end;
       
   204 
       
   205 (*Merge two signatures.  Forms unions of tables.  Prefers sign1. *)
       
   206 fun merge
       
   207   (sign1 as Sg {tsig = tsig1, const_tab = ctab1, stamps = stamps1, syn = syn1},
       
   208    sign2 as Sg {tsig = tsig2, const_tab = ctab2, stamps = stamps2, syn = syn2}) =
       
   209     if stamps2 subset stamps1 then sign1
       
   210     else if stamps1 subset stamps2 then sign2
       
   211     else (*neither is union already; must form union*)
       
   212       let val tsig = Type.merge (tsig1, tsig2);
       
   213       in
       
   214         Sg {tsig = tsig, const_tab = merge_tabs (ctab1, ctab2),
       
   215           stamps = merge_stamps (stamps1, stamps2),
       
   216           syn = Syntax.merge (Type.logical_types tsig) syn1 syn2}
       
   217       end;
       
   218 
       
   219 
       
   220 
       
   221 fun read_typ(Sg{tsig,syn,...}, defS) s =
       
   222     let val term = Syntax.read syn Syntax.typeT s;
       
   223         val S0 = Type.defaultS tsig;
       
   224         fun defS0 s = case defS s of Some S => S | None => S0;
       
   225     in Syntax.typ_of_term defS0 term end;
       
   226 
       
   227 (** pretty printing of terms **)
       
   228 
       
   229 fun pretty_term (Sg{tsig,syn,...}) = Syntax.pretty_term syn;
       
   230 
       
   231 fun string_of_term sign t = Pretty.string_of (pretty_term sign t);
       
   232 
       
   233 fun pprint_term sign = Pretty.pprint o Pretty.quote o (pretty_term sign);
       
   234 
   315 
   235 end;
   316 end;
   236 
   317