Chapter 9 Attacking Data Stores(5)-Injecting into LDAP

LDAP注入

Posted by D on March 16, 2020

参考:The Web Application Hackers Handbook Chapter 9

轻型目录访问协议(LDAP-Lightweight Directory Access Protocol)用于通过网络访问目录服务。 目录是按层次结构组织的数据存储,可以包含任何类型的信息,但通常用于存储个人数据,例如姓名,电话号码,电子邮件地址和职务。 LDAP的常见示例是Windows域中使用的Active Directory,以及在各种情况下使用的OpenLDAP。 您很可能会遇到基于公司Intranet的Web应用程序中使用的LDAP,例如允许用户查看和修改有关员工信息的HR应用程序。

每个LDAP查询使用一个或多个搜索过滤器,这些过滤器确定查询返回的目录条目。 搜索过滤器可以使用各种逻辑运算符来表示复杂的搜索条件。 您可能会遇到的最常见的搜索过滤器如下:

  • 简单匹配条件 匹配单个属性的值。 例如,通过用户名搜索用户的应用程序功能可以使用以下过滤器:
    (username=daf)
    
  • 析取查询 指定多个条件,返回的条目必须满足其中任何一个条件。 例如,在几个目录属性中查找用户提供的搜索词的搜索功能可能会使用以下过滤器:
    (|(cn=searchterm)(sn=searchterm)(ou=searchterm))
    
  • 合并查询 指定多个条件,返回的条目必须满足所有条件。 例如,在LDAP中实现的登录机制可以使用以下过滤器:
    (&(username=daf)(password=secret)
    

    与其他形式的注入一样,如果用户提供的输入未经任何验证就插入LDAP搜索过滤器中,则攻击者可能会提供修改过滤器结构的精心设计的输入,从而检索数据或在其中执行操作。 未经授权的方式。

通常,由于以下因素,LDAP注入漏洞不如SQL注入漏洞容易利用:

  • 如果搜索过滤器使用逻辑运算符指定连接查询或连接查询,则此查询通常出现在插入用户提供的数据之前,因此无法修改。 因此,简单的匹配条件和联合查询不具有SQL注入所引起的or 1=1类型的攻击。
  • 在常用的LDAP实现中,要返回的目录属性作为与搜索过滤器不同的参数传递给LDAP API,通常在应用程序中进行硬编码。 因此,通常不可能操纵用户提供的输入来检索与查询意图不同的属性。
  • 应用程序很少返回信息错误消息,因此通常需要blind利用漏洞。

1.利用LDAP注入(Exploiting LDAP Injection)

尽管有上述限制,但在许多实际情况下,仍有可能利用LDAP注入漏洞从应用程序检索未经授权的数据或执行未经授权的操作。 通常如何完成此操作的细节在很大程度上取决于搜索过滤器的结构,用户输入的入口点以及后端LDAP服务本身的实现细节。

1.1 析取查询

考虑一个应用程序,该应用程序允许用户列出业务指定部门中的员工。 搜索结果仅限于用户有权查看的地理位置。 例如,如果用户被授权查看伦敦和雷丁的位置,并且他搜索“销售”部门,则该应用程序执行以下析取查询:

(|(department=London sales)(department=Reading sales))

在这里,应用程序构造一个析取查询,并在用户提供的输入之前添加不同的表达式以实施所需的访问控制。

在这种情况下,攻击者可以通过提交以下搜索词来颠覆查询,以返回所有位置的所有员工的详细信息:

)(department=*

*字符是LDAP中的通配符; 它匹配任何项目。 当此输入嵌入LDAP搜索过滤器时,将执行以下查询:

(|(department=London )(department=*)(department=Reading )(department=*))

由于这是一个析取查询,并且包含通配符(department=*),因此它在所有目录条目上都匹配。 它返回所有位置的所有员工的详细信息,从而颠覆了应用程序的访问控制。

1.2 联合查询

考虑一个类似的应用程序功能,该功能允许用户再次在其有权查看的地理区域内按名称搜索员工。

如果授权用户在伦敦位置内搜索,并且他搜索名称daf,则执行以下查询:

(&(givenName=daf)(department=London*))

在这里,用户的输入被插入到一个联合查询中,该查询的第二部分通过仅匹配伦敦一个部门中的项目来实施所需的访问控制。

在这种情况下,取决于后端LDAP服务的详细信息,两种不同的攻击可能会成功。 包括OpenLDAP在内的某些LDAP实现允许批处理多个搜索过滤器,并且这些过滤器是分开应用的。 (换句话说,将返回与任何批处理过滤器匹配的目录条目。)例如,攻击者可能提供以下输入:

*))(&(givenName=daf

当此输入嵌入原始搜索过滤器后,它将变为:

(&(givenName=*))(&(givenName=daf)(department=London*))

现在,它包含两个搜索过滤器,其中第一个包含一个通配符匹配条件。 从所有位置返回所有员工的详细信息,从而破坏了应用程序的访问控制。

NOTE 如果后端实现接受多个搜索过滤器,则注入第二个搜索过滤器的这种技术还可以有效地应对不使用任何逻辑运算符的简单匹配条件。

针对联合查询的第二种攻击类型利用了多少个LDAP实现处理NULL字节。 因为这些实现通常是用本机代码编写的,所以搜索过滤器中的NULL字节有效地终止了字符串,并且NULL之后的所有字符都将被忽略。 尽管LDAP本身不支持注释(可以在SQL中使用--序列),但是可以有效利用NULL字节的这种处理来“注释”查询的其余部分。

在前面的示例中,攻击者可以提供以下输入:

*))%00

应用程序服务器将%00序列编码为文字NULL字节,因此,当将输入嵌入搜索过滤器时,它变为:

(&(givenName=*))[NULL])(department=London*))

因为此过滤器在NULL字节处被截断,所以就LDAP而言,它仅包含一个通配符条件,因此,伦敦地区以外部门的所有员工的详细信息也将返回。

2.查找LDAP注入缺陷(Finding LDAP Injection Flaws)

向LDAP操作提供无效的输入通常不会导致信息错误消息。 通常,可用于诊断漏洞的证据包括搜索功能返回的结果以及错误的发生,例如HTTP 500状态代码。 但是,您可以使用以下步骤来确定LDAP注入流的可靠性。

HACK STEPS

  • 1.尝试仅输入*字符作为搜索词。 该字符在LDAP中充当通配符,但在SQL中不起作用。 如果返回大量结果,则表明您正在处理LDAP查询。
  • 2.尝试输入多个右括号:
    )))))))))))
    

    此输入将关闭包含您的输入的所有方括号,以及用于封装主搜索过滤器本身的方括号。 这导致不匹配的右括号,从而使查询语法无效。 如果导致错误,则该应用程序可能容易受到LDAP注入的攻击。 (请注意,此输入还可能破坏许多其他类型的应用程序逻辑,因此,只有在您已经确定要处理LDAP查询时,这才可以提供有力的指示。)

  • 3.尝试输入旨在干扰不同类型查询的各种表达式,并查看它们是否使您能够影响返回的结果。 cn属性受所有LDAP实现支持,如果您不知道所查询目录的任何详细信息,则该属性很有用。 例如:
    )(cn=*
    *))(|(cn=*
    *))%00
    

3.防止LDAP注入(Preventing LDAP Injection)

如果有必要将用户提供的输入插入LDAP查询中,则应仅对可以进行严格输入验证的简单数据项执行此操作。 应该对照可接受的字符白名单检查用户输入,理想情况下,白名单应仅包含字母数字字符。 应该阻止可能用于干扰LDAP查询的字符,包括 ( ) ; , * | =空字节 。 任何与白名单不匹配的输入都应拒绝,而不是清除。

Summary

我们已经研究了一系列漏洞,这些漏洞使您可以注入Web应用程序数据存储中。 这些漏洞可能使您可以读取或修改敏感的应用程序数据,执行其他未经授权的操作或破坏应用程序逻辑以实现目标。

尽管这些攻击很严重,但它们只是涉及注入已解释上下文的更广泛攻击的一部分。 此类别中的其他攻击可能使您可以在服务器的操作系统上执行命令,检索任意文件并干扰其他后端组件。 下一章将研究这些攻击和其他攻击。 它研究了Web应用程序中的漏洞如何导致损害支持该应用程序的更广泛基础架构的关键部分。

Chapter 9 Attacking Data Stores(4)-Injecting into XPath
Chapter 10 Attacking Back-End Components(1)-Injecting OS Commands(1)

: