12/30/2019

Run other application on Burp suite(Burp suite에서 다른 앱 실행하기)

오늘은 Burp suite에서 외부 앱을 실행하는 방법에 대해 이야기하려고 합니다. 사실 비슷한 내용(ZAP)으로 예전에 글을 쓴적이 있었는데요, 드디어 관련 확장 기능이 업데이트되어서 Burp suite에서도 동일한 짓을 할 수 있습니다.
Today I'am going to talk about how to run an external app on the Burp suite. In fact, I've written something similar in the past, and it's finally updated to do the same thing with the Burp suite.

Run other application on ZAP
(https://www.hahwul.com/2019/07/easy-security-testing-with-applications-bridge-in-zap.html)


드디어! Burp도 된다!

if you use MacOS?

MacOS에선 리눅스 xterm과 같이 기본 터미널에 명령행을 전달할 수 없습니다. (파일 로드만 가능함)
그래서 외부 코드를 실행해줄 수 있는 파일을 만들고 이를 호출하여 실행이 필요합니다.
MacOS is unable to forward command lines to the primary terminal, such as Linux xterm. (File load only)
So you need to create a file that can run an external code and call it to run.

echo '
on run argv
  if length of argv is equal to 0
    set command to ""
  else
    set command to item 1 of argv
  end if
  if length of argv is greater than 1
    set profile to item 2 of argv
    runWithProfile(command, profile)
  else
    runSimple(command)
  end if
end run
on runSimple(command)
  tell application "Terminal"
    activate
    set newTab to do script(command)
  end tell
  return newTab
end runSimple
on runWithProfile(command, profile)
  set newTab to runSimple(command)
  tell application "Terminal" to set current settings of newTab to (first settings set whose name is profile)
end runWithProfile
' | osascript - "$@" > /dev/null

실행이 필요하기 때문에 권한을 부여해줍니다.
Grants permission because it requires execution.

$ chmod 755 thisscript.sh

Install Custom send to

BApp 스토어에 보면 Custom Send To 라는 앱이 있습니다. Pro 버전 전용도 아니니 CE 유저분들도 설치해서 사용할 수 있습니다.
If you look at the BApp store, there is an app called Custom Send To. It's not only for Pro version, so CE users can install it and use it.



Setting application information

설치를 완료하면 탭이 생기게 됩니다. 해당 탭에서 어떤 명령을 실행할지, 어떤 터미널에서 실행할지 지정해줄 수 있습니다.
When you complete the installation, you will have tabs. You can specify which commands to run on that tab and which terminals to run.


리눅스의 경우 기본 터미널인 xterm을 유지해도 되지만, MacOS의 경우 문제가 있어서 아까 만들어둔 스크립트로 경로를 변경해줍니다. 이 때 %C는 위에 지정한 명령이 들어가는 자리입니다.
For Linux, you can keep the default terminal xterm, but for MacOS, there is a problem, so you change the path to the script you created. At this point, %C is the place where the command specified above is placed.


< Entires >
%S : Seleted data(string)
%F : Seleted data(save file)

< Miscellaneous >
%C : Command


Send to Other Application

Request tab => Copy All data => Context menu(right click) => Send to your app





여기서 재미있는점은 Send to 로 요청 시 request 탭에서 선택한 부분이 파일로 저장되어 파일 인자값으로 사용됩니다. XSpear의 경우 --raw 옵션을 통해 파일을 읽을 수 있어서 아까 설정에서 그렇게 지정해줬습니다.
The interesting point here is that when you request Send to , the selected portion of the request tab is saved to a file and used as a file argument. For XSpear, you can read the file through the --raw option, so that's what the upper this post.



Conclusion

예전 ZAP글에도 써놨듯이, 외부 툴 연동은 정말 유용한 기능입니다. 꼭 세팅해두고 쓰시길 바래요!
Share: | Coffee Me:

12/29/2019

XSpear 1.3 version released!

Hi hackers! I worked hard to finish the XSpear 1.3 version with this year's last release. and, 1.3 version released!



Key features included in this update include:

1)
There was an enhancement to the scanning function. Scanning for Path and scanning for JS internal XSS have been added. (In fact, everyone can easily develop and give PR because all scanning functions operate as modules.)

2) Config file usage is supported.
It was inconvenient to insert blind-xs url (xsshunter, etc..), but it can be automatically included via the setup file.

3) Reforming the Log-UI of the CLI
The verbose phase has been increased. (and add progress-bar!)

In addition, I been adding features since version 1.2. Please read README!

https://github.com/hahwul/XSpear


How to update?

gem update XSpear

Conclusion

and, Happy new year!


Share: | Coffee Me:

12/26/2019

Test with GoBuster! (Powerful bruteforcing tool of golang)

directory 스캔 도구의 dirbuster가 아주 강세였습니다만, 올해부터 gobuster가 더 많이쓰이는 것 같은 느낌이 듭니다. 당연히 스캔 도구는 이젠 golang이 압도적일겁니다. (고루틴과 고채널의 힘이란..)
The directory scan tool's dirbuster has been very strong, but it feels like gobuster going to be more popular this year. Of course, now the scanners are going to be dominated by golang.

오늘은 golang으로 만들어진 gobuster에 대한 이야기를 하려고 합니다.
Today I'm going to write about a gobuster made of golang.



Install gobuster

go get을 이용하여 설치해줍시다. 덤으로 alias 설정까지 해주면 더더욱 베스트.

$ go get github.com/OJ/gobuster
# check gobuster path and copy
$ ls ~/go/bin/gobuster
/Users/hahwul/go/bin/gobuster

# edit your terminal rc (zsh, bash, etc..)
$ vim ~/.zshrc

alias gobuster='/Users/hahwul/go/bin/gobuster'

# reload rc file
$ source ~/.zshrc

run gobuster

$ gobuster
Usage:
  gobuster [command]

Available Commands:
  dir         Uses directory/file brutceforcing mode
  dns         Uses DNS subdomain bruteforcing mode
  help        Help about any command
  vhost       Uses VHOST bruteforcing mode

Flags:
      --delay duration    Time each thread waits between requests (e.g. 1500ms)
  -h, --help              help for gobuster
  -z, --noprogress        Don't display progress
  -o, --output string     Output file to write results to (defaults to stdout)
  -q, --quiet             Don't print the banner and other noise
  -t, --threads int       Number of concurrent threads (default 10)
  -v, --verbose           Verbose output (errors)
  -w, --wordlist string   Path to the wordlist

Use "gobuster [command] --help" for more information about a command.


gobuster scanning mode?

gobuster는 총 3가지의 모드를 지원합니다. dir dns vhost 이며 각각 항목들에 대해 bruteforcing이 가능합니다.
The gobuster supports a total of three modes: It is ‘dir’, ‘dns’ and ‘vhost’ and each item can be bruteforcing.

dir         Uses directory/file brutceforcing mode
dns         Uses DNS subdomain bruteforcing mode
vhost       Uses VHOST bruteforcing mode

dir은 url(-u) 와 wordlist(-w)가 필수 파라미터입니다.
The dir url wordlist and (-u) (-w) required parameters.

dns는 domain(-d) 와 wordlist(-w)가 필수 파라미터입니다.
The dns domain wordlist and (-d) (-w) required parameters.

vhost는 url(-u) 와 wordlist(-w)가 필수 파라미터입니다.
The vhost url wordlist and (-u) (-w) required parameters.

Finding directory and file using gobuster

$ gobuster dir -u https://www.hahwul.com -w Discovery/Web-Content/common.txt
===============================================================
Gobuster v3.0.1
by OJ Reeves (@TheColonial) & Christian Mehlmauer (@_FireFart_)
===============================================================
[+] Url:            https://www.hahwul.com
[+] Threads:        10
[+] Wordlist:       Discovery/Web-Content/common.txt
[+] Status codes:   200,204,301,302,307,401,403
[+] User Agent:     gobuster/3.0.1
[+] Timeout:        10s
===============================================================
2019/12/26 01:59:03 Starting gobuster
===============================================================
/1000 (Status: 200)
/1001 (Status: 200)
/1990 (Status: 200)
/1994 (Status: 200)
/1992 (Status: 200)
.......
snip...

Finding Subdomain using gobuster

$ gobuster dns -d hahwul.com -w ./Discovery/DNS/subdomains-top1million-5000.txt
===============================================================
Gobuster v3.0.1
by OJ Reeves (@TheColonial) & Christian Mehlmauer (@_FireFart_)
===============================================================
[+] Domain:     hahwul.com
[+] Threads:    10
[+] Timeout:    1s
[+] Wordlist:   ./Discovery/DNS/subdomains-top1million-5000.txt
===============================================================
2019/12/26 01:56:35 Starting gobuster
===============================================================
Found: localhost.hahwul.com
Found: www.hahwul.com
Found: test.hahwul.com
Found: phoenix.hahwul.com
Found: WWW.hahwul.com
===============================================================
2019/12/26 01:57:08 Finished
===============================================================

Using Pipeline

-z(progress 출력하지 않음) -q(배너를 출력하지 않음) -o(결과 파일저장) 를 이용하면 충분히 pipeline에도 사용할 수 있습니다.
-z(no progress output) -q(no banner output) -o(save result file) is sufficient for pipeline.

$ gobuster dns -d hahwul.com -w ./Discovery/DNS/subdomains-top1million-5000.txt -z -q -o out.txt

$ cat out.txt
Found: www.hahwul.com
Found: localhost.hahwul.com
Found: test.hahwul.com
Found: phoenix.hahwul.com
Found: WWW.hahwul.com

이전에도 Amass와 Subjack을 이용한 Takeover 체크에 대한 을 썼었는데, 참고해보면 좋은 아이디어가 많이 나올 것 같아요.
I wrote about the check the subdomain takeover using Amass and SubJack. You see this, have any idea of testing.

Wordlist?

I used SecList!
https://github.com/danielmiessler/SecLists
Share: | Coffee Me:

12/25/2019

terminal에서의 golang 개발을 위한 vim-go 세팅하기

TL;DR

One-line script
cd ~/.vim ; mkdir autoload ; mkdir bundle ;cd autoload ; curl -LSso pathogen.vim https://tpo.pe/pathogen.vim ; cd ~/.vim/bundle ; git clone https://github.com/fatih/vim-go.git ; echo "execute pathogen#infect()
filetype plugin indent on" >> ~/.vimrc; git clone https://github.com/vim-airline/vim-airline.git ~/.vim/bundle/vim-airline ; git clone https://github.com/scrooloose/nerdtree.git ~/.vim/bundle/nerdtree
# if you use mac?
brew install mercurial

# if you use linux?
apt install mercurial

Finally
$ vim
:GoInstallBinaries


What is vim-go?

vim은 제가 생각하기에 최고의 콘솔 에디터가 아닌가 싶습니다. vim은 플러그인들을 통해 여러가지 언어에 맞는 기능들을 지원하는데, go의 경우도 예외는 없습니다. vim-go는 golang을 위한 vim 플러그인입니다.

Install pathogen

우선 작업에 필요한 디렉토리를 만들어준 후 pathogen을 설치해줍니다.

$ cd ~/.vim
$ mkdir autoload ; mkdir bundle ;cd autoload
$ curl -LSso pathogen.vim https://tpo.pe/pathogen.vim

pathogen을 활성화 하기 위해선 vimrc에 execute가 추가되어야 합니다.

# ~/.vimrc

set nu
syn on
set backspace=indent,eol,start
set encoding=utf-8

# 아래 2줄 추가해주세요
execute pathogen#infect()
filetype plugin indent on

Install vim-go

그 다음 bundle 디렉토리로 이동 후 vim-go를 clone 해주세요.

$ cd ~/.vim/bundle
$ git clone https://github.com/fatih/vim-go.git

이후 vim에서 GoInstallBinaries로 설치할껀데, 시스템에 mercurial이 없다면 별도로 설치해주셔야 합니다.

# MacOS
$ brew install mercurial

# Linux (debian base)
$ apt-get install mercurial

vim으로 진입해서 :GoInstallBinaries 타이핑합시다.


막 열심히 설치합니다.

그럼 위와 같이 vim-go에 필요한 플러그인들을 싹 설치해줍니다. 설치 이후에 .go 등 golang 관련 확장자로 파일을 만들면, 기본적인 세팅은 구성해줍니다.

$ vim 1.go
  1 package main
  2
  3 import "fmt"
  4
  5 func main() {
  6         fmt.Println("vim-go")
  7 }

이제부터 아래와 같은 명령들로 간단하게 작업을 수행할 수 있습니다.

:GoRun # 코드 실행
:GoBuild or :make # 코드 빌드
:GoImport {package_name} # 패키지 임포트 
:GoDef # 심볼 정의 찾기
:GoPlay # GoPlay 코드 생성

하나 예를들어보면..



vim-go: snippet uploaded: http://play.golang.org/p/VLAx5JyCLGJ

바로 go play에서 코드를 확인할 수 있습니다. 간단한 코드스니펫 공유엔 정말 좋은 기능같아요!


vim-go Commands

위에 서술한 기능 이외에도 정말 많은 기능이 내장되어 있습니다. 아래 링크를 참고해주세요.
https://raw.githubusercontent.com/fatih/vim-go/master/doc/vim-go.txt

Conclusion

vim-ruby를 잠깐 쓰다가 결국 RubyMine으로 싹 갈아탔었는데, go의 경우는 vim-go도 상당히 매력적인 것 같습니다. 아무래도 백엔드에서 많이 쓰이는 언어다보니, GoLand 같은걸 쓰는것도 좋겠지만, Cli에서 직접 코딩하는게 더 좋을수도 있습니다.

vim-airline 이나 nerdtree 등의 플러그인은 정말 쓸만하니 vim 세팅 통해서 해주시면 더더욱 좋은 코딩 환경이 될거라 생각합니다.

vim 세팅 관련
https://agvim.com/2017/09/05/vim-plugins-100/
https://www.hahwul.com/2018/02/coding-vim-plugin-language-plugin-ctrlp.html
Share: | Coffee Me:

12/23/2019

Burp Beautifier - Beautifying JSON/JS/HTML/XML In Burp Suite

오늘은 빠르게 Burp Extension 하나 소개할까 합니다.
Today, I will introduce a Burp Extension.

Burp Beautifier 라는 확장 기능인데 Burp 내부에 Beautifier가 생깁니다. 보통은 온라인에 만들어진 JS Beautifier 나 JSON Beautifier를 사용하는데, 이 확장 기능을 설치하면 Request/Response Tab 내부와 별도 탭에서 JS , JSON, HTML, XML 포맷에 대해 예쁘게 볼 수 있습니다.
It's an extension called Buff Beautifier and it creates a tab for beautifying code within the burp suite. Usually, Some use JS Beautifier or JSON Beautifier, which is created online, and when we install this extension, we can look at the JS , JSON, HTML and XML formats in the Request/Response Tab and in separate tabs.

Tab for Beautifier

Request and Response Tab

최근에 신규 기능으로 올라온걸 보고 좀 의아했었는데 (ZAP에선 원래 쓰던 기능이라 혼동이 있었네요) 아래 깃과 원본 깃을 보시면 아시겠지만.. 정말 최근 기능입니다.
https://github.com/portswigger/burp-beautifier
https://github.com/Ovi3/BurpBeautifier

Install

현재 BApp Store 올라와 있어서 Jython 설치 후 바로 install 가능합니다. 직접 코드에서 설치하는 경우에도 .py 파일 넣어주면 끝납니다.
You can install it right after installing Jython because you are currently up in the BApp Store. If you install it from git cloned code just insert the .py file to finish it.


Share: | Coffee Me:

12/21/2019

맥OS의 기본 VNC Client 사용하기

메모용으로 작성합니다..

집에 있는 테스트용 서버에 VNC 사용해야할 일이 있어 설치&세팅하고 맥으로 붙으려고 찾아보다 보니 MacOS에는 기본적으로 VNC Client가 깔려있다고 하네요. 별도 앱으로 있는건 아니고 vnc:// 프로토콜을 통해 바로 접근할 수 있습니다. 만약 VNC Sever의 IP가 192.168.0.11 Port가 5901 이라고 가정했을 때 아래와 같습니다.

vnc://192.168.0.11:5901


웹 브라우저로 붙여보면, 바로 접근 요청을 수행합니다. 간단하게 접근할 수 있으니 북마크에 등록해둡시다 :)

별다른 기능은 없지만, 사용하는데 있어 불편함은 없습니다.

Share: | Coffee Me:

Update golang 1.10 to 1.13 with update-golang(subfinder install error fix)

SubFinder 설치 중 undefined: os.UserHomeDir , undefined: strings.ReplaceAll 에러가 발생해서 해결 방법 정리해둡니다. 아마.. 현재 일부 피씨에서 설치 시 위와 같은 에러가 발생할텐데요, 원인은 golang 의 버전 문제입니다.

subfinder가 최근에 go 1.13 기준으로 문법이 변경됬는데, 하위 버전에선 메소드가 달라서 발생한 에러입니다. 저장소의 golang 버전이 1.13 이상일 경우 해당없겠지만, 하위버전인 경우 문제가 아래와 같은 에러가 발생합니다.

hahwul@salamander:~/lab/salamander/salamander$ go get -v github.com/projectdiscovery/subfinder/cmd/subfinder
github.com/projectdiscovery/subfinder/pkg/runner
# github.com/projectdiscovery/subfinder/pkg/runner
../../../go/src/github.com/projectdiscovery/subfinder/pkg/runner/config.go:39:20: undefined: os.UserHomeDir
../../../go/src/github.com/projectdiscovery/subfinder/pkg/runner/enumerate.go:52:18: undefined: strings.ReplaceAll


Update golang 1.10 to 1.13 with update-golang

원인이 버전인만큼, golang 버전 업그레이드로 해결이 가능하고, 저장소에서 지원하지 않는 경우는 아래 update-golang을 이용해서 간단하게 업데이트할 수 있습니다.

git clone https://github.com/udhos/update-golang
cd update-golang
sudo ./update-golang.sh

제가 사용하는 코드 일부는 1.13 이상이여서, 해당 서버에서 결국 go 바이너리까지 교체해주었습니다.

mv /usr/bin/go /usr/bin/go-1.10
mv /usr/local/go/bin/go /usr/bin/go


Reference

https://github.com/projectdiscovery/subfinder/issues/197
Share: | Coffee Me:

12/18/2019

nq를 이용한 command line queueing

최근 Pipeline으로 여러가지를 스캐닝해줄 도구를 만들고 있는데, 해당 구간에서 사용할 큐에 대해 고민하던중 심플한 툴이 있어서 공유해봅니닷.. (사실 장인정신으로 한땀한땀 서비스를 분석하는걸 즐기지만, 슬슬 개인적인 영역에도 자동화의 필요성을 점점 느끼고 있네요..)

처음엔 RabbitMQ를 생각했었는데, 간단한 큐잉을 위해서 저거까지 써야하나 고민이 들었습니다. 그래서 생각을 정리한걸론 직접 만들자 vs 좀 더 찾아보자 였고 찾아본 결과 nq와 pueue로 압축되었습니다. 둘 다 간단한 툴이며, 그냥 개인적인 환경 구성 상 nq가 깔끔하게 설치되길래 nq로 정했습니다. (만드는게 베스트이긴한데, 할 일은 산더미..)

Installing nq

# if on linux
$ apt install nq

# if on Mac
$ brew install nq 

리눅스 패키지 관리자들(apt, yum, pacman 등)을 지원하고 HomeBrew 또한 지원하기 때문에 상대적으로 설치가 쉽습니다. 사실 Pueue도 Cobra로 바로 설치가 가능하지만, 테스트한다고 Rust 개발 환경 때문에... 좀 에러가 있습니다.

$ nq
usage: nq [-q] [-w ... | -t ... | CMD...]


Usage

자 ... -h--help를 봐도 똑같습니다. 정보를 정말 안줍니다. 구글링해서 옵션을 정리해봅시다.

nq

$ nq
usage: nq [-c] [-q] [-w ... | -t ... | CMD...]
$ nq [your commands]
-q : nq는 기본적으로 job id를 리턴해줍니다. -q 옵션으로 안보이게 끌 수 있습니다. 
-c : job을 모두 지웁니다(clean jobs)
-w : job이 완료까지 대기합니다. 
-t : 대기하는 job이 있느지 테스트합니다.


fq

fq 현재 실행 중인 작업의 로그를 출력하여 작업이 완료되면 종료하는 보조적인 툴입니다.

$ fq [your job id]

-a : 모든 job의 결과 출력
-n : 기다리지 않습니다 (no wating)
-q : job 당 하나의 행만 출력

Test

간단하게 테스트해봅니다. nq에 2가지 job을 추가합니다. (sleep 10, 5)
그럼 sleep 10이 우선 실행되고 해당 명령이 완료되면 sleep 5가 실행됩니다. fq로 출력을 받았기 때문에 10초 후에 맨 아래 구문이 찍힙니다.

$ nq sleep 10
,16f134fd88a.32350

$ nq sleep 5
,16f134fde8c.32353

$ fq -q
==> ,16f134fd88a.32350 exec 'nq' 'sleep' '10'
==> ,16f134fde8c.32353 exec 'nq' 'sleep' '5'

Conclusion

사실 nq 자체가 기능이 많진 않아서 직접 짜는게 더 편할수도 있습니다. (확장성 측면에서)
다만 간단한 작업에는 이만한 도구가 없는 것 같은데, 잘 활용하면 여러가지 포인트로 사용할 수 있을 것 같네요 :)




Reference

https://github.com/leahneukirchen/nq
https://github.com/leahneukirchen/nq/commit/381576322800ee3afe3246fadaf74d61377951ba
https://github.com/leahneukirchen/nq/commit/871185b1ba7e1cfb41be9290e9c166190b7b1a5d

Share: | Coffee Me:

12/17/2019

Arachni scanner에서 Webhook으로 Slack 연동하기(Send msg to slack when arachni scan is complete)

Arachni는 성능 좋은 웹 취약점 스캐너임과 동시에 CI/CD 및 확장성이 굉장히 좋습니다. Web-UI, REST Server , RPCd, Cli, Interactive Shell 지원하는 것만 봐도 개발자가 엄청 신경썼다는게 느껴지지요.
Arachni is powerful scanner of universe.



스캔이 완료됬을 떄 노티를 받을 수 있으면 참 좋은데, Arachni에서는 플러그인으로 Email 과 Webhook 2개를 지원해줍니다. Webhook이 있다면.. 이미 모든 서비스는 연동할 수 있는 상태이지요.
arachni can receive results when scanning is complete through email and webbook plug-ins.


(예전엔 코드를 직접 커스텀해서 사용했던지라 리포트 생성단계에서 별도로 요청을 보냈던거 같네요..)

아무튼 오늘은 간단하게 Arachni의 webhook notify를 통해 slack으로 메시지를 전달하는 방법에 대해 정리해보죠.
Today is the how to arachni notify message to slack with webhook.

Make Slack Webhook

Slack에 들어가셔서 incoming webhook을 적용해줍니다. Slack 무료 플랜이 10개까지인가 쓸 수 있는데, 확장성을 고려하면 incoming, outgoing webhook 2개는 무조건 필수로 생각됩니다.
First, Go to the Slack and apply incoming webhook.

Add Incoming Webhooks on Slack

Setting Webhook and copy Webhook URL


생성 이후 Web Hook URL 복사해둡니다. (미리 쓰고 계셨다면 기존 URL을..)
And.. Copy WebHook URL

Add(edit) Profile for Webhook notify Plugin

이제 Arachni의 Scan Profile을 변경해주어야 하는데요, Web-UI 기준으론 아래 경로에 있습니다.
New(or Edit) Profile > Plugins > Webhook notify (webhook_notify)
Let's approach the path above and modify the profile.

플러그인쪽에 Webhook notify 추가하면 몇가지 데이터를 작성하는 부분이 나타납니다. 여기서 미리 Arachni에 정의된 변수들을 쓸 수 있는데, 아래와 같습니다.
When you add a Webhook plugin, you will see some data. Here you can write the variables defined in Aracini in advance, as shown below.

Sends a webhook payload over HTTP/HTTPS at the end of the scan.

Valid payload variables to use in the payload:

$SEED$ – Unique seed used for the scan.
$URL$ – Targeted URL.
$MAX_SEVERITY$ – Maximum severity of the identified issues.
$ISSUE_COUNT$ – Amount of identified issues.
$DURATION$ – Scan duration.

(첨에 이걸 링크 안보고 테스트하다가 고생좀 했네요..)

아무튼.. 형식에 맞게 데이터를 넣어보면..
URL
Your hook url

Type
json

Payload
{"channel": "#your_channel", "username": "your_arachni_name?", "text": "Finish scan $URL$\n+ Max Severity: $MAX_SEVERITY$\n+ Found Issues: $ISSUE_COUNT$\n+ Seed: $SEED$", "icon_emoji": ":dragon_face:"}

요런 형태가 됩니다.



Shall we try?

test now!

run arachni scanning and when finish..

Notify to slack

Slack에 Report URL 추가하기

Slack에 받은 데이터에서 바로 Report를 열고 싶은 경우가 있습니다. 이 때 우리가 중요하게 봐야할 SEED 값입니다. Web-UI에선 사용되지 않는 값이지만, 이 값은 실제 스캔 건에 대해 Key 값이며, REST API에서 scan을 식별하는 주요 키 값으로 쓰입니다.
You may want to open the Report directly from the data you received in the Slack. And that's the SEED that we need to look at as important. This value is not used in the Web-UI, but it is the key value for the actual scan case and is used as the main key value to identify scan in the REST API.


REST API 문서를 보면 Report쪽은 아래와 같이 정의됩니다.
Defines the Report page as follows:

GET /scans/:id/report
GET /scans/:id/report.json
GET /scans/:id/report.xml
GET /scans/:id/report.yaml
GET /scans/:id/report.html.zip

여기서 :id 값은 위에서의 SEED 값이며, 이를 활용하면 이런 URL을 만들 수 있습니다.
The value of :id is the SEED value above, and you can make report API url.

http://your-arachni-rest-server/scans/$SEED$/report.html.zip

요 내용이 Webhook notify에 들어간다면 아래처럼 치환되겠죠.

http://your-arachni-rest-server/scans/cb6881995df794f82bad153425ecc602/report.html.zip

압축은.. REST API를 그냥 쓴다면 어쩔 수 없는 부분입니다. 코드를 수정해서 최종 리포트 생성 이후 또는 리포트 요청 할 때 강제로 압축 풀도록 하면 좋습니다 :)


Share: | Coffee Me:

12/12/2019

How to find End-point URL in Javascript with LinkFinder

@ZracheSs-AnasZ트윗을 보다가 아주 괜찮은 툴을 알게되어 공유합니다.
I've seen the tweet from @ZracheSs-AnasZ yesterday, and I got to know awesome tool and I share it now



LinkFinder?

이름 그대로 링크를 찾아주는 도구인데, 일반적인 크롤러와 다른점은 Javascript 내부에 정의된 URL 패턴도 찾아준다는 겁니다.
It's tool for finding link(url), but what's different from a typical crawler is it also looks for URL patterns defined inside Javascript.


보통 버그바운티 대상 사이트들은 굉장히 많은 테스팅을 거쳐서 단단하기 때문에 취약점이 쉽게 나오진 않습니다. 특히 뻔한 주소, 뻔한 취약점일 수록 중복 확률도 매우 높죠.
Usually, bugbounty sites are hard after a lot of testing, so they're not easily vulnerable. The common urls, the common the vulnerability is the more likely duplicated


저 또한 느끼고 있고 다른 해커들도 동일하게 생각하는 점은 Javascript 를 꼼꼼하게 봐야한다는 점입니다. Js에서 deprecated 된 주소를 찾을수도 있고 다른 사람이 아직 식별하지 못한 URL들을 찾아낼 수 있습니다.
What I feel and what other hackers think the same is that you have to look at Javascript carefully. Js can find addresses that have been de-preceded or URLs that others have not yet identified.


그래서, 이 툴이 좋은 이유입니다.
So this tool is awesome!


(제가 예전에 SMT Solver 보고 Js단에서 흐름을 추적하는걸 만들어보고 싶단 생각을 했었는데, 어찌보면 이런쪽으로도 활용해볼 여지가 있었네요.. 그러나 어차피 못만듬..)

How to Install?

$ git clone https://github.com/GerbenJavado/LinkFinder
$ cd LinkFinder
$ python3 setup.py install


finish!

$ python3 linkfinder.py


Options

$ linkfinder -h
usage: linkfinder.py [-h] [-d] -i INPUT [-o OUTPUT] [-r REGEX] [-b]
                     [-c COOKIES]

optional arguments:
  -h, --help            show this help message and exit
  -d, --domain          Input a domain to recursively parse all javascript
                        located in a page
  -i INPUT, --input INPUT
                        Input a: URL, file or folder. For folders a wildcard
                        can be used (e.g. '/*.js').
  -o OUTPUT, --output OUTPUT
                        Where to save the file, including file name. Default:
                        output.html
  -r REGEX, --regex REGEX
                        RegEx for filtering purposes against found endpoint
                        (e.g. ^/api/)
  -b, --burp
  -c COOKIES, --cookies COOKIES
                        Add cookies for authenticated JS files


Scan endpoint url in Javascript

$ linkfinder -i https://pagead2.googlesyndication.com/pagead/js/r20191205/r20190131/show_ads_impl_fy2019.js -o cli
text/javascript
https://pagead2.googlesyndication.com/getconfig/sodar
//tpc.googlesyndication.com/sodar/%{basename}.js
http://googleads.g.doubleclick.net
http://pagead2.googlesyndication.com
https://googleads.g.doubleclick.net
https://pagead2.googlesyndication.com
amp4ads-host-v0.js
https://cdn.ampproject.org/
//fonts.googleapis.com/css
text/css
https://pagead2.googlesyndication.com/pagead/gen_204
/pagead/gen_204?id=
/images/icons/material/system/2x/close_white_24dp.png
//www.google.com/settings/ads/anonymous
/pagead/js/logging_library.js
/r20100101
//www.googletagservices.com/activeview/js/current/osd.js?cb=
//pagead2.googlesyndication.com/pagead/gen_204?id=osd&amp;r=om
/r20190131
//www.google.com/adsense/search/ads.js
https://www.gstatic.com/adsense/autoads/icons/gpp_good_24px_blue_600.svg
https://www.gstatic.com/adsense/autoads/icons/close_24px_grey_700.svg
https://fundingchoicesmessages.google.com/uf/%{externalId}
/pagead/js/
/r20190131/reactive_library.js
/r20190131/debug_card_library.js
/pagead/js/adsbygoogle.js
https://pagead2.googlesyndication.com/pagead/gen_204?id=imerr
/pagead/html/
/r20190131/zrt_lookup.html#
/pagead/ads?
/pagead/lopri?
/pagead/blank.gif#?
/pagead/js/r20191205/r20190131/rum.js
/pagead/js/r20191205/r20190131/creativetoolset/xpc_expansion_embed.js

Scan endpoint url in Javascript on Target domain

$ linkfinder -i https://www.hahwul.com -d -o cli | more
Running against: https://ajax.googleapis.com/ajax/libs/jquery/3.2.1/jquery.min.js

process/browser.js
./auth.js
../vendor/es6-promise.js
../vendor/easyXDM.js
./util.js
./common.js
./api.authType
/v1/api/story/upload/multi
/v2/api/talk/message/image/upload
/v1/user/signup
....
https://www.hahwul.com/2018/08/install-kakaotalk-on-ubuntu-18.04.html
https://www.hahwul.com/2019/10/find-subdomain-takeover-with-amass-and-subjack.html
https://www.hahwul.com/2018/08/git-credential-helper.html
https://www.hahwul.com/2017/08/hacking-frida-hooking-to-multi-platform.html
https://www.hahwul.com/2016/08/debian-apt-get-could-not-get-lock.html
https://www.hahwul.com/2016/02/coding-git-push-push-error-failed-to.html
https://www.hahwul.com/2016/04/coding-git-pull-pull.html
https://www.hahwul.com/2019/11/how-to-diable-detectportal-firefox.html
https://www.hahwul.com/search/label/Hacking
https://www.hahwul.com/search/label/Web%20Hacking
https://www.hahwul.com/search/label/%23Hacking
https://www.hahwul.com/search/label/Coding


Output options

기본적으론 html output을 지원하고 -o 옵션 중 cli 를 통해 console output도 뿌려줄 수 있습니다. 개인적으론 pipeline 하기 위해선 cli 옵션쪽이 좀 더 현명한 선택 같네요 :)


Conclusion

아무튼 Javascript를 유심히 살펴보는건 웹이나 모바일(웹뷰, 인앱브라우저 등?)에서도 굉장히 중요한 작업니다. 슬슬 Js를 심도있게 분석해줄 수 있는 도구의 필요성이 점점 느껴지네요.
Share: | Coffee Me:

12/08/2019

Easy command for find iOS Application directory on Jailed Device

Unlike Android, iOS has a random pattern of directory names for each app. This is a little annoying when analyzing it.



but you can simply check it out by using the commands below. (Create for Memo)

$ find . -maxdepth 3 | grep <Search App Name>


With the -type option, you can search in fast.

$ find . -type f -maxdepth 3 | grep <Search App Name>
$ find . -type d -maxdepth 3 | grep <Search App Name>


e.g
$ find . -maxdepth 3 | grep YouTube



Share: | Coffee Me:

12/06/2019

MacOS에서 터미널앱이 차단된 경우 (Gatekeeper disable for terminal application)

간만에 Arachni 소스를 좀 고쳐볼까 하고 보던 중 난감한 상황이 있었습니다..
언젠가 부터 MacOS에서 출처가 애매한 어플리케이션(앱스토어가 아닌..) 경우 기본적으로 실행을 차단하고 별도의 과정을 통해 실행할 수 있게 하고 있습니다. 이게 바로 게이트키퍼인데요, 보통은 Finder에서 우클릭 후 실행을 하면 열기 라는 버튼을 통해 활성화 시킬 수 있었습니다.

좀 애매한 경우가 있었는데, 앱은 승인을 해도 앱 내 포함된 dylib로 인해 차단되는거였죠..



$ ./arachni
dyld: Library not loaded: /Users/zapotek/arachni-build-dir/arachni/system/usr/lib/libruby.2.2.0.dylib
  Referenced from: /Users/hahwul/HAHWUL/tool/arachni/bin/../system/usr/bin/ruby
  Reason: no suitable image found.  Did find:
 /Users/hahwul/HAHWUL/tool/arachni/bin/../system/usr/lib/libruby.2.2.0.dylib: code signature in (/Users/hahwul/HAHWUL/tool/arachni/bin/../system/usr/lib/libruby.2.2.0.dylib) not valid for use in process using Library Validation: library load disallowed by system policy
[1]    84989 abort      ./arachni

Why?

애플 개발자 문서에서 정책을 찾아보니 dyld는 기본적으로 차단한다고 합니다.
https://developer.apple.com/documentation/bundleresources/entitlements/com_apple_security_cs_disable-library-validation?language=objc

Discussion
Typically, the Hardened Runtime’s library validation prevents an app from loading frameworks, plug-ins, or libraries unless they’re either signed by Apple or signed with the same team ID as the app. The macOS dynamic linker (dyld) provides a detailed error message when this happens. Use the Disable Library Validation Entitlement to circumvent this restriction.

To add this entitlement to your app, first enable the Hardened Runtime capability in Xcode, and then under Runtime Exceptions, select Disable Library Validation.

Solution1 로드되는 Dyld 모두 허용처리하기

실행 시 차단된 Dyld들은 시스템 환경설정 > 보안 및 개인정보 보호 > 일반에서 별도로 내용이 나타나고, 예외처리를 할 수 있습니다.



처음엔 그렇게 하려고 했으나... 엄청난 양의 Dyld로 인해 멘탈이 부숴져버렸죠..

Solution2 게이트키퍼 비활성화 후 실행하여 신뢰처리

가장 위험하지만, 가장 깔끔한 방법입니다. 일정 시간동안 게이트키퍼를 비활성화 시켜 모든 앱을 허용시킨 후 앱의 기능을 수행합니다. 그럼 신뢰받는 dyld로 보고 다시 활성화 되여도 재확인을 하지 않습니다. 아래와 같이 spctl 로 비활성화 시킵니다.

sudo spctl --master-disable




이후 앱을 실행하면 잘 실행됩니다. 여기서 하나 중요한점은, 실행 과정에서 필요한 dyld가 모두 로드되어야한다는건데, 즉 아래처럼 ./arachni 만 실행한 경우.. 실제로 스캔을 돌릴 때 또 에러가 나게 됩니다. (스캔에서 다시 필요한 dyld를 불러와서)

./arachni
Arachni - Web Application Security Scanner Framework v1.5.1
   Author: Tasos "Zapotek" Laskos <tasos.laskos@arachni-scanner.com>

           (With the support of the community and the Arachni Team.)

   Website:       http://arachni-scanner.com
   Documentation: http://arachni-scanner.com/wiki


 [-] Missing URL argument.

그래서 되도록이면, 여러가지 루트로 어플리케이션에서 사용하는 dyld를 최대한 사용해주고, 다시 기능을 활성화합니다.

sudo spctl --master-enable
Share: | Coffee Me:

12/05/2019

Two easy ways to get a list of scopes from a hackerone

Hi hackers, I write post for easy get bugbounty target scope. simple 2 way.
해커원 버그바운티 프로그램들을 보면 타겟 도메인이 굉장히 많은 경우가 있습니다. 매번 Scope 처리하거나, 테스트 할 때 확인하기 불편한감이 있는데, 이를 쉽게 처리할 수 있는 2가지 방법에 대해 이야기할까 합니다.

TL;DR

- Using Burp project config
- Using my simple script or bookmarklet

1. Burp Suite Project file

Hackerone provides the Burp suite Project config file. This makes it easy to apply the scope to the Burp suite. Look at the bottom of the hackerone page. There's an answer.
해커원에서 고맙게도 타겟 도메인들에 대해 Burp Project 파일로 제공해주고 있습니다. 버바 페이지 맨 아래에 보시면 링크가 있습니다. View change 통해서 변경 이력도 볼 수 있는데, 신규로 추가된 도메인을 식별하기에 좋으니 참고해주세요.



2. Write to simple Code for scope list

I wrote the very simple code because parsing to scope was too annoying. Simple to output a list of domains, which can be used as material values for other tools.
자바스크립트로 간단하게 작성했습니다. 그냥 테이블 정보 읽어서 필요한 필드만 출력하는 정도입니다..

dtable = document.getElementsByClassName("daisy-table")[1].children[0].children;
weblist = ""
applist = ""
for(i=0;i<dtable.length;i++){
  if(dtable[i].children[0].children[0].innerText == "Domain" ){
      weblist = weblist + dtable[i].children[1].children[0].children[0].innerText + "\n"
    }else{
        applist = applist + dtable[i].children[1].children[0].children[0].innerText + "\n"
    }
}
console.log("< WEB >")
console.log(weblist)
console.log("< APP >")
console.log(applist)


case to paypal (https://hackerone.com/paypal)

< WEB >
*.xoom.com
paypal.me
scrutiny.swiftfinancial.com
pigeon.swiftfinancial.com
decision.swiftfinancial.com
partner.swiftfinancial.com
prequal.swiftfinancial.com
*.braintree.tools
*.braintree-api.com
py.pl
paypalobjects.com
*.paydiant.com
*.braintreegateway.com
*.venmo.com
swiftcapital.com
swiftfinancial.com
loanbuilder.com
my.loanbuilder.com
api.loanbuilder.com
my.swiftfinancial.com
api.swiftfinancial.com
www.swiftfinancial.com
www.loanbuilder.com
www.swiftcapital.com
*.braintreepayments.com
www.paypal-*.com
*.paypal.com

< APP >
com.paypal.here
com.venmo
com.paypal.merchant.client
com.xoom.android.app
com.paypal.android.p2pmobile
com.paypal.merchant
com.yourcompany.PPClient
com.paypal.here
com.xoom.app
net.kortina.labs.Venmo
com.paypal.herehd



2-2. Change Bookmarklet

Copy this link and add bookmark with paste :)

javascript:%64%74%61%62%6c%65%20%3d%20%64%6f%63%75%6d%65%6e%74%2e%67%65%74%45%6c%65%6d%65%6e%74%73%42%79%43%6c%61%73%73%4e%61%6d%65%28%22%64%61%69%73%79%2d%74%61%62%6c%65%22%29%5b%31%5d%2e%63%68%69%6c%64%72%65%6e%5b%30%5d%2e%63%68%69%6c%64%72%65%6e%3b%77%65%62%6c%69%73%74%20%3d%20%22%22%3b%61%70%70%6c%69%73%74%20%3d%20%22%22%3b%66%6f%72%28%69%3d%30%3b%69%3c%64%74%61%62%6c%65%2e%6c%65%6e%67%74%68%3b%69%2b%2b%29%7b%69%66%28%64%74%61%62%6c%65%5b%69%5d%2e%63%68%69%6c%64%72%65%6e%5b%30%5d%2e%63%68%69%6c%64%72%65%6e%5b%30%5d%2e%69%6e%6e%65%72%54%65%78%74%20%3d%3d%20%22%44%6f%6d%61%69%6e%22%20%29%7b%77%65%62%6c%69%73%74%20%3d%20%77%65%62%6c%69%73%74%20%2b%20%64%74%61%62%6c%65%5b%69%5d%2e%63%68%69%6c%64%72%65%6e%5b%31%5d%2e%63%68%69%6c%64%72%65%6e%5b%30%5d%2e%63%68%69%6c%64%72%65%6e%5b%30%5d%2e%69%6e%6e%65%72%54%65%78%74%20%2b%20%22%5c%6e%22%7d%65%6c%73%65%7b%61%70%70%6c%69%73%74%20%3d%20%61%70%70%6c%69%73%74%20%2b%20%64%74%61%62%6c%65%5b%69%5d%2e%63%68%69%6c%64%72%65%6e%5b%31%5d%2e%63%68%69%6c%64%72%65%6e%5b%30%5d%2e%63%68%69%6c%64%72%65%6e%5b%30%5d%2e%69%6e%6e%65%72%54%65%78%74%20%2b%20%22%5c%6e%22%7d%7d%63%6f%6e%73%6f%6c%65%2e%6c%6f%67%28%22%3c%20%57%45%42%20%3e%22%29%3b%63%6f%6e%73%6f%6c%65%2e%6c%6f%67%28%77%65%62%6c%69%73%74%29%3b%63%6f%6e%73%6f%6c%65%2e%6c%6f%67%28%22%3c%20%41%50%50%20%3e%22%29%3b%63%6f%6e%73%6f%6c%65%2e%6c%6f%67%28%61%70%70%6c%69%73%74%29


Share: | Coffee Me:

Fixing a pip3 crash error after a Mac Catalina update

Problem

I have fatal error when running pip3 after Mac Catalina update in my mac. This made it impossible to install, update, or delete using pip.

pip3 install objection
[1]    66557 abort      pip3 install objection


Details crash log.
Process:               python3.7 [8546]
Path:                  /usr/local/Cellar/salt/2019.2.1/libexec/bin/python3.7
Identifier:            python3.7
Version:               0
Code Type:             X86-64 (Native)
Parent Process:        python3.7 [8537]
Responsible:           python3.7 [8537]
..snip...
Thread 0 Crashed:: Dispatch queue: com.apple.main-thread
0   libsystem_kernel.dylib         0x00007fff671c847a __pthread_kill + 10
1   libsystem_pthread.dylib        0x00007fff67289707 pthread_kill + 384
2   libsystem_c.dylib              0x00007fff67150a08 abort + 120
3   libcrypto.dylib                0x00007fff64ae6804 __report_load + 352
....


https://i.giphy.com/Rkis28kMJd1aE.gif

Solution?

I found the same issue as me in the github. It appears to be a problem with the asn1crypto package on python3, which can be resolved by deleting.
https://github.com/Homebrew/homebrew-core/issues/44996

asn1crypto package is in python3 site-package directory

$ ll /usr/local/lib/python3.7/site-packages/asn1crypto
total 1048
-rw-r--r--   1 hahwul  admin   209B  5  6  2019 __init__.py
drwxr-xr-x  27 hahwul  admin   864B  5  6  2019 __pycache__
-rw-r--r--   1 hahwul  admin   9.2K  5  6  2019 _elliptic_curve.py
-rw-r--r--   1 hahwul  admin   967B  5  6  2019 _errors.py
-rw-r--r--   1 hahwul  admin   738B  5  6  2019 _ffi.py
-rw-r--r--   1 hahwul  admin   4.6K  5  6  2019 _inet.py
-rw-r--r--   1 hahwul  admin   4.5K  5  6  2019 _int.py
-rw-r--r--   1 hahwul  admin   8.4K  5  6  2019 _iri.py
-rw-r--r--   1 hahwul  admin   4.4K  5  6  2019 _ordereddict.py
drwxr-xr-x   5 hahwul  admin   160B  5  6  2019 _perf
-rw-r--r--   1 hahwul  admin   4.9K  5  6  2019 _teletex_codec.py
-rw-r--r--   1 hahwul  admin   939B  5  6  2019 _types.py
-rw-r--r--   1 hahwul  admin    33K  5  6  2019 algos.py
-rw-r--r--   1 hahwul  admin    25K  5  6  2019 cms.py
-rw-r--r--   1 hahwul  admin   154K  5  6  2019 core.py
-rw-r--r--   1 hahwul  admin    16K  5  6  2019 crl.py
-rw-r--r--   1 hahwul  admin   2.1K  5  6  2019 csr.py
-rw-r--r--   1 hahwul  admin    34K  5  6  2019 keys.py
-rw-r--r--   1 hahwul  admin    17K  5  6  2019 ocsp.py
-rw-r--r--   1 hahwul  admin   8.9K  5  6  2019 parser.py
-rw-r--r--   1 hahwul  admin   2.2K  5  6  2019 pdf.py
-rw-r--r--   1 hahwul  admin   6.0K  5  6  2019 pem.py
-rw-r--r--   1 hahwul  admin   4.5K  5  6  2019 pkcs12.py
-rw-r--r--   1 hahwul  admin   7.6K  5  6  2019 tsp.py
-rw-r--r--   1 hahwul  admin    18K  5  6  2019 util.py
-rw-r--r--   1 hahwul  admin   154B  5  6  2019 version.py
-rw-r--r--   1 hahwul  admin    90K  5  6  2019 x509.py

Remove asn1crypto

$ rm -rf /usr/local/lib/python3.7/site-packages/asn1crypto


It's work? right!

$ pip3 install objection
Collecting objection
  Downloading https://files.pythonhosted.org/packages/b3/12/aba1cee91a1183f51eafefec5ae71040159dbb0fbf04d2603dbb1f362e6a/objection-1.8.3.tar.gz (221kB)
     |████████████████████████████████| 225kB 255kB/s
Requirement already satisfied: frida in /usr/local/lib/python3.7/site-pa


Share: | Coffee Me:

11/23/2019

Check logic vulnerability point using GET/HEAD in Ruby on Rails

최근에 Github OAuth flow bypass 취약점이 공개되었습니다. 이 취약점은 Rails 앱의 특성을 이용한 취약점이고, Github만의 문제가 아니고 패치로 모든 Rails 앱을 보호할 수도 없습니다.
Today, I going to review one vulnerability that needs to be checked in the Rails App environment through the Github OAuth flow bypass vulnerability.
(B recently shared something interesting to me.)

그래서 어떤 내용이고 어떤 부분을 중점으로 분석해야할지 정리해봅니다.

Thanks to B for letting me test it again.

Summary

A brief description of the link below. For English, just refer to the link. :)

우선 취약점에 대해 간략히 살펴봅시다. 깃허브 사용자가 외부 앱에 로그인하는 경우 버튼을 통해 확인을 받게 됩니다. 이 과정에는 당연하게 CSRF에 대한 대응로직은 당연하게 존재합니다.

Github의 3rd App에 대한 Authorize 플로우 중 https://github.com/login/oauth/authorize 페이지가 인증 버튼을 보여주는 뷰어(GET)이자, 인증 요청이 맨 마지막 페이지(POST)이기도 합니다. Rails 앱은 기본적으로 CSRF Token으로 모든 요청을 검증하고 있지만, 이 부분에서 아래 설명할 HEAD 메소드를 이용하여 CSRF 대응 로직을 우회하고 이를 가능하게 합니다.

자세한 내용은 아래 링크를 참고해주세요.
https://blog.teddykatz.com/2019/11/05/github-oauth-bypass.html

What is HEAD Method

HEAD Method는 HTTP의 기본 메소드로 바디를 포함하지 않는 헤더만을 리턴받는 메소드입니다. 보통은 파일의 크기를 가늠하기 위해서 사용하는 경우들이 있는데, 아래 RFC 문서를 보면 이렇게 명시되어 있습니다.
The HEAD Method is the default method for HTTP and only the header that does not contain the body is returned. There are usually cases that you use to measure the size of a file. refer to RFC document below.

...
The server SHOULD send the same
   header fields in response to a HEAD request as it would have sent if
   the request had been a GET
...
Hypertext Transfer Protocol (HTTP/1.1): Semantics and Content 중 HEAD



결국 HEAD 메소드는 GET과 동일한 요청 베이스를 가지는거죠.
The point is that GET and HEAD behave the same.

HEAD Method in Rails

Rails에서도 HEAD Method는 동일하게 GET과 같은 취급을 받습니다. 그래서..
routes.rb에 이런식으로 명시되어 있다면, GET 뿐만이 아니라 HEAD로도 요청이 가능합니다.
The point is that GET and HEAD behave the same on Rails router


Rails.application.routes.draw do
  get 'app/index'
end

Vulnerable Point

대충.. 이런식으로 코드를 하나 만들어봤습니다. 웹 요청을 받으면 GET인 경우 302로 제 블로그, 이외 케이스는 모두 307로 localhost로 가게끔 말이죠.
I made a test code. For GET, 302 and all other methods are 307.


controller
class TesterController < ApplicationController
  def test_redirect
    p 'this is test_redirect'
    p "Method: "+request.method
    # 메소드를 출력 후
    # GET인 경우 제 블로그로 redirect
    if request.method.to_s == 'GET'
      respond_to do |format|
        format.html {redirect_to '[https://www.hahwul.com](https://www.hahwul.com/)', :status => 302}
        format.json {}
      end
    # GET이 아닌 경우 localhost로 리다이렉트 시켰습니다.
    else
      respond_to do |format|
        format.html {redirect_to '[http://127.0.0.1](http://127.0.0.1/)', :status => 307}
        format.json {}
      end
    end
  end

당연히 route는 get만 처리할 수 있도록 지정해줍니다.

routes.rb
Rails.application.routes.draw do
  get 'tester/test_redirect'
end


자 이제 실제로 테스트해보면 이렇습니다.
우선 GET부터 보내게 되면, 당연히 제 블로그 주소로 302 redirect 됩니다.

Test with GET Method
$ curl -i -k http://127.0.0.1/tester/test_redirect
HTTP/1.1 301 Moved Permanently
X-Frame-Options: SAMEORIGIN
X-XSS-Protection: 1; mode=block
X-Content-Type-Options: nosniff
X-Download-Options: noopen
X-Permitted-Cross-Domain-Policies: none
Referrer-Policy: strict-origin-when-cross-origin
Content-Type: text/html; charset=utf-8
Location: [https://www.hahwul.com](https://www.hahwul.com/)
Cache-Control: no-cache
X-Request-Id: f0c1e322-cbc7-4bc8-9535-84471bd8c11e
X-Runtime: 0.039037
Transfer-Encoding: chunked<html><body>You are being <a href="[https://www.hahwul.com](https://www.hahwul.com/)">redirected</a>.</body></html>

그럼 HEAD로 요청을 날리게 될 땐 어떻게 처리될까요?

Test with HEAD Method
$ curl -i -k http://127.0.0.1/tester/test_redirect -X HEAD
Warning: Setting custom HTTP method to HEAD with -X/--request may not work the
Warning: way you want. Consider using -I/--head instead.
HTTP/1.1 307 Temporary Redirect
X-Frame-Options: SAMEORIGIN
X-XSS-Protection: 1; mode=block
X-Content-Type-Options: nosniff
X-Download-Options: noopen
X-Permitted-Cross-Domain-Policies: none
Referrer-Policy: strict-origin-when-cross-origin
Content-Type: text/html; charset=utf-8
Location: [http://127.0.0.1](http://127.0.0.1/)
Cache-Control: no-cache
X-Request-Id: 3b13e501-7c8b-45be-8e45-cb43e5fabbee
X-Runtime: 0.034709

routes.rb에는 get으로 제한했기 때문에 HEAD 또한 컨트롤러로 넘어갑니다. 이후 컨트롤러에서 request.method 로 검증을 했기 때문에 같은 GET 베이스의 요청이지만 실제로 처리하는 동작이 달라지게 됩니다.
A test_redirect page is only use get method because routes.rb.
but passed request with HEAD Method. In the controller, GET and HEAD method a diffrent. they are crossroads.

깃헙의 경우...

if request.get?
  # serve authorization page HTML
else
  # grant permissions to app
end

인증 뷰 페이지와 auth 플로우의 마지막 페이지의 주소가 같았고, 위 처럼 request.get? 으로 검증했기 때문에 authorize 요청을 CSRF 토큰 처리 없이 전달할 수 있게 됩니다.
결국 JS를 통해 HEAD 요청을 전달하는 CSRF 코드를 만들면 사용자의 동의 없이 3rd App을 연동할 수 있게 됩니다.

In github case, address of the last page of the auth flow was the same as the authentication view page, and because the address was verified as request.get?, the authoreize request can be send without CSRF token. Eventually, when you create a CSRF code that passes HEAD requests through JS, you can added the 3rd App without your consent.

HEAD login/oauth/authorize?client_id={CLIENT_ID}&scope=read:user&authorize=1
Host: github.com
(https://not-an-aardvark.github.io/oauth-bypass-poc-fbdf56605489c74b2951/ 실제 PoC)

Conclusion

HEAD에 대한 처리 방식을 Rails의 스펙적인 부분이기 때문에 (사실 당연한 이치) Rails 자체의 문제는 아닙니다. 결국은 개발자가 로직을 구성할 때 이러한 점들이 고려되지 않은 웹에서는 분명히 문제가 될 수 있는 부분이겠죠.

결국은 매번 분석할 때 마다 컨트롤러들의 동작과 분기를 잘 살펴봐야할 것 같네요.. HTTP Method 검증에 자주 사용되는 루비 메소드들입니다.

request.method
request.get?
request.post?
etc..



Reference

https://blog.teddykatz.com/2019/11/05/github-oauth-bypass.html
https://developer.mozilla.org/ko/docs/Web/HTTP/Methods/HEAD
Share: | Coffee Me:

11/22/2019

[루비에서 Go로 넘어가기] Revel을 이용해 MVC 웹 구성하기

Ruby에서 golang으로 주력 언어를 바꿔가는 중입니다. 이 과정에서 가장 문제가 되는 부분이 .. 웹앱이였습니다. 이미 Rails에 익숙해진터라 대안이 될만한 여러 프레임워크를 찾아봤고, 2가지 생각이 나왔습니다.

1) revel을 통한 개발(MVC)
2) 기본으로 제공되는 net/http와 VueJS 조합

go에 MVC가 어울리는지는 모르겠으나, 우선 익숙함을 채워줄 것이 필요했기 때문에 Revel부터 진행했습니다.
(왜냐믄.. Rails랑 비슷하단 느낌을 많이 받았거든요.)

그리고 단일 페이지에 Vue로 프론트 구성하고, 백엔드 API로 동작 구현하는 2번 방식도 자주 써볼까합니다.
(어차피 난 전문 개발자가 아니니깐!)

아무튼 오늘 글은 1번에 대한 내용이고, Revel 사용하는 방법 정도만 정리해둡니다.
(모든건 실전!)



Install revel

go get으로 revel을 설치해줍시다.

$ go get -u github.com/revel/cmd/revel

쓰기 편하게 alias 등록해줍시다.

$ vim ~.zshrc
alias revel='/Users/hahwul/go/bin/revel' # 추가

$ source ~/.zshrc

자 초기 세팅은 끝났습니다.

$ revel 
Usage:
  revel [OPTIONS] <command>

Application Options:
  -v, --debug              If set the logger is set to verbose
      --historic-run-mode  If set the runmode is passed a string not json
  -X, --build-flags=       These flags will be used when building the application. May be specified multiple times,
                           only applicable for Build, Run, Package, Test commands

Available commands:
  build
  clean
  new
  package
  run
  test
  version



Create New WebApp

gopath로 이동해서 프로젝트를 생성해줍니다.

$ cd $GOPAHT(~/go)
$ revel new -a teszz
Revel executing: create a skeleton Revel application
Your application has been created in:
   /Users/hahwul/go/src/teszz

기본적으로 구조는 잡아주고, revel run 명령으로 실행할 수 있습니다.

$ revel run -a teszz
Revel executing: run a Revel application
WARN  01:34:22    run.go:150: No http.addr specified in the app.conf listening on localhost interface only. This will not allow external access to your application
INFO  01:34:24    app     run.go:26: Running revel server
INFO  01:34:24    app revel_hooks.go:32: Go to /@tests to run the tests.
Revel engine is listening on.. localhost:49464
Revel proxy is listening, point your browser to : 9000

서버의 기본 포트는 9000번입니다. 웹 브라우저로 접속해보면...

it works!


Revel App의 구조 파악하기

처음에 이야기드렸던대로 MVC 모델을 따르며, 전반적으로 Rails랑 비슷한 느낌이 많이듭니다.

$ cd ~/go/src/testzz
$ tree
.
├── README.md
├── app
│   ├── controllers
│   │   └── app.go
│   ├── init.go
│   ├── routes
│   │   └── routes.go
│   ├── tmp
│   │   ├── main.go
│   │   └── run
│   │       └── run.go
│   └── views
│       ├── App
│       │   └── Index.html
│       ├── debug.html
│       ├── errors
│       │   ├── 404.html
│       │   └── 500.html
│       ├── flash.html
│       ├── footer.html
│       └── header.html
├── conf
│   ├── app.conf
│   └── routes
├── messages
│   └── sample.en
├── public
│   ├── css
│   │   └── bootstrap-3.3.6.min.css
│   ├── fonts
│   │   ├── glyphicons-halflings-regular.ttf
│   │   ├── glyphicons-halflings-regular.woff
│   │   └── glyphicons-halflings-regular.woff2
│   ├── img
│   │   └── favicon.png
│   └── js
│       ├── bootstrap-3.3.6.min.js
│       └── jquery-2.2.4.min.js
└── tests
    └── apptest.go

대략 정리해보면...

app 디렉토리: 어플리케이션(view, controller)
conf: 설정정보,라우팅
public: 라우팅 없이 불러올 수 있는 퍼블릭 디렉토리
tests: 기본 유닛테스트

Routing

라우팅은 config/routes 를 통해 설정할 수 있습니다. 아래와 같은 형태를 띄며, URL과 페이지, 컨트롤러를 매핑할 수 있습니다.

module:testrunner
# module:jobs

GET     /                                       App.Index

# Ignore favicon requests
GET     /favicon.ico                            404

# Map static resources from the /app/public folder to the /public path
GET     /public/*filepath                       Static.Serve("public")


View and Template

위에 라우팅에서 / 를 가리키는 App.index 의 실제 뷰인 아래 코드를 봐봅시다.

$ cat app/views/App/Index.html
{{set . "title" "Home"}}
{{template "header.html" .}}

<header class="jumbotron" style="background-color:#A9F16C">
  <div class="container">
    <div class="row">
      <h1>It works!</h1>
      <p></p>
    </div>
  </div>
</header>

<div class="container">
  <div class="row">
    <div class="span6">
      {{template "flash.html" .}}
    </div>
  </div>
</div>

{{template "footer.html" .}}

일반 html 파일이지만, 기본적으로 template를 사용합니다. 구문은 {{template $}} 형태이며, 이를 이용해 어플리케이션 데이터를 직접 사용하거나, 외부 파일을 include 시킬 수 있습니다.

Controller

컨트롤러도 Rails와 거의 유사합니다. (어차피 MVC라 다른 언어도 뭐 비슷하겠죠)

$ cat app/controllers/app.go
..snip..
type App struct {
 *revel.Controller
}

func (c App) Index() revel.Result {
 return c.Render()
}

헤더랑 코드 설정하는 거 몇가지 남겨둡니다. (어차피 결국 doc을 보게됩니다.)

type App struct {
 *revel.Controller
}

// ContentType이나 Statsu 코드, 헤더 등의 추가
func (c App) Index() revel.Result {
  c.Response.Status = http.StatusTeapot
  // or c.Response.Status = 301, 302, 404, etc..
 c.Response.ContentType = "application/json"
 return c.Render()
}

// 외부 Redirect도 Rails와 유사함..
func (c App) redirect_302() revel.Result {
  data := "callback?"
 return c.Redirect("/otherpath/%d", data)
}


Conclusion

사실 글 작성한지는 좀 됬습니다.. 저장만 해뒀다가 이제야 글을 올리게 되네요.
루비에서 고로 바꾸면서 PoC 코드의 작성 범위가 좀 넓어진 느낌이긴합니다. (세심한 컨트롤?)
툴도 하나씩 포팅하고, 신규 툴은 고로 만들고 있는데, 루비랑은 다르게 또 다른 재미가 있네요.
Share: | Coffee Me:

11/19/2019

How to diable detectportal.firefox.com in firefox(enemy of burpsuite)

When i hack the web with proxy tools like Firefox + Burp suite or ZAP, there’s a very annoying request.
파이어폭스와 Burp suite, ZAP 등의 프록시 도구로 테스트를 하다보면, 굉장히 거슬리는 요청이 있습니다.

http://detectportal.firefox.com/success.txt?ipv4, ipv6


This is a request from Firefox to find the Network Login page. (some.. private network, cafe wifi with authentication)
바로 이런 요청인데, 이 기능은 firefox에서 폐쇄망일 경우 네트워크 로그인 페이지(예를들면, 스벅 Wifi에서 로그인 페이지 등)을 찾기 위해 발생하는 요청입니다.
이 요청이 굉장히 짧은 주기로 무제한 호출되기 떄문에 Burp suite에는 이런.. 만행이 일어납니다.


Disable detectportal in config

1) about:config
2) captiv 검색(search captiv)
3) network.captive-portal-service.enabled 를 false로 수정(true to false)


Other way..

1) replace & match on Burp suite
2) SSL Bypass options on Burp suite(I’m not sure if this will work or not.)
Share: | Coffee Me:

Mac 업그레이드 후 개발 관련 도구 에러(xcrun: error: invalid active developer path) 해결방법(xcode-select --install)

최근에 모하비에서 카탈리나로 업그레이드 했습니다. 매번 업데이트 때마다 여러 문제가 발생하는데, 이번에도 어김없이 xcode cli 관련 이슈가 또 터지네요..
매번 명령어 때문에 검색하기도 귀찮은데, 그냥 블로그에 메모해둡니다.



이런 경우에 git을 비롯한 다수의 개발 툴들이 다 xcrun 에러를 뱉게됩니다.

$ git
xcrun: error: invalid active developer path (/Library/Developer/CommandLineTools), missing xcrun at: /Library/Developer/CommandLineTools/usr/bin/xcrun

$ make
xcrun: error: invalid active developer path (/Library/Developer/CommandLineTools), missing xcrun at: /Library/Developer/CommandLineTools/usr/bin/xcrun

$ gcc
xcrun: error: invalid active developer path (/Library/Developer/CommandLineTools), missing xcrun at: /Library/Developer/CommandLineTools/usr/bin/xcrun

xcode-select 명령으로 xcode cli만 따로 설치해서 이 문제를 해결해줍시다.

$ xcode-select --install

대략 설치는 1~2분 정도였던 것 같고 설치가 완료되면 git이 잘 됩니다.


$ git
usage: git [--version] [--help] [-C <path>] [-c <name>=<value>]
           [--exec-path[=<path>]] [--html-path] [--man-path] [--info-path]
           [-p | --paginate | -P | --no-pager] [--no-replace-objects] [--bare]
           [--git-dir=<path>] [--work-tree=<path>] [--namespace=<name>]
           <command> [<args>]

These are common Git commands used in various situations:

start a working area (see also: git help tutorial)
   clone      Clone a repository into a new directory
   init       Create an empty Git repository or reinitialize an existing one

work on the current change (see also: git help everyday)
   add        Add file contents to the index
   mv         Move or rename a file, a directory, or a symlink
   reset      Reset current HEAD to the specified state
   rm         Remove files from the working tree and from the index

examine the history and state (see also: git help revisions)
   bisect     Use binary search to find the commit that 
   ...snip..
Share: | Coffee Me:

11/16/2019

Burp suite using Tor network

버그 바운티를 하다보면, 간혹 차단되는 경우가 있습니다. 다시 차단을 우회하고 접속할 수 있는 방법에는 여러가지가 있으나 tor를 이용하면 간단하게 처리할 수 있습니다.
Sometimes, when you do a bug bounty, network block me from target’s security team… There are many ways to bypass blockage and connect, but with tor, you can do it simply


다만 tor를 사용하면 내 request와 response는 나만의 것이 아니니 중요정보가 포함되거나 인증 쿠키등은 조심해야합니다.
But, if you use tor, my request and response are not only my own, so I have to be careful of important information and certified cookies.


Install & Run tor

Install

$ brew install tor

Running tor

$ tor
Nov 15 23:55:22.342 [notice] Tor 0.4.1.6 running on Darwin with Libevent 2.1.11-stable, OpenSSL 1.1.1d, Zlib 1.2.11, Liblzma N/A, and Libzstd N/A.
Nov 15 23:55:22.342 [notice] Tor can't help you if you use it wrong! Learn how to be safe at https://www.torproject.org/download/download#warning
Nov 15 23:55:22.343 [notice] Configuration file "/usr/local/etc/tor/torrc" not present, using reasonable defaults.
Nov 15 23:55:22.351 [notice] Opening Socks listener on 127.0.0.1:9050
Nov 15 23:55:22.351 [notice] Opened Socks listener on 127.0.0.1:9050
Nov 15 23:55:22.000 [notice] Parsing GEOIP IPv4 file /usr/local/Cellar/tor/0.4.1.6/share/tor/geoip.
Nov 15 23:55:22.000 [notice] Parsing GEOIP IPv6 file /usr/local/Cellar/tor/0.4.1.6/share/tor/geoip6.
Nov 15 23:55:22.000 [notice] Bootstrapped 0% (starting): Starting
Nov 15 23:55:22.000 [notice] Starting with guard context "default"
Nov 15 23:55:23.000 [notice] Bootstrapped 5% (conn): Connecting to a relay
Nov 15 23:55:24.000 [notice] Bootstrapped 10% (conn_done): Connected to a relay
Nov 15 23:55:24.000 [notice] Bootstrapped 14% (handshake): Handshaking with a relay
Nov 15 23:55:25.000 [notice] Bootstrapped 15% (handshake_done): Handshake with a relay done
Nov 15 23:55:25.000 [notice] Bootstrapped 20% (onehop_create): Establishing an encrypted directory connection
Nov 15 23:55:25.000 [notice] Bootstrapped 25% (requesting_status): Asking for networkstatus consensus
Nov 15 23:55:25.000 [notice] Bootstrapped 30% (loading_status): Loading networkstatus consensus
Nov 15 23:55:30.000 [notice] Bootstrapped 45% (requesting_descriptors): Asking for relay descriptors
Nov 15 23:55:30.000 [notice] I learned some more directory information, but not enough to build a circuit: We need more microdescriptors: we have 2862/6000, and can only build 15% of likely paths. (We have 55% of guards bw, 53% of midpoint bw, and 53% of exit bw = 15% of path bw.)
Nov 15 23:55:31.000 [notice] Bootstrapped 56% (loading_descriptors): Loading relay descriptors
Nov 15 23:55:34.000 [notice] Bootstrapped 62% (loading_descriptors): Loading relay descriptors
Nov 15 23:55:34.000 [notice] Bootstrapped 67% (loading_descriptors): Loading relay descriptors
Nov 15 23:55:35.000 [notice] Bootstrapped 72% (loading_descriptors): Loading relay descriptors
Nov 15 23:55:35.000 [notice] Bootstrapped 75% (enough_dirinfo): Loaded enough directory info to build circuits
Nov 15 23:55:36.000 [notice] Bootstrapped 90% (ap_handshake_done): Handshake finished with a relay to build circuits
Nov 15 23:55:36.000 [notice] Bootstrapped 95% (circuit_create): Establishing a Tor circuit
Nov 15 23:55:37.000 [notice] Bootstrapped 100% (done): Done

Setting SOCK5 Proxy on Burp suite

Burp suite > Project options(or User options) > SOCK5 Proxy


host : localhost
port : 9050

Burp request using tor tunnel

The outgoing proxy is now use a tor network

https://i.giphy.com/B37cYPCruqwwg.gif

Share: | Coffee Me:

11/07/2019

Navigation with Embedded Browser on Burp suite 2.1.05(new releases)

Today’s blog post is written only in Korean. This is brief information about the release notes. if you need english, just see release note or translate please.
(http://releases.portswigger.net/2019/11/professional-2105.html)

자 오늘은 Burp suite pro 2.1.05 릴리즈 내용에 대해 이야기할까 합니다.
보통 마이너 버전 업그레이드는 글로 잘 안쓰는데, Burp suite 쪽의 방향성? 을 볼 수 있는 부분이 있어서 간략하게 정리해봐요.

https://i.giphy.com/12GSQqUY9CSmJO.gif

Intro

사실 트위터에서 먼저 봤어서 대충 어떤 업데이트인지는 알고있었는데, 오늘 회사에서 일하다보니 바로 업데이트가 뜨더라구요. 나름 기대했던 기능이라 대충 써보고 집에도 업데이트 후 글 작성중이네요.



사실상 업데이트의 메인 부분인 실험적인 기능인데요.. 내용이 뭔가하면, burp suite 내 크로미움 브라우저를 내장하고 Scanning(Crawl, Audit) 시 기존 크롤러와 함께 내장 브라우저를 이용한 크롤링을 진행한다는 점입니다.

여기서 내장 브라우저를 쓰기 때문에 Vue, React 등 동적으로 페이지를 구성하는 싱글 페이지의 서비스들의 컴포넌트를 식별하고 개별 페이지로 인식시킬 수 있습니다. (이거 구현한거 자체가 대단한듯…)
아무튼 이로인해서, Burp suite의 기능 자체가 크게 향상 될 것 같은 느낌이 드네요. 아직은 초기단계라서 성능 이슈가 있다고는 하는데요, 어떻게 이 실험 기능을 사용하는지 정리해볼게요.

How to use Embedded Browser(chromium) for Navigation

2.1.05 로 업데이트 이후 Scan 쪽 config에 기능이 추가됬습니다. 기본적으론 Disalbe 되어있어서 스캔 시 별도로 활성화 후 테스트를 진행해주시면 됩니다.
먼저, New scan 으로 스캔 위자드 진입 후 Scan configure로 들어가서 설정을 추가해줍니다. 크롤링, 스캐닝에 따라 골라서 추가해주시면 되고 추가하는 과정에서 Miscellaneous 탭에 보시면 Use embedded browser for navigation



Conclusion

확실히 방향이 잡힌듯합니다. Burp suite는 분석쪽으로 강하게 초점을 맞춰서 기능을 업데이트 하는 느낌이고(아 물론 Enterpise는 또 다른 느낌이죠) ZAP은 백그라운드&API화 및 HUD 등을 이용한 진단 방식의 변화를 노려보는 것 같네요.
그나저나 Burp suite, 제발 SSL 에러좀 고쳐주세요. 모두가 희망합니다..


Share: | Coffee Me: