src/Pure/context.ML
changeset 32738 15bb09ca0378
parent 31971 8c1b845ed105
child 32784 1a5dde5079ac
equal deleted inserted replaced
32737:76fa673eee8b 32738:15bb09ca0378
   105  {empty: Object.T,
   105  {empty: Object.T,
   106   copy: Object.T -> Object.T,
   106   copy: Object.T -> Object.T,
   107   extend: Object.T -> Object.T,
   107   extend: Object.T -> Object.T,
   108   merge: Pretty.pp -> Object.T * Object.T -> Object.T};
   108   merge: Pretty.pp -> Object.T * Object.T -> Object.T};
   109 
   109 
   110 val kinds = ref (Datatab.empty: kind Datatab.table);
   110 val kinds = Unsynchronized.ref (Datatab.empty: kind Datatab.table);
   111 
   111 
   112 fun invoke f k =
   112 fun invoke f k =
   113   (case Datatab.lookup (! kinds) k of
   113   (case Datatab.lookup (! kinds) k of
   114     SOME kind => f kind
   114     SOME kind => f kind
   115   | NONE => sys_error "Invalid theory data identifier");
   115   | NONE => sys_error "Invalid theory data identifier");
   123 
   123 
   124 fun declare_theory_data empty copy extend merge =
   124 fun declare_theory_data empty copy extend merge =
   125   let
   125   let
   126     val k = serial ();
   126     val k = serial ();
   127     val kind = {empty = empty, copy = copy, extend = extend, merge = merge};
   127     val kind = {empty = empty, copy = copy, extend = extend, merge = merge};
   128     val _ = CRITICAL (fn () => change kinds (Datatab.update (k, kind)));
   128     val _ = CRITICAL (fn () => Unsynchronized.change kinds (Datatab.update (k, kind)));
   129   in k end;
   129   in k end;
   130 
   130 
   131 val copy_data = Datatab.map' invoke_copy;
   131 val copy_data = Datatab.map' invoke_copy;
   132 val extend_data = Datatab.map' invoke_extend;
   132 val extend_data = Datatab.map' invoke_extend;
   133 
   133 
   147 (** datatype theory **)
   147 (** datatype theory **)
   148 
   148 
   149 datatype theory =
   149 datatype theory =
   150   Theory of
   150   Theory of
   151    (*identity*)
   151    (*identity*)
   152    {self: theory ref option,      (*dynamic self reference -- follows theory changes*)
   152    {self: theory Unsynchronized.ref option,  (*dynamic self reference -- follows theory changes*)
   153     draft: bool,                  (*draft mode -- linear destructive changes*)
   153     draft: bool,                  (*draft mode -- linear destructive changes*)
   154     id: serial,                   (*identifier*)
   154     id: serial,                   (*identifier*)
   155     ids: unit Inttab.table} *     (*cumulative identifiers of non-drafts -- symbolic body content*)
   155     ids: unit Inttab.table} *     (*cumulative identifiers of non-drafts -- symbolic body content*)
   156    (*data*)
   156    (*data*)
   157    Object.T Datatab.table *       (*body content*)
   157    Object.T Datatab.table *       (*body content*)
   184 (* staleness *)
   184 (* staleness *)
   185 
   185 
   186 fun eq_id (i: int, j) = i = j;
   186 fun eq_id (i: int, j) = i = j;
   187 
   187 
   188 fun is_stale
   188 fun is_stale
   189     (Theory ({self = SOME (ref (Theory ({id = id', ...}, _, _, _))), id, ...}, _, _, _)) =
   189     (Theory ({self =
       
   190         SOME (Unsynchronized.ref (Theory ({id = id', ...}, _, _, _))), id, ...}, _, _, _)) =
   190       not (eq_id (id, id'))
   191       not (eq_id (id, id'))
   191   | is_stale (Theory ({self = NONE, ...}, _, _, _)) = true;
   192   | is_stale (Theory ({self = NONE, ...}, _, _, _)) = true;
   192 
   193 
   193 fun vitalize (thy as Theory ({self = SOME r, ...}, _, _, _)) = (r := thy; thy)
   194 fun vitalize (thy as Theory ({self = SOME r, ...}, _, _, _)) = (r := thy; thy)
   194   | vitalize (thy as Theory ({self = NONE, draft, id, ids}, data, ancestry, history)) =
   195   | vitalize (thy as Theory ({self = NONE, draft, id, ids}, data, ancestry, history)) =
   195       let
   196       let
   196         val r = ref thy;
   197         val r = Unsynchronized.ref thy;
   197         val thy' = Theory (make_identity (SOME r) draft id ids, data, ancestry, history);
   198         val thy' = Theory (make_identity (SOME r) draft id ids, data, ancestry, history);
   198       in r := thy'; thy' end;
   199       in r := thy'; thy' end;
   199 
   200 
   200 
   201 
   201 (* draft mode *)
   202 (* draft mode *)
   241 
   242 
   242 (*theory_ref provides a safe way to store dynamic references to a
   243 (*theory_ref provides a safe way to store dynamic references to a
   243   theory in external data structures -- a plain theory value would
   244   theory in external data structures -- a plain theory value would
   244   become stale as the self reference moves on*)
   245   become stale as the self reference moves on*)
   245 
   246 
   246 datatype theory_ref = TheoryRef of theory ref;
   247 datatype theory_ref = TheoryRef of theory Unsynchronized.ref;
   247 
   248 
   248 fun deref (TheoryRef (ref thy)) = thy;
   249 fun deref (TheoryRef (Unsynchronized.ref thy)) = thy;
   249 
   250 
   250 fun check_thy thy =  (*thread-safe version*)
   251 fun check_thy thy =  (*thread-safe version*)
   251   let val thy_ref = TheoryRef (the_self thy) in
   252   let val thy_ref = TheoryRef (the_self thy) in
   252     if is_stale thy then error ("Stale theory encountered:\n" ^ string_of_thy thy)
   253     if is_stale thy then error ("Stale theory encountered:\n" ^ string_of_thy thy)
   253     else thy_ref
   254     else thy_ref
   435 
   436 
   436 (* proof data kinds *)
   437 (* proof data kinds *)
   437 
   438 
   438 local
   439 local
   439 
   440 
   440 val kinds = ref (Datatab.empty: (theory -> Object.T) Datatab.table);
   441 val kinds = Unsynchronized.ref (Datatab.empty: (theory -> Object.T) Datatab.table);
   441 
   442 
   442 fun invoke_init k =
   443 fun invoke_init k =
   443   (case Datatab.lookup (! kinds) k of
   444   (case Datatab.lookup (! kinds) k of
   444     SOME init => init
   445     SOME init => init
   445   | NONE => sys_error "Invalid proof data identifier");
   446   | NONE => sys_error "Invalid proof data identifier");
   468 struct
   469 struct
   469 
   470 
   470 fun declare init =
   471 fun declare init =
   471   let
   472   let
   472     val k = serial ();
   473     val k = serial ();
   473     val _ = CRITICAL (fn () => change kinds (Datatab.update (k, init)));
   474     val _ = CRITICAL (fn () => Unsynchronized.change kinds (Datatab.update (k, init)));
   474   in k end;
   475   in k end;
   475 
   476 
   476 fun get k dest prf =
   477 fun get k dest prf =
   477   dest (case Datatab.lookup (data_of_proof prf) k of
   478   dest (case Datatab.lookup (data_of_proof prf) k of
   478     SOME x => x
   479     SOME x => x