(************************************************************************) (* * The Rocq Prover / The Rocq Development Team *) (* v * Copyright INRIA, CNRS and contributors *) (* <O___,, * (see version control and CREDITS file for authors & dates) *) (* \VV/ **************************************************************) (* // * This file is distributed under the terms of the *) (* * GNU Lesser General Public License Version 2.1 *) (* * (see LICENSE file for the text of the license) *) (************************************************************************)
open Util open Xml_datatype
type'annotation located = {
annotation : 'annotation option;
startpos : int;
endpos : int
}
type'a stack =
| Leaf
| Node ofstring * 'a located gxml list * int * 'a stack
type'a context = {
mutable stack : 'a stack; (** Pending opened nodes *)
mutable offset : int; (** Quantity of characters printed so far *)
}
(** We use Format to introduce tags inside the pretty-printed document. Eachinsertedtagisafreshindexthatwekeepinsyncwiththecontents ofannotations.
WebuildanXMLtreeonthefly,bypluggingourselvesinFormattag markingfunctions.Asthosefunctionsarecalledwhenactuallywritingto thedevice,theresultingtreeiscorrect.
*) let rich_pp ~width ?depth ppcmds =
let context = {
stack = Leaf;
offset = 0;
} in
let pp_buffer = Buffer.create 180in
let push_pcdata () = (* Push the optional PCData on the above node *) let len = Buffer.length pp_buffer in if len = 0then () elsematch context.stack with
| Leaf -> assert false
| Node (node, child, pos, ctx) -> let data = Buffer.contents pp_buffer in let () = Buffer.clear pp_buffer in let () = context.stack <- Node (node, PCData data :: child, pos, ctx) in
context.offset <- context.offset + len in
let open_xml_tag = function
| Format.String_tag tag -> let () = push_pcdata () in
context.stack <- Node (tag, [], context.offset, context.stack)
| _ -> () in
let close_xml_tag = function
| Format.String_tag tag -> let () = push_pcdata () in
(match context.stack with
| Leaf -> assert false
| Node (node, child, pos, ctx) -> let () = assert (String.equal tag node) in let annotation = {
annotation = Some tag;
startpos = pos;
endpos = context.offset;
} in let xml = Element (node, annotation, List.rev child) in match ctx with
| Leaf -> (* Final node: we keep the result in a dummy context *)
context.stack <- Node ("", [xml], 0, Leaf)
| Node (node, child, pos, ctx) ->
context.stack <- Node (node, xml :: child, pos, ctx))
| _ -> () in
letopen Format in
let ft = formatter_of_buffer pp_buffer in
let tag_functions = {
mark_open_stag = (fun tag -> let () = open_xml_tag tag in"");
mark_close_stag = (fun tag -> let () = close_xml_tag tag in"");
print_open_stag = ignore;
print_close_stag = ignore;
} in
pp_set_formatter_stag_functions ft tag_functions;
pp_set_mark_tags ft true;
(* Setting the formatter *)
pp_set_margin ft width; Option.iter (pp_set_max_boxes ft) depth; let m = max (64 * width / 100) (width-30) in
pp_set_max_indent ft m;
pp_set_max_boxes ft 50 ;
pp_set_ellipsis_text ft "...";
(* The whole output must be a valid document. To that
end, we nest the document inside <pp> tags. *)
pp_open_box ft 0;
pp_open_stag ft (String_tag "pp");
Pp.(pp_with ft ppcmds);
pp_close_stag ft ();
pp_close_box ft ();
(* Get the resulting XML tree. *) let () = pp_print_flush ft () in let () = assert (Buffer.length pp_buffer = 0) in match context.stack with
| Node ("", [xml], 0, Leaf) -> xml
| _ -> assert false
let annotations_positions xml = let rec node accu = function
| Element (_, { annotation = Some annotation; startpos; endpos }, cs) ->
children ((annotation, (startpos, endpos)) :: accu) cs
| Element (_, _, cs) ->
children accu cs
| _ ->
accu and children accu cs = List.fold_left node accu cs in
node [] xml
let xml_of_rich_pp tag_of_annotation attributes_of_annotation xml = let rec node = function
| Element (index, { annotation; startpos; endpos }, cs) -> let attributes =
[ "startpos", string_of_int startpos; "endpos", string_of_int endpos
]
@ (match annotation with
| None -> []
| Some annotation -> attributes_of_annotation annotation
) in let tag = match annotation with
| None -> index
| Some annotation -> tag_of_annotation annotation in
Element (tag, attributes, List.map node cs)
| PCData s ->
PCData s in
node xml
type richpp = xml
let richpp_of_pp ~width ?depth pp = let rec drop = function
| PCData s -> [PCData s]
| Element (_, annotation, cs) -> let cs = List.concat (List.map drop cs) in match annotation.annotation with
| None -> cs
| Some s -> [Element (s, [], cs)] in let xml = rich_pp ~width ?depth pp in
Element ("_", [], drop xml)
Messung V0.5 in Prozent
¤ Dauer der Verarbeitung: 0.12 Sekunden
(vorverarbeitet am 2026-06-10)
¤
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.