Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Welcome To Ask or Share your Answers For Others

Categories

0 votes
236 views
in Technique[技术] by (71.8m points)

.net - XPath injection mitigation

Are there any pre-existing methods in .NET to detect/prevent an xpath injection attack?

I can forsee 2 examples but there are likely many more.

e.g.

"/Some/XPath/" + UntrustedNodeName

If UntrustedNodeName is "DoesNotExist | /Some/Other/XPath" then this could be an attack.

"/Some/XPath[" + UntrustedFilter + "]"

If UntrustedFilter is "1 = 1" then this could also be an attack.

I make no assumption that I have covered all cases here!

I am guessing that the 2 situations need to be tested separately with different logic.

For other types of attacks there are encoding methods and parameterised classes to mitigate the risks. For XPath I can't find anything similar.

(Except - I did find this: http://www.tkachenko.com/blog/archives/000385.html but the installer didn't work)

See Question&Answers more detail:os

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome To Ask or Share your Answers For Others

1 Answer

0 votes
by (71.8m points)

As Michael Kay says, the right approach here is to use XPath variables, but this is a bit tricky using built-in .NET APIs. I'll provide an example below of a (very bare bones) class that allows you to define XPath variables. Once you have that, you can make use of it like this:

VariableContext context = 
               new VariableContext { { "hello", 4 }, { "goodbye", "adios" } };

// node is a System.Xml.XmlNode object
XmlNodeList result = 
               node.SelectNodes("/my/field[. = $hello or . = $goodbye]", context);

This same class should also work with XmlNode.SelectSingleNode(), XPathNavigator.Select(), XPathNavigator.SelectSingleNode(), XPathNavigator.Evaluate(), and the XPath methods in XElement.

This provides a safe way to incorporate user-provided data values into your XPath, but as with Tomalak's answer, it does not address the issue of how to allow your user to provide entire pieces of XPath. I don't think there is a way to determine whether a piece of XPath is objectively safe or not, so if you're worried about that being a security risk, then the only solution is to not do it.

Here is the class. If you want to have it handle namespaces and stuff like that, that would need to be added.

class VariableContext : XsltContext
{
    private Dictionary<string, object> m_values;

    public VariableContext()
    {
        m_values = new Dictionary<string, object>();
    }

    public void Add(string name, object value)
    {
        m_values[name] = value;
    }

    public override IXsltContextVariable ResolveVariable(string prefix, string name)
    {
        return new XPathVariable(m_values[name]);
    }

    public override int CompareDocument(string baseUri, string nextbaseUri)
    {
        throw new NotImplementedException();
    }

    public override bool PreserveWhitespace(XPathNavigator node)
    {
        throw new NotImplementedException();
    }

    public override IXsltContextFunction ResolveFunction(string prefix, string name, 
                                                         XPathResultType[] ArgTypes)
    {
        throw new NotImplementedException();
    }

    public override bool Whitespace
    {
        get { throw new NotImplementedException(); }
    }

    private class XPathVariable : IXsltContextVariable
    {
        private object m_value;

        internal XPathVariable(object value)
        {
            m_value = value;
        }

        public object Evaluate(XsltContext xsltContext)
        {
            return m_value;
        }

        public bool IsLocal
        {
            get { throw new NotImplementedException(); }
        }

        public bool IsParam
        {
            get { throw new NotImplementedException(); }
        }

        public XPathResultType VariableType
        {
            get { throw new NotImplementedException(); }
        }
    }

}

与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…
Welcome to OStack Knowledge Sharing Community for programmer and developer-Open, Learning and Share
Click Here to Ask a Question

...