xxs 강의중에 instance 부분이 이해가 안가네요... 설명좀 가능할까요 아님 사이트라도..

"alert\x281\x29"instanceof{[Symbol.hasInstance]:eval};
Array.prototype[Symbol.hasInstance]=eval;"alert\x281\x29"instanceof[];

#웹해킹
작성자 정보
답변 1
avatar
as3617
워게임 고인물

지금 올려주신 xss페이로드 두 개는 아래와 같이 나눌 수 있습니다.

"alert\x281\x29" instanceof {[Symbol.hasInstance]:eval};

Array.prototype[Symbol.hasInstance]=eval; "alert\x281\x29" instanceof [];

위의 페이로드를 이해하기 위해선 우선 Symbol이 무엇인지 알아야합니다.
Symbol은 ecmascript 6에 도입된 자바스크립트의 새로운 원시타입으로 고유한 값을 가지며 객체의 속성의 식별자로 이용됩니다.
이 Symbol에는 다양한 속성이 존재하는데 그중 하나가 Symbol.hasInstance로 주어진 객체의 생성자가 함수의 인스턴스인지 확인하는데 사용하는 메소드입니다.

image
이 메소드는 instanceof와 함께 사용할 수 있는데
instanceof는 우측에 오는 값이 객체인지 확인하고 Symbol.hasInstance가 설정되있다면 해당 객체를 메소드로 호출하여 연산의 결과로 이용합니다.

그럼 만약 Array의 Symbol.hasInstance가 설정되있다면 위의 코드는 아래와 같이 나타낼 수 있습니다.

Array[Symbol.hasInstance](obj);

위의 두 페이로드는 이 원리를 이용한 페이로드입니다.
그럼 이제 페이로드를 하나씩 분석해보겠습니다.
우선적으로 분석해볼 페이로드는 "alert\x281\x29" instanceof {[Symbol.hasInstance]:eval}; 입니다.
"alert\x281\x29"는 Ecma Script에서 Hex Ascii String과 Unicode String, Octal String에 대하여 Auto Typecasting을 지원하기 때문에 "alert(1)"로 자동으로 변환되게 됩니다.
이제 중요한 부분은 {[Symbol.hasInstance]:eval}입니다. 간단하게 설명하자면 {} 빈 객체의 Symbol.hasInstance 속성의 값을 eval로 설정한 것인데
여기서 사용된 것은 Computed Property Name으로 객체의 key값을 표현식을 이용하여 나타내는 것 입니다.
image
위와 같이 객체의 Symbol.hasInstance가 설정되었으므로 instanceof는 아래와 같이 함수를 호출하게 되고

obj = {[Symbol.hasInstance]:eval}
obj[Symbol.hasInstance](alert(1))

obj[Symbol.hasInstance]는 eval함수이기때문에 최종적으론 alert함수가 실행됩니다.

다음 페이로드는 Array.prototype[Symbol.hasInstance]=eval; "alert\x281\x29" instanceof []; 입니다.
여기서 사용된 원리는 기본적으로 위의 페이로드와 같습니다. 다른 점이 있다면 이 페이로드는 javascript의 특징 중 하나인 prototype을 이용했다는 것입니다.
javascript는 prototype기반 언어로 모든 객체들은 속성과 메소드를 상속받기 위해 prototype 객체를 가지게 됩니다. 따라서 Array함수의 Prototype에 Symbol.hasInstance를 key로 값을 설정하면 모든 배열은 해당 속성을 상속받게 됩니다.
image

따라서 Array.prototype[Symbol.hasInstance]를 eval함수로 설정했으므로 []는 eval함수를 값으로 하는 Symbol.hasInstance라는 속성을 상속받게되고 "alert\x281\x29" instanceof [];는 최종적으로 eval('alert(1)')을 한 것과 같은 효과를 가지게 되어 alert가 실행되게됩니다.

2021.10.19. 21:15
질문에 대한 답을 알고 계신가요?
지식을 나누고 포인트를 획득해보세요.
답변하고 포인트 받기