src/Pure/ProofGeneral/parsing.ML
author aspinall
Tue, 05 Dec 2006 22:04:24 +0100
changeset 21655 01b2d13153c8
parent 21637 a7b156c404e2
child 21867 8750fbc28d5c
permissions -rw-r--r--
Document structure in pgip_markup.ML. Minor fixes.
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
21637
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
     1
(*  Title:      Pure/ProofGeneral/parsing.ML
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
     2
    ID:         $Id$
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
     3
    Author:     David Aspinall
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
     4
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
     5
Parsing theory files to add PGIP markup.
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
     6
*)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
     7
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
     8
signature PGIP_PARSER =
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
     9
sig
21655
01b2d13153c8 Document structure in pgip_markup.ML. Minor fixes.
aspinall
parents: 21637
diff changeset
    10
    val xmls_of_str: string -> XML.content
21637
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    11
end
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    12
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    13
structure PgipParser : PGIP_PARSER =
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    14
struct
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    15
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    16
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    17
(** Parsing proof scripts without execution **)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    18
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    19
structure P = OuterParse;
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    20
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    21
(* Notes.
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    22
   This is quite tricky, because 1) we need to put back whitespace which
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    23
   was removed during parsing so we can provide markup around commands;
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    24
   2) parsing is intertwined with execution in Isar so we have to repeat
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    25
   the parsing to extract interesting parts of commands.  The trace of
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    26
   tokens parsed which is now recorded in each transition (added by
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    27
   Markus June '04) helps do this, but the mechanism is still a bad mess.
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    28
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    29
   If we had proper parse trees it would be easy, although having a
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    30
   fixed type of trees might be tricky with Isar's extensible parser.
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    31
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    32
   Probably the best solution is to produce the meta-information at
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    33
   the same time as the parse, for each command, e.g. by recording a
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    34
   list of (name,objtype) pairs which record the bindings created by
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    35
   a command.  This would require changing the interfaces in
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    36
   outer_syntax.ML (or providing new ones),
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    37
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    38
    datatype metainfo = Binding of string * string  (* name, objtype *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    39
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    40
    val command_withmetainfo: string -> string -> string ->
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    41
      (token list ->
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    42
       ((Toplevel.transition -> Toplevel.transition) * metainfo list) *
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    43
       token list) -> parser
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    44
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    45
   We'd also like to render terms as they appear in output, but this
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    46
   will be difficult because inner syntax is extensible and we don't
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    47
   have the correct syntax to hand when just doing outer parsing
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    48
   without execution.  A reasonable approximation could
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    49
   perhaps be obtained by using the syntax of the current context.
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    50
   However, this would mean more mess trying to pick out terms,
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    51
   so at this stage a more serious change to the Isar functions
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    52
   seems necessary.
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    53
*)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    54
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    55
local
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    56
    fun markup_text str elt = [XML.Elem(elt, [], [XML.Text str])]
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    57
    fun markup_text_attrs str elt attrs = [XML.Elem(elt, attrs, [XML.Text str])]
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    58
    fun empty elt = [XML.Elem(elt, [], [])]
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    59
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    60
    fun whitespace str = XML.Elem("whitespace", [], [XML.Text str])
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    61
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    62
    (* an extra token is needed to terminate the command *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    63
    val sync = OuterSyntax.scan "\\<^sync>";
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    64
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    65
    fun named_item_elt_with nameattr toks str elt nameP objtyp =
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    66
        let
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    67
            val name = (fst (nameP (toks@sync)))
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    68
                        handle _ => (error ("Error occurred in name parser for " ^ elt ^
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    69
                                            "(objtype: " ^ objtyp ^ ")");
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    70
                                     "")
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    71
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    72
        in
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    73
            [XML.Elem(elt,
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    74
                     ((if name="" then [] else [(nameattr, name)])@
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    75
                      (if objtyp="" then [] else [("objtype", objtyp)])),
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    76
                     [XML.Text str])]
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    77
        end
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    78
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    79
    val named_item_elt = named_item_elt_with "name"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    80
    val thmnamed_item_elt = named_item_elt_with "thmname"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    81
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    82
    fun parse_warning msg = warning ("script->PGIP markup parser: " ^ msg)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    83
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    84
    (* FIXME: allow dynamic extensions to language here: we need a hook in
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    85
       outer_syntax.ML to reset this table. *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    86
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    87
    val keywords_classification_table = ref (NONE: string Symtab.table option)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    88
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    89
    fun get_keywords_classification_table () =
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    90
        case (!keywords_classification_table) of
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    91
          SOME t => t
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    92
        | NONE => (let
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    93
                     val tab = fold (fn (c, _, k, _) => Symtab.update (c, k))
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    94
                                    (OuterSyntax.dest_parsers ()) Symtab.empty;
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    95
                   in (keywords_classification_table := SOME tab; tab) end)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    96
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    97
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    98
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
    99
    fun xmls_of_thy_begin (name,toks,str) = (* see isar_syn.ML/theoryP *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   100
        let
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   101
            val ((thyname,imports,files),_) = ThyHeader.args (toks@sync)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   102
        in
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   103
            markup_text_attrs str "opentheory"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   104
                              ([("thyname",thyname)] @
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   105
                               (if imports=[] then [] else
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   106
                                [("parentnames", (space_implode ";" imports) ^ ";")]))
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   107
        end
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   108
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   109
    fun xmls_of_thy_decl (name,toks,str) = (* see isar_syn.ML/thy_decl cases  *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   110
        let
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   111
            (* NB: PGIP only deals with single name bindings at the moment;
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   112
               potentially we could markup grouped definitions several times but
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   113
               that might suggest the wrong structure to the editor?
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   114
               Better alternative would be to put naming closer around text,
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   115
               but to do that we'd be much better off modifying the real parser
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   116
               instead of reconstructing it here. *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   117
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   118
            val plain_items = (* no names, unimportant names, or too difficult *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   119
                ["defaultsort","arities","judgement","finalconsts",
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   120
                 "syntax", "nonterminals", "translations",
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   121
                 "global", "local", "hide",
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   122
                 "ML_setup", "setup", "method_setup",
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   123
                 "parse_ast_translation", "parse_translation", "print_translation",
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   124
                 "typed_print_translation", "print_ast_translation", "token_translation",
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   125
                 "oracle",
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   126
                 "declare"]
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   127
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   128
            val plain_item   = markup_text str "theoryitem"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   129
            val comment_item = markup_text str "doccomment"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   130
            val named_item   = named_item_elt toks str "theoryitem"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   131
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   132
            val opt_overloaded = P.opt_keyword "overloaded";
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   133
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   134
            val thmnameP = (* see isar_syn.ML/theoremsP *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   135
                let
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   136
                    val name_facts = P.and_list1 ((P.opt_thm_name "=" --| P.xthms1) >> #1)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   137
                    val theoremsP = P.opt_locale_target |-- name_facts >> (fn [] => "" | x::_ => x)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   138
                in
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   139
                    theoremsP
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   140
                end
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   141
        in
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   142
            (* TODO: ideally we would like to render terms properly, just as they are
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   143
               in output. This implies using PGML for symbols and variables/atoms.
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   144
               BUT it's rather tricky without having the correct concrete syntax to hand,
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   145
               and even if we did, we'd have to mess around here a whole lot more first
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   146
               to pick out the terms from the syntax. *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   147
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   148
            if member (op =) plain_items name then plain_item
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   149
            else case name of
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   150
                     "text"      => comment_item
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   151
                   | "text_raw"  => comment_item
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   152
                   | "typedecl"  => named_item (P.type_args |-- P.name) "type"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   153
                   | "types"     => named_item (P.type_args |-- P.name) "type"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   154
                   | "classes"   => named_item P.name "class"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   155
                   | "classrel"  => named_item P.name "class"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   156
                   | "consts"    => named_item (P.const >> #1) "term"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   157
                   | "axioms"    => named_item (P.spec_name >> (#1 o #1)) "theorem"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   158
                   | "defs"      => named_item (opt_overloaded |-- P.spec_name >> (#1 o #1)) "theorem"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   159
                   | "constdefs" => named_item P.name (* FIXME: heavily simplified/wrong *) "term"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   160
                   | "theorems"  => named_item thmnameP "thmset"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   161
                   | "lemmas"    => named_item thmnameP "thmset"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   162
                   | "oracle"    => named_item P.name "oracle"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   163
                   | "locale"    => named_item ((P.opt_keyword "open" >> not) |-- P.name) "locale"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   164
                   | _ => (parse_warning ("Unrecognized thy-decl command: " ^ name); plain_item)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   165
        end
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   166
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   167
    fun xmls_of_thy_goal (name,toks,str) =
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   168
        let
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   169
            (* see isar_syn.ML/gen_theorem *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   170
         val statement = P.and_list1 (P.opt_thm_name ":" -- Scan.repeat1 P.propp);
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   171
         val general_statement =
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   172
            statement >> pair [] || Scan.repeat P.locale_element -- (P.$$$ "shows" |-- statement);
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   173
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   174
            val gen_theoremP =
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   175
                P.opt_locale_target -- Scan.optional (P.opt_thm_name ":" --|
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   176
                 Scan.ahead (P.locale_keyword || P.$$$ "shows")) ("", []) --
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   177
                                 general_statement >> (fn ((locale, a), (elems, concl)) =>
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   178
                                                         fst a) (* a : (bstring * Args.src list) *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   179
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   180
            val nameP = P.opt_locale_target |-- (Scan.optional ((P.opt_thm_name ":") >> #1) "")
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   181
            (* TODO: add preference values for attributes
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   182
               val prefval = XML.element "prefval" [("name","thm-kind"),("value",name)]
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   183
            *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   184
        in
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   185
            (thmnamed_item_elt toks str "opengoal" nameP "") @
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   186
            (empty "openblock")
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   187
        end
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   188
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   189
    fun xmls_of_qed (name,markup) =
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   190
        let val qedmarkup  =
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   191
                (case name of
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   192
                     "sorry" => markup "postponegoal"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   193
                   | "oops"  => markup "giveupgoal"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   194
                   | "done"  => markup "closegoal"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   195
                   | "by"    => markup "closegoal"  (* nested or toplevel *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   196
                   | "qed"   => markup "closegoal"  (* nested or toplevel *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   197
                   | "."     => markup "closegoal"  (* nested or toplevel *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   198
                   | ".."    => markup "closegoal"  (* nested or toplevel *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   199
                   | other => (* default to closegoal: may be wrong for extns *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   200
                                  (parse_warning
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   201
                                       ("Unrecognized qed command: " ^ quote other);
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   202
                                       markup "closegoal"))
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   203
        in qedmarkup @ (empty "closeblock") end
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   204
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   205
    fun xmls_of_kind kind (name,toks,str) =
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   206
    let val markup = markup_text str in
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   207
    case kind of
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   208
      "control"        => markup "badcmd"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   209
    | "diag"           => markup "spuriouscmd"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   210
    (* theory/files *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   211
    | "theory-begin"   => xmls_of_thy_begin (name,toks,str)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   212
    | "theory-decl"    => xmls_of_thy_decl (name,toks,str)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   213
    | "theory-heading" => markup "doccomment"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   214
    | "theory-script"  => markup "theorystep"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   215
    | "theory-end"     => markup "closetheory"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   216
    (* proof control *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   217
    | "theory-goal"    => xmls_of_thy_goal (name,toks,str)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   218
    | "proof-heading"  => markup "doccomment"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   219
    | "proof-goal"     => (markup "opengoal") @ (empty "openblock")  (* nested proof: have, show, ... *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   220
    | "proof-block"    => markup "proofstep" (* context-shift: proof, next; really "newgoal" *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   221
    | "proof-open"     => (empty "openblock") @ (markup "proofstep")
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   222
    | "proof-close"    => (markup "proofstep") @ (empty "closeblock")
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   223
    | "proof-script"   => markup "proofstep"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   224
    | "proof-chain"    => markup "proofstep"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   225
    | "proof-decl"     => markup "proofstep"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   226
    | "proof-asm"      => markup "proofstep"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   227
    | "proof-asm-goal" => (markup "opengoal") @ (empty "openblock")  (* nested proof: obtain *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   228
    | "qed"            => xmls_of_qed (name,markup)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   229
    | "qed-block"      => xmls_of_qed (name,markup)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   230
    | "qed-global"     => xmls_of_qed (name,markup)
21655
01b2d13153c8 Document structure in pgip_markup.ML. Minor fixes.
aspinall
parents: 21637
diff changeset
   231
    | other => (* default for anything else is "spuriouscmd", ignored for undo *)
21637
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   232
      (parse_warning ("Internal inconsistency, unrecognized keyword kind: " ^ quote other);
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   233
       markup "spuriouscmd")
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   234
    end
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   235
in
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   236
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   237
fun xmls_of_transition (name,str,toks) =
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   238
   let
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   239
     val classification = Symtab.lookup (get_keywords_classification_table ()) name
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   240
   in case classification of
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   241
          SOME k => (xmls_of_kind k (name,toks,str))
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   242
        | NONE => (* an uncategorized keyword ignored for undo (maybe wrong) *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   243
          (parse_warning ("Uncategorized command found: " ^ name ^ " -- using spuriouscmd");
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   244
           markup_text str "spuriouscmd")
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   245
   end
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   246
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   247
fun markup_toks [] _ = []
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   248
  | markup_toks toks x = markup_text (implode (map OuterLex.unparse toks)) x
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   249
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   250
fun markup_comment_whs [] = []
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   251
  | markup_comment_whs (toks as t::ts) = (* this would be a lot neater if we could match on toks! *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   252
    let
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   253
        val (prewhs,rest) = take_prefix (OuterLex.is_kind OuterLex.Space) toks
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   254
    in
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   255
        if (prewhs <> []) then
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   256
            whitespace (implode (map OuterLex.unparse prewhs))
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   257
            :: (markup_comment_whs rest)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   258
        else
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   259
            (markup_text (OuterLex.unparse t) "comment") @
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   260
            (markup_comment_whs ts)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   261
    end
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   262
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   263
fun xmls_pre_cmd [] = ([],[])
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   264
  | xmls_pre_cmd toks =
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   265
    let
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   266
        (* an extra token is needed to terminate the command *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   267
        val sync = OuterSyntax.scan "\\<^sync>";
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   268
        val spaceP = Scan.bulk (Scan.one (fn t =>not (OuterLex.is_proper t)) >> OuterLex.val_of) >> implode
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   269
        val text_with_whs =
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   270
            ((spaceP || Scan.succeed "") --
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   271
             (P.short_ident || P.long_ident || P.sym_ident || P.string || P.number || P.verbatim) >> op^)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   272
             -- (spaceP || Scan.succeed "") >> op^
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   273
        val (prewhs,rest1) = take_prefix (not o OuterLex.is_proper) (toks@sync)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   274
        (* NB: this collapses  litcomment,(litcomment|whitespace)* to a single litcomment *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   275
        val (_,rest2) = (Scan.bulk (P.$$$ "--" |-- text_with_whs) >> implode || Scan.succeed "") rest1
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   276
        val (postwhs,rest3) = take_prefix (not o OuterLex.is_proper) rest2
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   277
    in
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   278
        ((markup_comment_whs prewhs) @
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   279
         (if (length rest2 = length rest1)  then []
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   280
          else markup_text (implode
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   281
                                (map OuterLex.unparse (Library.take (length rest1 - length rest2, rest1))))
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   282
               "doccomment") @
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   283
         (markup_comment_whs postwhs),
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   284
         Library.take (length rest3 - 1,rest3))
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   285
    end
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   286
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   287
fun xmls_of_impropers toks =
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   288
    let
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   289
        val (xmls,rest) = xmls_pre_cmd toks
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   290
    in
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   291
        xmls @ (markup_toks rest "unparseable")
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   292
    end
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   293
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   294
fun markup_unparseable str = markup_text str "unparseable"
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   295
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   296
end
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   297
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   298
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   299
local
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   300
    (* we have to weave together the whitespace/comments with proper tokens
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   301
       to reconstruct the input. *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   302
    (* TODO: see if duplicating isar_output/parse_thy can help here *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   303
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   304
    fun match_tokens ([],us,vs) = (rev vs,us)  (* used, unused *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   305
      | match_tokens (t::ts,w::ws,vs) =
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   306
        if (t = w) then match_tokens (ts,ws,w::vs)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   307
        else match_tokens (t::ts,ws,w::vs)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   308
      | match_tokens _ = error ("match_tokens: mismatched input parse")
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   309
in
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   310
    fun xmls_of_str str =
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   311
    let
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   312
       (* parsing:   See outer_syntax.ML/toplevel_source *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   313
       fun parse_loop ([],[],xmls) = xmls
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   314
         | parse_loop ([],itoks,xmls) = xmls @ (xmls_of_impropers itoks)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   315
         | parse_loop ((nm,toks,_)::trs,itoks,xmls) =
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   316
           let
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   317
               (* first proper token after whitespace/litcomment/whitespace is command *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   318
               val (xmls_pre_cmd,cmditoks') = xmls_pre_cmd itoks
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   319
               val (cmdtok,itoks') = case cmditoks' of x::xs => (x,xs)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   320
                                                     | _ => error("proof_general/parse_loop impossible")
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   321
               val (utoks,itoks'') = match_tokens (toks,itoks',[])
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   322
               (* FIXME: should take trailing [w/s+] semicolon too in utoks *)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   323
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   324
               val str = implode (map OuterLex.unparse (cmdtok::utoks))
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   325
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   326
               val xmls_tr  = xmls_of_transition (nm,str,toks)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   327
           in
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   328
               parse_loop(trs,itoks'',xmls @ xmls_pre_cmd @ xmls_tr)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   329
           end
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   330
    in
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   331
        (let val toks = OuterSyntax.scan str
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   332
         in
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   333
             parse_loop (OuterSyntax.read toks, toks, [])
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   334
         end)
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   335
           handle _ => markup_unparseable str
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   336
    end
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   337
end
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   338
a7b156c404e2 Revamped Proof General interface.
aspinall
parents:
diff changeset
   339
end