HttpListener:侦听具有显式主机名的端口(无顶级通配符)

时间:2019-04-11 14:55:40

标签: c# httplistener

假设我有一台具有IP的机器,例如183.41.22.22。我想听所有将发送到本地主机上此IP端口43的HTTP消息。实际上,我对发送到此端口的所有消息并不真正感兴趣,仅对发送到https://183.41.22.22:443/CustomerData/

的消息感兴趣

class HttpListener的文档说我应该添加一个前缀。他们举了一个例子:http://www.contoso.com:8080/customerData/

这是否意味着我应该添加前缀https://183.41.22.22:443/CustomerData/?还是应该使用https://localhost:443/CustomerData/

或者,由于我的计算机专用于此任务,因此我确定我的计算机上没有其他人可以接收到发送到端口443的任何消息。因此,根据同一文档,我还可以使用通配符: http://*:443

但是,文档警告:

  

不应使用顶级通配符绑定(http:// *:80 /和http://+:80)。顶级通配符绑定会创建应用程序安全漏洞。这适用于强通配符和弱通配符。使用明确的主机名或IP地址,而不要使用通配符。

什么是显式主机名?是CustomerData的一部分吗?

对于那些感兴趣的人,代码的简化部分(没有适当的可能性终止程序)

using (var httpListener = new HttpListener())
{
    httpListener.Prefixes.Add("https://*:443/");
    httpListener.Start();

    while (true)
    {
        var context = httpListener.GetContext();
        var httpRequest = context.Request();

        // fill the response
        string responseText = this.CreateResponseText(httpRequest);
        byte[] buf = Encoding.UTF8.GetBytes(responseText);
        context.Response.ContentLength64 = buf.Length;
        context.Response.OutputStream.Write(buf, 0, buf.Length);
    };

1 个答案:

答案 0 :(得分:1)

  

什么是显式主机名?这是CustomerData的一部分吗?

主机名通常称为“域”。参见The components of a URL。此外,警告还包含更多信息(为简洁起见,您省略了这些信息,但其中包含重要信息):

  如果您控制整个父域(而不是容易受攻击的*.mysub.com),则

子域通配符绑定(例如*.com)不存在此安全风险。有关更多信息,请参见rfc7230 section-5.4

RFC部分引用了HTTP Host header。这是HTTP / 1.1规范的一部分,是在人们回到网络早期running more than 1 website on a host时才引入的。主机(“机器”),用于简单地(通常)侦听端口80并提供客户端请求的页面。但是,当网络开始被更广泛地使用时,就需要在单个计算机上“托管”多个网站。您可能使用DNS的foo.combar.com都指向相同的IP,但是计算机不知道是发送foo.com主页还是发送bar.com主页。因此,引入了Host标头;然后,webbrowsers(更正确的是:http客户端)可以让服务器知道他们感兴趣的主机,并可以提供正确的页面。

请注意,域的每个部分(例如sub.domain.foo.co.uk可能都指向不同的主机(但同样,它们也都可能指向同一主机)。使用top-level domain通配符(例如*.com,或更糟糕的是:*)是潜在的风险,因为任何人都可以获取.com域({{ 1}})并将其指向您的服务器。如果您使用myevildomain.com,则*.company.com之外的任何人都无法控制子域。 为什么这是另外一个安全隐患,但要点是使用通配符company.com将使您的应用程序对任何以{{ 1}},而*.com将阻止您的应用程序响应(可能被欺骗的)客户端请求host