URL 매개변수와 같은 사용자 제공 데이터는 항상 신뢰할 수 없고 오염된 것으로 간주해야 합니다. 공격자는 오염된 데이터에서 직접 LDAP 이름이나 검색 필터를 만들면 이름이나 필터 자체의 초기 의미를 변경하는 특수하게 조작된 값을 삽입할 수 있습니다. LDAP 인젝션 공격에 성공하면 디렉토리 서비스에서 중요한 정보를 읽거나 수정 또는 삭제할 수 있습니다.
LDAP 이름 내에서 특수 문자 ‘ ‘, ‘#’, ‘”’, ‘+’, ‘,’, ‘;’, ‘<’, ‘>’, ‘' 및 null은 RFC 4514에 따라 백슬래시 문자 ‘'와 이스케이프할 문자의 ASCII 코드에 해당하는 16진수 두 자리로 대체하는 등의 방법으로 치환해야 합니다. 마찬가지로 LDAP 검색 필터는 RFC 4515에 따라 다른 특수 문자 집합(‘*’, ‘(‘, ‘)’, ‘' 및 null을 포함하되 이에 국한되지 않음)을 치환해야 합니다.
규칙을 어긴 코드
from flask import request
import ldap
@app.route("/user")
def user():
dn = request.args['dn']
username = request.args['username']
search_filter = "(&(objectClass=*)(uid="+username+"))"
ldap_connection = ldap.initialize("ldap://127.0.0.1:389")
user = ldap_connection.search_s(dn, ldap.SCOPE_SUBTREE, search_filter) # 규칙을 어긴 코드
return user[0]
규칙을 준수한 해결책
from flask import request
import ldap
import ldap.filter
import ldap.dn
@app.route("/user")
def user():
dn = "dc=%s" % ldap.dn.escape_dn_chars(request.args['dc']) # 알려진 특수 문자 치환
username = ldap.filter.escape_filter_chars(request.args['username']) # 검색 필터 특수 문자 치환
search_filter = "(&(objectClass=*)(uid="+username+"))"
ldap_connection = ldap.initialize("ldap://127.0.0.1:389")
user = ldap_connection.search_s(dn, ldap.SCOPE_SUBTREE, search_filter) # 규칙을 준수한 코드
return user[0]
같이보면 좋은 자료
- OWASP Top 10 2021 Category A3 - 인젝션
- OWASP Top 10 2017 Category A1 - 인젝션
- RFC 4514 - LDAP: 고유 이름의 문자열 표현
- RFC 4515 - LDAP: 검색 필터의 문자열 표현
- MITRE, CWE-20 - 부적절한 입력 유효성 검사
-
MITRE, CWE-90 - LDAP 쿼리에 사용된 특수 요소의 부적절한 무력화(‘LDAP Injection’)
If you like SONARKUBE, don’t forget to give me a star.