
이 글은 아래 글을 번역한 후 이해를 바탕으로 작성한 글입니다.
https://book.hacktricks.xyz/pentesting-web/deserialization/nodejs-proto-prototype-pollution
NodeJS - __proto__ & prototype Pollution - HackTricks
function (container, depth0, helpers, partials, data) { return ((stack1 = (lookupProperty(helpers, "undefined") || (depth0 && lookupProperty(depth0, "undefined")) || container.hooks.helperMissing).call(depth0 != null ? depth0 : (container.nullContext || {}
book.hacktricks.xyz
1. Prototype?
C++, java 같은 객체지향언어에는 class라는 개념이있다.
하지만 javascript 에는 class 대신 prototype을 쓴다.
한마디로 자바스크립트에서 prototype == class 인셈
2. Prototype의 기본
1.
function person(fullName, age) {
this.age = age;
this.fullName = fullName;
}
var person1 = new person("test", 70);
* 함수.prototype 은 함수 본체만 사용 가능하고, 함수.__proto__ 는 함수에 의해 생성된 객체에 사용하는 것이다.
( 편의를 위해 함수 본체를 모체함수로 명명하고, 본체 함수로 부터 생성된 객체는 생성함수라고 하겠다.)
* 함수 본체는 바뀌지 않는다.
2.
* 모체함수.prototype.변수명을 써서 변수를 추가하면 이미 만들어진 객체에도 추가가 된다.
* 객체를 찍어보면 추가한 변수는 나오지 않지만(myFriend1 에 "gender"라는 변수가 x) 실제로 값을 찍어보면 값이 들어있다.(myFriend1.gender = male 이 나온다.)
3.
function person(fullName) {
this.fullName = fullName;
}
var person1 = new person("Satoshi");
person1.__proto__.__proto__.printHello = function(){console.log("Hello");}
person1.printHello()
var person2 = new person("test");
person2.printHello()
* 물론 다음과 같이 생성함수.__proto__.변수명 으로도 오염시킬 수 있다.
* 예시에선 왜 __proto__를 두번씩 썼는지 모르지만 실제로는 한번만 써도 됨
4.
function person(fullName) {
this.fullName = fullName;
}
var person1 = new person("Satoshi");
person.prototype.sayHello = function(){console.log("Hello");}
person.prototype.newConstant = true
person1.__proto__.sayHello = function(){console.log("Hello");}
person1.__proto__.newConstant = true
person1.__proto__["sayHello"] = function(){console.log("Hello");}
person1.__proto__["newConstant"] = true
person1.constructor.prototype.sayHello = function(){console.log("Hello");}
person1.constructor.prototype.newConstant = true
* 위에 코드는 전부 같은 말이다. 특정 단어가 필터링 된다고 생각할때 유동적으로 쓰면 된다.
5.
* 헷갈리면 안되는게 prototype 은 함수 뿐만이 아니다.
* 위와 같이 Object.protptype.변수명 을 정해놓으면 모든 객체가 변수명을 가지게 된다.
> 취약점 점검 사례
1. highcharts 취약한 버전에서의 prototype pollution
highcharts 9.0.0 이하의 버전애서 prototype pollution 취약점이 존재함
let obj = JSON.parse('{"__proto__" :{"polluted":"yes"}}');
Highcharts.merge({}, obj);
document.write('Polluted : ' + polluted);
- 출처 : https://security.snyk.io/vuln/SNYK-JS-HIGHCHARTS-1018906
1.1 점검 방법
해당 npm 모듈이 깔려 있는 홈페이지 개발자도구 console 에서 상단에 있는 poc를 입력
1.2 결과
홈페이지가 Polluted : yes 로 바뀜
해당 취약점은 server에서 나오는게 아닌 client 단에서 발생하는 취약점이라 DOS, XSS의 취약점이 존재 할 수 있음.
홈페이지에서 차트를 표시할 때 사용자입력을 받아 사용한다면 그 부분을 이용해서 RCE 등 더 영향력이 강한 취약점을 발생시킬 수 있음.
만약 사용자 입력을 받지 않는다면 취약 라이브러리 사용으로 잡는다.
출처:
- Prototype Pollution XSS POC (Vue.js, Google Analytics 등)
https://github.com/BlackFan/client-side-prototype-pollution
- Prototype Pollution 이해
https://www.neuralegion.com/blog/prototype-pollution/
- Prototype Pollution 이해 2
https://research.securitum.com/prototype-pollution-and-bypassing-client-side-html-sanitizers/
- 특정 템플릿 사용시 Prototype Pollution을 이용한 RCE (Handlebars, Pug)
https://blog.p6.is/AST-Injection/
- 실제 사례를 기반으로 설명
https://slides.com/securitymb/prototype-pollution-in-kibana/#/64
'WEB > 공부' 카테고리의 다른 글
Log4j 취약점( CVE-2021-44228 ) 자료 정리 (0) | 2021.12.18 |
---|---|
$(document).ready 사용 시 $ is not defined 에러 (0) | 2021.11.19 |
Electron으로 만든 앱에서 정보얻기 (0) | 2021.10.28 |
XSS 시 자주 써먹는 팁 과 구문들 (0) | 2021.10.14 |
Mermaid 툴을 이용한 DOS & XSS (0) | 2021.10.13 |