> php教程 > php手册 > PHP에서 '==' 연산자의 보안 문제

PHP에서 '==' 연산자의 보안 문제

大家讲道理
풀어 주다: 2016-11-12 10:28:27
원래의
1168명이 탐색했습니다.
머리말

PHP는 일반적인 오픈소스 스크립트 언어로 C, Java, Perl 등 우수한 언어의 구문을 혼합한 것입니다. 또한 개발자가 사용할 수 있는 수많은 함수 라이브러리도 제공합니다. 그러나 부적절하게 사용하면 PHP는 응용 프로그램에 매우 큰 보안 위험을 가져올 수도 있습니다.

이 기사에서는 PHP 애플리케이션에서 자주 발생하는 몇 가지 문제에 대해 심층 분석을 수행합니다. 특히 "=="(비교 연산자)를 사용하여 문자열 비교를 수행할 때 일부 보안 문제가 발생할 수 있습니다. . 최근 이 주제에 대해 많은 기사가 논의되었지만, 나는 이 문제를 어떻게 활용하여 대상을 침투하고 공격할 수 있는지를 "블랙박스 테스트"의 관점에서 논의하기로 결정했습니다. 먼저, 이 문제의 근본 원인을 분석하여 작동 메커니즘을 더 깊이 이해하고 이 보안 문제를 최대한 피할 수 있도록 하겠습니다.

문제 설명

2011년 PHP 공식 버그 추적 시스템에서는 문자열과 숫자를 비교할 때 프로그램에서 매우 이상한 현상이 발생한다는 사실을 발견했습니다. 보안 관점에서 볼 때 이 문제는 실제로 보안 문제가 아닙니다. 예를 들어 다음과 같은 코드를 볼 수 있습니다.

PHP에서 == 연산자의 보안 문제

실제로 "==" 같은 비교 연산자를 사용해 연산을 하면 이런 상황이 나옵니다. 위 예제의 문제는 PHP에서 제공하는 '형변환'이라는 함수이므로 취약점으로 볼 수 없습니다. 본질적으로 특정 비교 연산자(예: ==, !=, )를 사용하여 작업할 때 PHP는 먼저 비교에 참여하는 데이터 유형을 결정하려고 시도합니다. 그러나 이러한 유형 변환 메커니즘으로 인해 계산 결과가 예상 결과와 크게 다를 수 있으며 매우 심각한 보안 문제도 발생할 수 있습니다. 보안 연구 전문가들은 이 문제에 대한 전체 공개 보고서에서 다음과 같이 썼습니다. 이러한 유형 변환 메커니즘은 권한 상승으로 이어질 수 있으며 심지어 프로그램의 비밀번호 확인 프로세스를 안전하지 않게 만들 수도 있습니다.

Gynvael은 이 주제에 대한 고전적인 기사를 썼습니다. PHP 등호 연산자 "=="가 다루는 데이터 유형은 매우 광범위하며 비교적 완전한 비교 참조 목록을 제공합니다.

PHP에서 == 연산자의 보안 문제

보시다시피, "=="를 사용하여 이러한 숫자 문자열을 비교할 때, 이때 비교에 포함되는 것은 문자열에 있는 숫자의 실제 크기는 보안 관점에서 매우 흥미로운 문제입니다. 이 경우 과학적 표기법을 사용하여 숫자를 표현하고 이를 문자열에 넣으면 PHP는 자동으로 이를 숫자 유형으로 처리합니다. 이러한 출력 유형을 얻는 이유는 PHP가 처리를 위해 해시 알고리즘(보통 16진수 값으로 표시)을 사용하기 때문입니다. 예를 들어 숫자가 0이면 PHP는 느슨한 비교 중에 해당 유형을 자동으로 변환하지만 해당 값은 항상 0입니다. 특정 해싱 알고리즘의 경우 비밀번호를 교체할 수 있습니다. 예를 들어, 비밀번호 해시가 과학적 표기법을 사용하여 숫자로 변환되면 다른 비밀번호 해시와 일치할 가능성이 높습니다. 이런 방식으로 완전히 다른 비밀번호라도 시스템 확인을 통과할 수 있습니다. 하지만 흥미로운 점은 과학적 표기법으로 표현된 특정 숫자를 비교할 때 놀라운 결과가 나올 수 있다는 것입니다.

PHP에서 == 연산자의 보안 문제

이 문제를 "블랙박스 테스트"의 관점에서 생각해 보세요

정적 분석의 관점에서 보면 이러한 보안 문제는 다소 평범해 보입니다. 하지만 블랙박스 관점에서 이러한 문제를 살펴보면 애플리케이션의 모든 사용자 계정에 대해 애플리케이션이 가장 널리 사용되는 해싱 알고리즘(예: SHA1 및 MD5)을 사용하여 비밀번호를 처리하는 경우 어떤 통찰력을 얻을 수 있습니까? 비밀번호 해시를 확인할 때 PHP의 느슨한 비교로 인해 이때 보안 문제가 발생할 수 있습니다. 이제 일반적인 침투 테스트를 고려해 볼 수 있습니다. 일반 계정을 만들고 비슷한 해시 값을 가진 비밀번호 중 하나에 비밀번호를 설정한 다음 다른 비밀번호를 사용하여 로그인할 수 있습니다. 분명히 시스템의 보안은 사용하는 해싱 알고리즘에 전적으로 달려 있습니다. 따라서 해싱 알고리즘에 "Salt" 값을 사용하지 않는다고 가정하면 비밀번호에 대해 최소한 두 가지 서로 다른 해싱 알고리즘을 사용해야 합니다.

이제 이러한 비밀번호 조합을 연구하기 전에 한 가지, 즉 비밀번호 요구 사항도 고려해야 합니다. 이러한 비밀번호와 해시 알고리즘을 분석하기 전에 먼저 설정한 초기 비밀번호가 비밀번호 복잡성 요구 사항을 충족하는지 확인해야 합니다. 그렇지 않으면 분석과 연구가 의미가 없게 됩니다. 따라서 비밀번호는 8자 이상, 대문자와 소문자, 숫자, 특수문자가 하나 이상 포함되어 있는지 확인해야 합니다. 자세한 내용은 다음과 같습니다.
import random
import hashlib
import re
import string
import sys
prof = re.compile("^0+ed*$") # you can also consider: re.compile("^d*e0+$")
prefix = string.lower(sys.argv[1])+'!'+string.upper(sys.argv[1])+"%s"
num=0
while True:
    num+=1
    b = hashlib.sha256(prefix % num).hexdigest()
    if (b[0]=='0' and prof.match(b)):
        print(prefix+str(num),b)
로그인 후 복사
이를 위해 특별히 Python 스크립트를 작성했습니다. , 비록 이 스크립트의 성능을 최적화하기 위해 많은 노력을 기울이지는 않았지만 PyPy 컴파일러의 도움으로 잘 작성된 이 스크립트는 내 AMD FX8350의 사용 가능한 모든 CPU 코어에서 안정적으로 실행됩니다. 또한 hashlib 라이브러리의 해시 함수도 사용했으며 Python GIL의 프로세스 동기화 문제가 발생하지 않도록 비밀번호 데이터를 처리하는 독립적인 프로세스도 생성했습니다. 뿐만 아니라 위의 코드에서 볼 수 있듯이 각 비밀번호에 대해 서로 다른 접두어를 생성하는 매우 정교한 기술도 사용했습니다.
분석 결과

1시간여의 분석 끝에 비밀번호 4개에 대한 SHA1 값을 알아냈습니다. 놀랍게도 4개 비밀번호의 MD5 값을 얻는 데 시간이 더 적게 걸렸습니다.

비밀번호 계산 결과는 아래와 같이 매우 유사합니다.

PHP에서 == 연산자의 보안 문제

비교를 위해 두 개의 비밀번호를 무작위로 선택할 수 있습니다. 결과는 다음과 같습니다.

PHP에서 == 연산자의 보안 문제

위와 같은 계산 결과를 얻을 수 없다면 운이 좋다고 생각해야 합니다. 사용자 이름과 비밀번호를 함께 묶은 다음 "솔트" 값이 포함된 해시 알고리즘을 사용하여 계산해 볼 수 있습니다. 이를 달성하려면 코드의 작은 부분만 수정하면 됩니다. 수정된 스크립트를 얻으려면 "여기"를 클릭하세요.
해결책

PHP에서 해결 방법을 제공합니다. 해시 값을 비교하려면 Password_verify() 또는 hash_equals() 함수를 사용해야 합니다. 데이터를 엄격하게 비교하고 다른 간섭 요인을 제거합니다. 그러나 hash_equals() 함수는 문자열 비교에도 사용될 수 있습니다.
분석 결론

분석 단계가 실행하기에는 다소 복잡하지만 블랙박스 테스트의 관점에서 설명하는 방법은 다음과 같은 유용한 정보를 제공할 수 있습니다. 정보. 애플리케이션의 비밀번호가 이러한 확인 메커니즘을 사용하는 경우 이로 인해 발생하는 보안 문제는 PHP 데이터 유형 변환 자체의 문제를 넘어섭니다.
문제는 그 이상입니다

이 문제가 우리에게 미치는 영향은 그 이상입니다. 공격자는 이러한 암호를 사전 파일에 추가한 다음 응용 프로그램의 모든 사용자에 대해 무차별 대입 공격을 수행할 수 있습니다. 또한 애플리케이션의 비밀번호 복구 메커니즘에 안전하지 않은 요소가 있는 경우 공격자는 공격이 성공할 때까지 대상 계정에 대해 무제한 공격을 수행할 수 있습니다.
원천:php.cn
본 웹사이트의 성명
본 글의 내용은 네티즌들의 자발적인 기여로 작성되었으며, 저작권은 원저작자에게 있습니다. 본 사이트는 이에 상응하는 법적 책임을 지지 않습니다. 표절이나 침해가 의심되는 콘텐츠를 발견한 경우 admin@php.cn으로 문의하세요.
최신 이슈
인기 추천
인기 튜토리얼
더>
최신 다운로드
더>
웹 효과
웹사이트 소스 코드
웹사이트 자료
프론트엔드 템플릿