LINQ to XML是否忽略DTD中的包含?

3

我正在使用MathML DTD和System.Xml.Linq解析MathML。虽然普通的MathML可以被正确识别,但是DTD中的MMLEXTRA被忽略了,导致出现错误。这是我使用的代码:

  if (!string.IsNullOrWhiteSpace(mathML))
  {
    try
    {
      const string preamble =
          "<!DOCTYPE mml:math PUBLIC \"-//W3C//DTD MathML 2.0//EN\"\n" +
           "\"http://www.w3.org/Math/DTD/mathml2/mathml2.dtd\" [\n" +
           "<!ENTITY % MATHML.prefixed \"INCLUDE\">\n" +
           "<!ENTITY % MATHML.prefix \"mml\"> \n" +
         "]>";
      var parsed = Parser.Parse(preamble + Environment.NewLine + mathML);
      textEditor.Text = printed;
      lblStatus.Caption = "MathML successfully translated.";
    } 
    catch (Exception e)
    {
      lblStatus.Caption = "Cannot translate text. " + e.Message;
    }
  }

解析器只需执行XDocument.Load()。需要任何帮助!

@Kirk Parser只是一个基本上执行XDocument.Load的组件。假设这个调用会直接解析所有的MathML引用,但实际上并不是这样。 - Dmitri Nesteruk
1个回答

6

这里

DTD中的实体本质上不安全。可能会有恶意的XML文档包含DTD,导致解析器使用所有内存和CPU时间,从而造成拒绝服务攻击。因此,在LINQ to XML中,默认情况下关闭DTD处理。您不应该接受来自不受信任的源的DTD。

但是,要启用它,您应该使用XDocumentType类

一些可能的解决方案:

XmlReaderSettings settings = new XmlReaderSettings();
settings.ProhibitDtd = false;

XmlReader reader = XmlReader.Create(Server.MapPath("filename"), settings);

XDocument doc = XDocument.Load(reader);

也许还有这样一个选择:
 XDocument xDocument = new XDocument(new XDocumentType("Books",null,"Books.dtd", null),new XElement("Book"));

所有信息来自同一来源

这个链接提供了相关的IT技术信息,可以作为参考。


太棒了!这完全满足我的需求。哎呀!花费了50个声望点,但我的产品是安全的 :) 谢谢! - Dmitri Nesteruk
引用的答案与当前的 MS 文档相矛盾,该文档指出:“当文档包含在 DTD 中定义的实体引用时,在创建 XML 树时会展开这些引用”:https://learn.microsoft.com/en-us/dotnet/api/system.xml.linq.xdocumenttype?redirectedfrom=MSDN&view=netcore-3.1 也许在这 9 年中有一些设计变更决策。 - interDist

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接