1 /* Helper routines for parsing XML using Expat.
3 Copyright (C) 2006, 2007 Free Software Foundation, Inc.
5 This file is part of GDB.
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 3 of the License, or
10 (at your option) any later version.
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with this program. If not, see <http://www.gnu.org/licenses/>. */
22 #include "exceptions.h"
23 #include "xml-support.h"
25 #include "gdb_string.h"
26 #include "safe-ctype.h"
31 /* The contents of this file are only useful if XML support is
35 #include "gdb_expat.h"
37 /* The maximum depth of <xi:include> nesting. No need to be miserly,
38 we just want to avoid running out of stack on loops. */
39 #define MAX_XINCLUDE_DEPTH 30
41 /* Simplified XML parser infrastructure. */
43 /* A parsing level -- used to keep track of the current element
47 /* Elements we allow at this level. */
48 const struct gdb_xml_element
*elements
;
50 /* The element which we are within. */
51 const struct gdb_xml_element
*element
;
53 /* Mask of which elements we've seen at this level (used for
54 optional and repeatable checking). */
57 /* Body text accumulation. */
60 typedef struct scope_level scope_level_s
;
61 DEF_VEC_O(scope_level_s
);
63 /* The parser itself, and our additional state. */
66 XML_Parser expat_parser
; /* The underlying expat parser. */
68 const char *name
; /* Name of this parser. */
69 void *user_data
; /* The user's callback data, for handlers. */
71 VEC(scope_level_s
) *scopes
; /* Scoping stack. */
73 struct gdb_exception error
; /* A thrown error, if any. */
74 int last_line
; /* The line of the thrown error, or 0. */
76 const char *dtd_name
; /* The name of the expected / default DTD,
78 int is_xinclude
; /* Are we the special <xi:include> parser? */
81 /* Process some body text. We accumulate the text for later use; it's
82 wrong to do anything with it immediately, because a single block of
83 text might be broken up into multiple calls to this function. */
86 gdb_xml_body_text (void *data
, const XML_Char
*text
, int length
)
88 struct gdb_xml_parser
*parser
= data
;
89 struct scope_level
*scope
= VEC_last (scope_level_s
, parser
->scopes
);
91 if (parser
->error
.reason
< 0)
94 if (scope
->body
== NULL
)
96 scope
->body
= XZALLOC (struct obstack
);
97 obstack_init (scope
->body
);
100 obstack_grow (scope
->body
, text
, length
);
103 /* Issue a debugging message from one of PARSER's handlers. */
106 gdb_xml_debug (struct gdb_xml_parser
*parser
, const char *format
, ...)
108 int line
= XML_GetCurrentLineNumber (parser
->expat_parser
);
115 va_start (ap
, format
);
116 message
= xstrvprintf (format
, ap
);
118 fprintf_unfiltered (gdb_stderr
, "%s (line %d): %s\n",
119 parser
->name
, line
, message
);
121 fprintf_unfiltered (gdb_stderr
, "%s: %s\n",
122 parser
->name
, message
);
126 /* Issue an error message from one of PARSER's handlers, and stop
130 gdb_xml_error (struct gdb_xml_parser
*parser
, const char *format
, ...)
132 int line
= XML_GetCurrentLineNumber (parser
->expat_parser
);
135 parser
->last_line
= line
;
136 va_start (ap
, format
);
137 throw_verror (XML_PARSE_ERROR
, format
, ap
);
140 /* Clean up a vector of parsed attribute values. */
143 gdb_xml_values_cleanup (void *data
)
145 VEC(gdb_xml_value_s
) **values
= data
;
146 struct gdb_xml_value
*value
;
149 for (ix
= 0; VEC_iterate (gdb_xml_value_s
, *values
, ix
, value
); ix
++)
150 xfree (value
->value
);
151 VEC_free (gdb_xml_value_s
, *values
);
154 /* Handle the start of an element. DATA is our local XML parser, NAME
155 is the element, and ATTRS are the names and values of this
156 element's attributes. */
159 gdb_xml_start_element (void *data
, const XML_Char
*name
,
160 const XML_Char
**attrs
)
162 struct gdb_xml_parser
*parser
= data
;
163 struct scope_level
*scope
;
164 struct scope_level new_scope
;
165 const struct gdb_xml_element
*element
;
166 const struct gdb_xml_attribute
*attribute
;
167 VEC(gdb_xml_value_s
) *attributes
= NULL
;
169 struct cleanup
*back_to
;
171 /* Push an error scope. If we return or throw an exception before
172 filling this in, it will tell us to ignore children of this
174 VEC_reserve (scope_level_s
, parser
->scopes
, 1);
175 scope
= VEC_last (scope_level_s
, parser
->scopes
);
176 memset (&new_scope
, 0, sizeof (new_scope
));
177 VEC_quick_push (scope_level_s
, parser
->scopes
, &new_scope
);
179 gdb_xml_debug (parser
, _("Entering element <%s>"), name
);
181 /* Find this element in the list of the current scope's allowed
182 children. Record that we've seen it. */
185 for (element
= scope
->elements
; element
&& element
->name
;
186 element
++, seen
<<= 1)
187 if (strcmp (element
->name
, name
) == 0)
190 if (element
== NULL
|| element
->name
== NULL
)
192 /* If we're working on XInclude, <xi:include> can be the child
193 of absolutely anything. Copy the previous scope's element
194 list into the new scope even if there was no match. */
195 if (parser
->is_xinclude
)
197 struct scope_level
*unknown_scope
;
199 XML_DefaultCurrent (parser
->expat_parser
);
201 unknown_scope
= VEC_last (scope_level_s
, parser
->scopes
);
202 unknown_scope
->elements
= scope
->elements
;
206 gdb_xml_debug (parser
, _("Element <%s> unknown"), name
);
210 if (!(element
->flags
& GDB_XML_EF_REPEATABLE
) && (seen
& scope
->seen
))
211 gdb_xml_error (parser
, _("Element <%s> only expected once"), name
);
215 back_to
= make_cleanup (gdb_xml_values_cleanup
, &attributes
);
217 for (attribute
= element
->attributes
;
218 attribute
!= NULL
&& attribute
->name
!= NULL
;
221 const char *val
= NULL
;
224 struct gdb_xml_value new_value
;
226 for (p
= attrs
; *p
!= NULL
; p
+= 2)
227 if (!strcmp (attribute
->name
, p
[0]))
233 if (*p
!= NULL
&& val
== NULL
)
235 gdb_xml_debug (parser
, _("Attribute \"%s\" missing a value"),
240 if (*p
== NULL
&& !(attribute
->flags
& GDB_XML_AF_OPTIONAL
))
242 gdb_xml_error (parser
, _("Required attribute \"%s\" of "
243 "<%s> not specified"),
244 attribute
->name
, element
->name
);
251 gdb_xml_debug (parser
, _("Parsing attribute %s=\"%s\""),
252 attribute
->name
, val
);
254 if (attribute
->handler
)
255 parsed_value
= attribute
->handler (parser
, attribute
, val
);
257 parsed_value
= xstrdup (val
);
259 new_value
.name
= attribute
->name
;
260 new_value
.value
= parsed_value
;
261 VEC_safe_push (gdb_xml_value_s
, attributes
, &new_value
);
264 /* Check for unrecognized attributes. */
269 for (p
= attrs
; *p
!= NULL
; p
+= 2)
271 for (attribute
= element
->attributes
;
272 attribute
!= NULL
&& attribute
->name
!= NULL
;
274 if (strcmp (attribute
->name
, *p
) == 0)
277 if (attribute
== NULL
|| attribute
->name
== NULL
)
278 gdb_xml_debug (parser
, _("Ignoring unknown attribute %s"), *p
);
282 /* Call the element handler if there is one. */
283 if (element
->start_handler
)
284 element
->start_handler (parser
, element
, parser
->user_data
, attributes
);
286 /* Fill in a new scope level. */
287 scope
= VEC_last (scope_level_s
, parser
->scopes
);
288 scope
->element
= element
;
289 scope
->elements
= element
->children
;
291 do_cleanups (back_to
);
294 /* Wrapper for gdb_xml_start_element, to prevent throwing exceptions
298 gdb_xml_start_element_wrapper (void *data
, const XML_Char
*name
,
299 const XML_Char
**attrs
)
301 struct gdb_xml_parser
*parser
= data
;
302 volatile struct gdb_exception ex
;
304 if (parser
->error
.reason
< 0)
307 TRY_CATCH (ex
, RETURN_MASK_ALL
)
309 gdb_xml_start_element (data
, name
, attrs
);
314 #ifdef HAVE_XML_STOPPARSER
315 XML_StopParser (parser
->expat_parser
, XML_FALSE
);
320 /* Handle the end of an element. DATA is our local XML parser, and
321 NAME is the current element. */
324 gdb_xml_end_element (void *data
, const XML_Char
*name
)
326 struct gdb_xml_parser
*parser
= data
;
327 struct scope_level
*scope
= VEC_last (scope_level_s
, parser
->scopes
);
328 const struct gdb_xml_element
*element
;
331 gdb_xml_debug (parser
, _("Leaving element <%s>"), name
);
333 for (element
= scope
->elements
, seen
= 1;
334 element
!= NULL
&& element
->name
!= NULL
;
335 element
++, seen
<<= 1)
336 if ((scope
->seen
& seen
) == 0
337 && (element
->flags
& GDB_XML_EF_OPTIONAL
) == 0)
338 gdb_xml_error (parser
, _("Required element <%s> is missing"),
341 /* Call the element processor. */
342 if (scope
->element
!= NULL
&& scope
->element
->end_handler
)
346 if (scope
->body
== NULL
)
352 length
= obstack_object_size (scope
->body
);
353 obstack_1grow (scope
->body
, '\0');
354 body
= obstack_finish (scope
->body
);
356 /* Strip leading and trailing whitespace. */
357 while (length
> 0 && ISSPACE (body
[length
-1]))
358 body
[--length
] = '\0';
359 while (*body
&& ISSPACE (*body
))
363 scope
->element
->end_handler (parser
, scope
->element
, parser
->user_data
,
366 else if (scope
->element
== NULL
)
367 XML_DefaultCurrent (parser
->expat_parser
);
369 /* Pop the scope level. */
372 obstack_free (scope
->body
, NULL
);
375 VEC_pop (scope_level_s
, parser
->scopes
);
378 /* Wrapper for gdb_xml_end_element, to prevent throwing exceptions
382 gdb_xml_end_element_wrapper (void *data
, const XML_Char
*name
)
384 struct gdb_xml_parser
*parser
= data
;
385 volatile struct gdb_exception ex
;
387 if (parser
->error
.reason
< 0)
390 TRY_CATCH (ex
, RETURN_MASK_ALL
)
392 gdb_xml_end_element (data
, name
);
397 #ifdef HAVE_XML_STOPPARSER
398 XML_StopParser (parser
->expat_parser
, XML_FALSE
);
403 /* Free a parser and all its associated state. */
406 gdb_xml_cleanup (void *arg
)
408 struct gdb_xml_parser
*parser
= arg
;
409 struct scope_level
*scope
;
412 XML_ParserFree (parser
->expat_parser
);
414 /* Clean up the scopes. */
415 for (ix
= 0; VEC_iterate (scope_level_s
, parser
->scopes
, ix
, scope
); ix
++)
418 obstack_free (scope
->body
, NULL
);
421 VEC_free (scope_level_s
, parser
->scopes
);
426 /* Initialize and return a parser. Register a cleanup to destroy the
429 struct gdb_xml_parser
*
430 gdb_xml_create_parser_and_cleanup (const char *name
,
431 const struct gdb_xml_element
*elements
,
434 struct gdb_xml_parser
*parser
;
435 struct scope_level start_scope
;
437 /* Initialize the parser. */
438 parser
= XZALLOC (struct gdb_xml_parser
);
439 parser
->expat_parser
= XML_ParserCreateNS (NULL
, '!');
440 if (parser
->expat_parser
== NULL
)
448 parser
->user_data
= user_data
;
449 XML_SetUserData (parser
->expat_parser
, parser
);
451 /* Set the callbacks. */
452 XML_SetElementHandler (parser
->expat_parser
, gdb_xml_start_element_wrapper
,
453 gdb_xml_end_element_wrapper
);
454 XML_SetCharacterDataHandler (parser
->expat_parser
, gdb_xml_body_text
);
456 /* Initialize the outer scope. */
457 memset (&start_scope
, 0, sizeof (start_scope
));
458 start_scope
.elements
= elements
;
459 VEC_safe_push (scope_level_s
, parser
->scopes
, &start_scope
);
461 make_cleanup (gdb_xml_cleanup
, parser
);
466 /* External entity handler. The only external entities we support
467 are those compiled into GDB (we do not fetch entities from the
471 gdb_xml_fetch_external_entity (XML_Parser expat_parser
,
472 const XML_Char
*context
,
473 const XML_Char
*base
,
474 const XML_Char
*systemId
,
475 const XML_Char
*publicId
)
477 struct gdb_xml_parser
*parser
= XML_GetUserData (expat_parser
);
478 XML_Parser entity_parser
;
480 enum XML_Status status
;
482 if (systemId
== NULL
)
484 text
= fetch_xml_builtin (parser
->dtd_name
);
486 internal_error (__FILE__
, __LINE__
, "could not locate built-in DTD %s",
491 text
= fetch_xml_builtin (systemId
);
493 return XML_STATUS_ERROR
;
496 entity_parser
= XML_ExternalEntityParserCreate (expat_parser
, context
, NULL
);
498 /* Don't use our handlers for the contents of the DTD. Just let expat
500 XML_SetElementHandler (entity_parser
, NULL
, NULL
);
501 XML_SetDoctypeDeclHandler (entity_parser
, NULL
, NULL
);
502 XML_SetXmlDeclHandler (entity_parser
, NULL
);
503 XML_SetDefaultHandler (entity_parser
, NULL
);
504 XML_SetUserData (entity_parser
, NULL
);
506 status
= XML_Parse (entity_parser
, text
, strlen (text
), 1);
508 XML_ParserFree (entity_parser
);
512 /* Associate DTD_NAME, which must be the name of a compiled-in DTD,
516 gdb_xml_use_dtd (struct gdb_xml_parser
*parser
, const char *dtd_name
)
520 parser
->dtd_name
= dtd_name
;
522 XML_SetParamEntityParsing (parser
->expat_parser
,
523 XML_PARAM_ENTITY_PARSING_UNLESS_STANDALONE
);
524 XML_SetExternalEntityRefHandler (parser
->expat_parser
,
525 gdb_xml_fetch_external_entity
);
527 /* Even if no DTD is provided, use the built-in DTD anyway. */
528 err
= XML_UseForeignDTD (parser
->expat_parser
, XML_TRUE
);
529 if (err
!= XML_ERROR_NONE
)
530 internal_error (__FILE__
, __LINE__
,
531 "XML_UseForeignDTD failed: %s", XML_ErrorString (err
));
534 /* Invoke PARSER on BUFFER. BUFFER is the data to parse, which
535 should be NUL-terminated.
537 The return value is 0 for success or -1 for error. It may throw,
538 but only if something unexpected goes wrong during parsing; parse
539 errors will be caught, warned about, and reported as failure. */
542 gdb_xml_parse (struct gdb_xml_parser
*parser
, const char *buffer
)
544 enum XML_Status status
;
545 const char *error_string
;
547 status
= XML_Parse (parser
->expat_parser
, buffer
, strlen (buffer
), 1);
549 if (status
== XML_STATUS_OK
&& parser
->error
.reason
== 0)
552 if (parser
->error
.reason
== RETURN_ERROR
553 && parser
->error
.error
== XML_PARSE_ERROR
)
555 gdb_assert (parser
->error
.message
!= NULL
);
556 error_string
= parser
->error
.message
;
558 else if (status
== XML_STATUS_ERROR
)
560 enum XML_Error err
= XML_GetErrorCode (parser
->expat_parser
);
561 error_string
= XML_ErrorString (err
);
565 gdb_assert (parser
->error
.reason
< 0);
566 throw_exception (parser
->error
);
569 if (parser
->last_line
!= 0)
570 warning (_("while parsing %s (at line %d): %s"), parser
->name
,
571 parser
->last_line
, error_string
);
573 warning (_("while parsing %s: %s"), parser
->name
, error_string
);
578 /* Parse a field VALSTR that we expect to contain an integer value.
579 The integer is returned in *VALP. The string is parsed with an
580 equivalent to strtoul.
582 Returns 0 for success, -1 for error. */
585 xml_parse_unsigned_integer (const char *valstr
, ULONGEST
*valp
)
593 result
= strtoulst (valstr
, &endptr
, 0);
601 /* Parse an integer string into a ULONGEST and return it, or call
602 gdb_xml_error if it could not be parsed. */
605 gdb_xml_parse_ulongest (struct gdb_xml_parser
*parser
, const char *value
)
609 if (xml_parse_unsigned_integer (value
, &result
) != 0)
610 gdb_xml_error (parser
, _("Can't convert \"%s\" to an integer"), value
);
615 /* Parse an integer attribute into a ULONGEST. */
618 gdb_xml_parse_attr_ulongest (struct gdb_xml_parser
*parser
,
619 const struct gdb_xml_attribute
*attribute
,
625 if (xml_parse_unsigned_integer (value
, &result
) != 0)
626 gdb_xml_error (parser
, _("Can't convert %s=\"%s\" to an integer"),
627 attribute
->name
, value
);
629 ret
= xmalloc (sizeof (result
));
630 memcpy (ret
, &result
, sizeof (result
));
634 /* A handler_data for yes/no boolean values. */
636 const struct gdb_xml_enum gdb_xml_enums_boolean
[] = {
642 /* Map NAME to VALUE. A struct gdb_xml_enum * should be saved as the
643 value of handler_data when using gdb_xml_parse_attr_enum to parse a
644 fixed list of possible strings. The list is terminated by an entry
645 with NAME == NULL. */
648 gdb_xml_parse_attr_enum (struct gdb_xml_parser
*parser
,
649 const struct gdb_xml_attribute
*attribute
,
652 const struct gdb_xml_enum
*enums
= attribute
->handler_data
;
655 for (enums
= attribute
->handler_data
; enums
->name
!= NULL
; enums
++)
656 if (strcasecmp (enums
->name
, value
) == 0)
659 if (enums
->name
== NULL
)
660 gdb_xml_error (parser
, _("Unknown attribute value %s=\"%s\""),
661 attribute
->name
, value
);
663 ret
= xmalloc (sizeof (enums
->value
));
664 memcpy (ret
, &enums
->value
, sizeof (enums
->value
));
669 /* XInclude processing. This is done as a separate step from actually
670 parsing the document, so that we can produce a single combined XML
671 document - e.g. to hand to a front end or to simplify comparing two
672 documents. We make extensive use of XML_DefaultCurrent, to pass
673 input text directly into the output without reformatting or
676 We output the DOCTYPE declaration for the first document unchanged,
677 if present, and discard DOCTYPEs from included documents. Only the
678 one we pass through here is used when we feed the result back to
679 expat. The XInclude standard explicitly does not discuss
680 validation of the result; we choose to apply the same DTD applied
681 to the outermost document.
683 We can not simply include the external DTD subset in the document
684 as an internal subset, because <!IGNORE> and <!INCLUDE> are valid
685 only in external subsets. But if we do not pass the DTD into the
686 output at all, default values will not be filled in.
688 We don't pass through any <?xml> declaration because we generate
689 UTF-8, not whatever the input encoding was. */
691 struct xinclude_parsing_data
693 /* The obstack to build the output in. */
694 struct obstack obstack
;
696 /* A count indicating whether we are in an element whose
697 children should not be copied to the output, and if so,
698 how deep we are nested. This is used for anything inside
699 an xi:include, and for the DTD. */
702 /* The number of <xi:include> elements currently being processed,
706 /* A function to call to obtain additional features, and its
708 xml_fetch_another fetcher
;
713 xinclude_start_include (struct gdb_xml_parser
*parser
,
714 const struct gdb_xml_element
*element
,
715 void *user_data
, VEC(gdb_xml_value_s
) *attributes
)
717 struct xinclude_parsing_data
*data
= user_data
;
718 char *href
= VEC_index (gdb_xml_value_s
, attributes
, 0)->value
;
719 struct cleanup
*back_to
;
723 gdb_xml_debug (parser
, _("Processing XInclude of \"%s\""), href
);
725 if (data
->include_depth
> MAX_XINCLUDE_DEPTH
)
726 gdb_xml_error (parser
, _("Maximum XInclude depth (%d) exceeded"),
729 text
= data
->fetcher (href
, data
->fetcher_baton
);
731 gdb_xml_error (parser
, _("Could not load XML document \"%s\""), href
);
732 back_to
= make_cleanup (xfree
, text
);
734 output
= xml_process_xincludes (parser
->name
, text
, data
->fetcher
,
736 data
->include_depth
+ 1);
738 gdb_xml_error (parser
, _("Parsing \"%s\" failed"), href
);
740 obstack_grow (&data
->obstack
, output
, strlen (output
));
743 do_cleanups (back_to
);
749 xinclude_end_include (struct gdb_xml_parser
*parser
,
750 const struct gdb_xml_element
*element
,
751 void *user_data
, const char *body_text
)
753 struct xinclude_parsing_data
*data
= user_data
;
759 xml_xinclude_default (void *data_
, const XML_Char
*s
, int len
)
761 struct gdb_xml_parser
*parser
= data_
;
762 struct xinclude_parsing_data
*data
= parser
->user_data
;
764 /* If we are inside of e.g. xi:include or the DTD, don't save this
766 if (data
->skip_depth
)
769 /* Otherwise just add it to the end of the document we're building
771 obstack_grow (&data
->obstack
, s
, len
);
775 xml_xinclude_start_doctype (void *data_
, const XML_Char
*doctypeName
,
776 const XML_Char
*sysid
, const XML_Char
*pubid
,
777 int has_internal_subset
)
779 struct gdb_xml_parser
*parser
= data_
;
780 struct xinclude_parsing_data
*data
= parser
->user_data
;
782 /* Don't print out the doctype, or the contents of the DTD internal
788 xml_xinclude_end_doctype (void *data_
)
790 struct gdb_xml_parser
*parser
= data_
;
791 struct xinclude_parsing_data
*data
= parser
->user_data
;
797 xml_xinclude_xml_decl (void *data_
, const XML_Char
*version
,
798 const XML_Char
*encoding
, int standalone
)
800 /* Do nothing - this function prevents the default handler from
801 being called, thus suppressing the XML declaration from the
806 xml_xinclude_cleanup (void *data_
)
808 struct xinclude_parsing_data
*data
= data_
;
810 obstack_free (&data
->obstack
, NULL
);
814 const struct gdb_xml_attribute xinclude_attributes
[] = {
815 { "href", GDB_XML_AF_NONE
, NULL
, NULL
},
816 { NULL
, GDB_XML_AF_NONE
, NULL
, NULL
}
819 const struct gdb_xml_element xinclude_elements
[] = {
820 { "http://www.w3.org/2001/XInclude!include", xinclude_attributes
, NULL
,
821 GDB_XML_EF_OPTIONAL
| GDB_XML_EF_REPEATABLE
,
822 xinclude_start_include
, xinclude_end_include
},
823 { NULL
, NULL
, NULL
, GDB_XML_EF_NONE
, NULL
, NULL
}
826 /* The main entry point for <xi:include> processing. */
829 xml_process_xincludes (const char *name
, const char *text
,
830 xml_fetch_another fetcher
, void *fetcher_baton
,
834 struct gdb_xml_parser
*parser
;
835 struct xinclude_parsing_data
*data
;
836 struct cleanup
*back_to
;
839 data
= XZALLOC (struct xinclude_parsing_data
);
840 obstack_init (&data
->obstack
);
841 back_to
= make_cleanup (xml_xinclude_cleanup
, data
);
843 parser
= gdb_xml_create_parser_and_cleanup (name
, xinclude_elements
, data
);
844 parser
->is_xinclude
= 1;
846 data
->include_depth
= depth
;
847 data
->fetcher
= fetcher
;
848 data
->fetcher_baton
= fetcher_baton
;
850 XML_SetCharacterDataHandler (parser
->expat_parser
, NULL
);
851 XML_SetDefaultHandler (parser
->expat_parser
, xml_xinclude_default
);
853 /* Always discard the XML version declarations; the only important
854 thing this provides is encoding, and our result will have been
855 converted to UTF-8. */
856 XML_SetXmlDeclHandler (parser
->expat_parser
, xml_xinclude_xml_decl
);
859 /* Discard the doctype for included documents. */
860 XML_SetDoctypeDeclHandler (parser
->expat_parser
,
861 xml_xinclude_start_doctype
,
862 xml_xinclude_end_doctype
);
864 gdb_xml_use_dtd (parser
, "xinclude.dtd");
866 if (gdb_xml_parse (parser
, text
) == 0)
868 obstack_1grow (&data
->obstack
, '\0');
869 result
= xstrdup (obstack_finish (&data
->obstack
));
872 gdb_xml_debug (parser
, _("XInclude processing succeeded:\n%s"),
878 do_cleanups (back_to
);
881 #endif /* HAVE_LIBEXPAT */
884 /* Return an XML document which was compiled into GDB, from
885 the given FILENAME, or NULL if the file was not compiled in. */
888 fetch_xml_builtin (const char *filename
)
892 for (p
= xml_builtin
; (*p
)[0]; p
++)
893 if (strcmp ((*p
)[0], filename
) == 0)
899 /* A to_xfer_partial helper function which reads XML files which were
900 compiled into GDB. The target may call this function from its own
901 to_xfer_partial handler, after converting object and annex to the
902 appropriate filename. */
905 xml_builtin_xfer_partial (const char *filename
,
906 gdb_byte
*readbuf
, const gdb_byte
*writebuf
,
907 ULONGEST offset
, LONGEST len
)
912 gdb_assert (readbuf
!= NULL
&& writebuf
== NULL
);
913 gdb_assert (filename
!= NULL
);
915 buf
= fetch_xml_builtin (filename
);
919 len_avail
= strlen (buf
);
920 if (offset
>= len_avail
)
923 if (len
> len_avail
- offset
)
924 len
= len_avail
- offset
;
925 memcpy (readbuf
, buf
+ offset
, len
);
931 show_debug_xml (struct ui_file
*file
, int from_tty
,
932 struct cmd_list_element
*c
, const char *value
)
934 fprintf_filtered (file
, _("XML debugging is %s.\n"), value
);
937 void _initialize_xml_support (void);
940 _initialize_xml_support (void)
942 add_setshow_boolean_cmd ("xml", class_maintenance
, &debug_xml
,
943 _("Set XML parser debugging."),
944 _("Show XML parser debugging."),
945 _("When set, debugging messages for XML parsers "
947 NULL
, show_debug_xml
,
948 &setdebuglist
, &showdebuglist
);