http://www.pythonchallenge.com/pc/hex/bonus.html

 

 

 

위와 같은 소의 사진을 확인할 있다

 

 

 

 

소스코드에는 이렇게 나타나 있다

 

그렇다면 풀어보면

 

 

번역해보니 이렇게 이야기 한다

 

누구에게 하는 것일까 사과는?

 

This 라는 모듈은 문서화가 것이 없다고 한다

 

파이썬을 실행하고 import 해보자

 

 

 

<!--	
	'va gur snpr bs jung?'
	-->

출처: <http://www.pythonchallenge.com/pc/hex/bonus.html>

 

문구가 마음에 걸린다

 

 

관련 검색을 통해 힌트를 얻었고 바로 코드로 작성하였다

 

 

코드를 짜고 실행해보면

 

 

모듈 import 보여진 내용에서 ambiguity 찾을 있었다

 

http://www.pythonchallenge.com/pc/hex/ambiguity.html

 

다음 라운드로 고고

http://www.pythonchallenge.com/pc/hex/copper.html

 

 

 

 

위와 같은 페이지를 확인할 있습니다 조이스틱? 조종해라?

 

소스코드를 확인해 보겠습니다

 

 

 

조금 밝아야 파일을 얻을 있다고 합니다

 

 

Url 보니 어두운 이미지만 보인다,,,,, 밝아야 한다는 것은 이미지의 밝기를 조정해보라는 같다

 

파이썬으로 코드를 보면

 

 

 

 

위와 같은 사진으로 결과는 bonus 얻을 있다

 

 

값을 url 대입해보면

 

파일의 내용을 보면 이렇다

 

 

 

무슨 내용인지 에당초 모르겠다

근데 하나 확실한것은 뒤돌아 보다 되돌아보다

 

인거 같으니까 이전 문제들중에 이런 게임이 있는지 되돌아 봐야 겠다

 

 

되돌아보는중….

 

모르겠다 ㅋㅋㅋㅋ

 

몇일의 고민 끝에 다시 작성하니다

 

 

정답인 코드를 알게 되었고

 

이를 분석하는 방향으로 이번 회차를 넘겨 보고자 합니다

 

 

 

일단 정답인 코드들을 돌려 보면 읽은 라인의 바이트마다

 

특정 패턴이 반복됨을 확인할 있습니다 이를 바탕으로

 

아하~

 

이해 완료

 

파일을 여러 압축한 것으로

 

 

 

https://stackabuse.com/python-zlib-library-tutorial/

여기를 참고하면 아래와 같은 설명을 있습니다 , 파일은 zlib 모듈로 압축된 것이고 이것을 한번 풀면 BZh 압축한 데이터가 나오고 이걸 다시 풀어보면 zlib 압축되어 있고 이것들을 반복하면 실제 데이터를 없을 있습니다

 

 

 

 

 

다만 하나 문제가 되는 것이

 

# elif data.endswith(b'\x9cx'):
#     print("endswith : ", data[:5], "~", data[-5:])
#     data = data[::-1]

 

 

부분입니다 구분자를 어덯게 알아내느냐가 핵심 포인트 인거 같습니다

 

이부분은 나중에 다시 고민해보기로 하고

 

 

구분자를 찾았다는 가정하에 진행하게 된다면

 

 

 

Copper 이라는 결과를 얻을 있습니다

 

다음 단계로 고고

http://www.pythonchallenge.com/pc/hex/idiot2.html

 

 

 

 

 

 

 

 

무엇을 의미하는지부터 또다시 고민하게 된다

 

중요한 부분을 찾지 못해 다른 사람들의 풀이를 참고하였다

 

Http 프로토콜에 관해 알고 있어야지 이쓴 문제로 관련 개념을 같이 검색하면서 진행하였다

 

https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Content-Range

 

Content-Range

The Content-Range response HTTP header indicates where in a full body message a partial message belongs.

developer.mozilla.org

 

링크를 사용하면 표현 방법을 쉽게 있을 것이다

 

http://sihadan.tistory.com/38

 

 

 

Content-range 부분이 핵심 키워드로

 

부분을 키로 잡고 풀어 보도록 하겟다

 

전체 데이터에서 특정 부분만 뽑아내도록 프로그래밍하면 될것 같다

 

 

 

 

 

위와 같이 작성하여 얻은 결과로 invader 이라는 키워드를 얻었다 이걸 대입해보면

 

침입자라는 뜻을 가진 invader

 

위와 같은 말을 했는지 이해된다

 

http://www.pythonchallenge.com/pc/hex/invader.html

 

Yes! that's you!

 

출처: <http://www.pythonchallenge.com/pc/hex/invader.html>

 

들어가보면 문장만 있다 이것으로 뭘하라는거지?

 

일단 데이터 뽑는 부분을 끝까지 뽑아 보도록 하자

 

 

 

 

이렇게 하니 너무 오래 걸렸다 그래서 마지막 부분을 추출해보기로 하엿다

 

오랜 시간이 걸릴 것이라는 말을 위에서 했기에….

 

뒤에서 6789 바이트를 출력해보고자 한다

 

 

 

 

 

이게 뭔소리람????

 

이상한 문구를 만나버렸다

 

근데 가만히 뒤에서부터 읽어보면 the password...란다 일단 다시 출력해보자

 

 

 

풀다보니 이런 부부을 발견할 있었다

 

And it is hiding at 1152983631.

 

어떠한 파일이 1152983631 여기서부터 숨겨져 있고 그파일의 패스워드는 이름을 거꾸로 읽으면 되다는 같다

 

그럼 파일을 일단 추출해보자 암호를 말하는거 보니 zip 파일이 바이트 형태로 있을거라 살포시 추측해본다

 

그럼 저부분부터 하번 출력해보자

 

 

 

일단 짐작한대로 압축파일인 것을 pk PE 확인할 있었다

 

그럼 부분을 이제 추출해서 파일로 저장해보자

 

20_hidden_data_result.zip
0.23MB

 

이렇게 파일을 다운로드 받을 있었다

 

일단 비밀번호부터 적어두면 redavni : invader

 

압축 파일이 깨져있다는 말이다

 

왜그런가 생각해 봣더니

 

윗부분의 패스워드는 이름 반댇 문구가 바이트 단위로 데이터 끝자락에 있어서 그렇다

 

마디로 압축파일은 실제 데이터가 깨지지 않은 것이기 때문에 압축해제가 가능하다

 

라고 생각했는데 내가 생각히 못하는 부분이 있나본다 파일이 열리지 않는다 이부분을 해결해보자

 

 

 

 

이렇게 구할 있었다 내가 놓친 부분은 파일을 저장할 그냐 옵션을 W+ 주어서 파일이 깨진 거엿다

 

원래는 wb 혹은 wb+ 주어야 한다 바이너리 옵션을 주지 않아서 이다 젠장….

 

그래서 40 정도 삽질 결과 알게되엇다…..

 

 

level20.zip
0.23MB

 

파일에 비밀번호를 입력하고 안에 내용들을 살펴보면

 

yes! This is really level 21 in here.

And yes, After you solve it, you'll be in level 22!

 

Now for the level:

 

* We used to play this game when we were kids

* When I had no idea what to do, I looked backwards.

 

 

------readme.txt

 

 

package.pack
0.23MB

 

 

내용은 이렇다

 

21 문제는 웹이 아니라 압축 파일을 푸는 것이라고 한다

 

이렇게 20 클리어!!!!!

 

빌어먹을 파일 다운로드 코드를 삽입한다

 

import base64, httplib

login = base64.b64encode("butter:fly")

headers = {"Authorization" : "Basic %s" % (login)}

conn = httplib.HTTPConnection("www.pythonchallenge.com")

data_index = 1152983631#30202


def get_byte(start,end = 0):
	tmp = ""
	if end > 0:
		for data_index in range(start,end,1):
			headers.update({"Range" : "bytes=%s-%s" % (data_index,data_index+1)})# get 1byte
			conn.request("GET","/pc/hex/unreal.jpg","",headers)
			get_data = conn.getresponse().read()
			if get_data:
				tmp += get_data
				return tmp
			else:
				headers.update({"Range" : "bytes=%s-" % (start)})# get 1byte
				conn.request("GET","/pc/hex/unreal.jpg","",headers)
				get_data = conn.getresponse().read()
		f = open("level20.zip", "wb+")
		f.write(get_data)
		f.close()
	print "save file"
	print "end"

get_byte(data_index)
print "GG"

 

http://www.pythonchallenge.com/pc/hex/bin.html

 

 

 

 

 

 

 

 

 

와우… 이번에는 소스 코드에 재밌는 내용이 많다

 

 

 

From: leopold.moz@pythonchallenge.com	
	Subject: what do you mean by "open the attachment?"
	Mime-version: 1.0
	Content-type: Multipart/mixed; boundary="===============1295515792=="
	It is so much easier for you, youngsters.
	Maybe my computer is out of order.
	I have a real work to do and I must know what's inside!
	--===============1295515792==
	Content-type: audio/x-wav; name="indian.wav"
	Content-transfer-encoding: base64

출처: <http://www.pythonchallenge.com/pc/hex/bin.html>

 

 

첨부파일을 확인해보라

 

Base64 인코딩 문자열을 디코딩하여 indian.wav 라는 파일을 추출하라는 같다

 

추출해보니…

 

 

import base64


f = open("indian.wav.txt",'r')
data = base64.b64decode(f.read())
f.close()

f = open("indian.wav",'wb')
f.write(data)
f.close()


print data

 

indian.wav
0.11MB

 

들린다….

 

 

Sorry…?

 

미친거아니야?

 

음악 파일의 특징은 시각화가 가능하다는 것이다

 

이걸 채널별로 시각화 해보자

 

 

 

이렇게 작성해보니 안된다

 

조오오온나 모르겠다

 

그래서 다른 분들의 헬프를 받았다

 

다른 분들의 도움을 받은 결과

 

indian.wav
0.11MB

이게 처음에 코드로 만든 거고

 

 

result.wav
0.11MB

이게 다른 풀이를 보고 만든 파일이다

 

http://sihadan.tistory.com/37

https://the-python-challenge-solutions.hackingnote.com/level-19.html

 

풀이를 보고 문제는

 

에디안과 리틀 에디안은 서로 표시 형식이 반대인 것을 나타내는 문제로 풀이된다

 

Email 이라는 모듈을 새로 설치해서 활용하였으며 풀이보다는

 

새로운 모듈을 사용해봣다는 것에 의미를 둔다

 

그래서 결과로는 모듈 관련은 python 노트에 기록되어 있다

 

Next Address : http://www.pythonchallenge.com/pc/hex/idiot.html

 

이렇게 얻을 있고 부분에 들어가니

 

 

 

 

이러한 페이지가 있었으며 그냥 다음 페이지로 넘어가는 부분인거 같다

 

 

http://www.pythonchallenge.com/pc/hex/idiot2.html

 

 

다음 페이지이다

 

코드를 첨부한다

 

import base64, email, wave

txt = open("indian.wav.txt",'rb').read()

data = email.message_from_string(txt)

content = data.get_payload(0).get_payload(decode=True)


f = open("indian.wav",'wb')

f.write(content)

f.close()

w = wave.open("indian.wav","rb")

h = wave.open("result.wav","wb")

print(w.getnchannels())

print(w.getsampwidth())

print(w.getframerate())

h.setnchannels(w.getnchannels())

h.setsampwidth(w.getsampwidth()//2)

h.setframerate(w.getframerate()*2)

frames = w.readframes(w.getnframes())

wave.big_endiana = 1

h.writeframes(frames)

h.close()

 

 

http://www.pythonchallenge.com/pc/return/balloons.html

 

 

 

<html>
<head>
<title>can you tell the difference?</title>
<link rel="stylesheet" type="text/css" href="../style.css">
</head>
<body>
<br><br>
<center>
<font color="gold">
<img src="balloons.jpg" border="0"/>
<!-- it is more obvious that what you might think -->
</body>
</html>

 

출처: <http://www.pythonchallenge.com/pc/return/balloons.html>

 

 

어김없이 나오는 주석처리 ㅋㅋㅋㅋㅋㅋ

 

차이점을 알수 있냐는 문구가 타이틀이다

 

그럼 알수 있지 음영 차이자나!

 

can you tell the difference?

 

출처: <http://www.pythonchallenge.com/pc/return/balloons.html>

 

 

it is more obvious that what you might think

 

그것들을 모으면 아마 도움이 될거라는 같은데….

 

 

 

뭐가 명백하다는건지…..?

 

RGB 뒤에 다른 값이 있는거 알고 있나?

 

부분을 보라는거 같은데

 

삽질을 시작하자

 

삽질을 해본 결과

 

밝기 차이로 무언가 만들어 수는 없었다

 

 

검색해보니 별거 없었다

 

from PIL import Image, ImageDraw

im = Image.open('balloons.jpg')
rgb_im = im.convert('RGBA')
tmp = tmp1 = tmp2 = ""

print(rgb_im.size)
for x in range(0,rgb_im.size[0]):
	for y in range(0,rgb_im.size[1]):
		#print(str(x)+"/"+str(y)+"|"+str(x+375)+"/"+str(y))
		pixelRGB=rgb_im.getpixel((x,y))
		R = pixelRGB[0]
		G = pixelRGB[1]
		B = pixelRGB[2]
		brightness = sum([R,G,B])/3
		pixelRGB = rgb_im.getpixel((x+375,y))
		R = pixelRGB[0]
		G = pixelRGB[1]
		B = pixelRGB[2]
		brightness1 = sum([R,G,B])/3
		#print(str(brightness)+"|"+str(brightness1)+"|"+str(brightness-brightness1)+"|"+chr(brightness-brightness1))
		#print(chr(brightness)+"|"+chr(brightness1)+"|"+chr(brightness-brightness1)+"|")
		print("--------------------------")
		tmp+=chr(brightness)
		tmp1+=chr(brightness1)
		#tmp2+=chr(brightness-brightness1)
		print("---")
		print(tmp)
		print("---")
		print(tmp1)
		print("---")
		print(tmp2)
		print("---")

 

 

이렇게 해보았지만 모르겟다…. 확실히 있을 거라고….?

 

밝기

 

Brightness

 

이걸 URL 넣어 볼까?

 

http://www.pythonchallenge.com/pc/return/brightness.html

 

Jpg html 바꾸니

 

 

똑같은 이미지가 출력되는 다른 페이지가 있었다

 

부분을 풀어야 되는 같다 문제에 문제를 심어 놓는 방식인가보다

 

 

 

소스 내용은 이렇게 되어 있다

 

Mybe consider deltas.gz

 

파일을 이용하라는 같다 바로 다운 받아서 삽질해보자

 

일단 파일을 읽어 보았다

 

https://docs.python.org/2/library/gzip.html

 

텍스트 문서가 하나 있었고 내용은 위와 같다

 

 

파일을 바이트로 넣은 같은데 헤더 파일 PE 부분을 보면

 

89 50 4e 47 0d 0a 1a 0a

 

검색해보면

 

 

 

Png 이미지라는 것을 알았습니다

 

이미지의 데이터 값의 차이를 이용하라는 같습니다

 

비교 하는 중에 difflib 이런 모듈이 있어서 사용해보겠다

 

처음에 파싱을  spllit 해서 가져왓으나 마기지으로 갈수록 데이터가 "  " 공백 3개로 파싱하기 어려워

문자열 인덱싱을 사용하기로 하였다

 

import gzip,difflib

with gzip.open('deltas.gz', 'rb') as f:
	file_content = f.read()
	data1 = []
	data2 = []

for line in file_content.split("\n"):
	# print line
	# print line[:53]
	# print line[56:]
	# print str(len(line[:53]))+" / "+str(len(line[56:]))
	data1.append(str(line[:53].strip()))
	data2.append(str(line[56:].strip()))
	comp = list(difflib.Differ().compare(data1,data2))
	#print comp

img1 = open('18_1.png','wb')
img2 = open('18_2.png','wb')
img3 = open('18_3.png','wb')

for line in comp:
	byte = [chr(int(b,16)) for b in line[2:].split()]
	print byte

	if line[:1]=='+':
		for tmp in byte:
			img1.write(tmp)
		pass
	elif line[:1]=='-':
		for tmp in byte:
			img2.write(tmp)
		pass
	else:
		for tmp in byte:
			img3.write(tmp)
		pass

img1.close()
img2.close()
img3.close()

 

 

그렇게 해서 짜여진 코드는 이렇다

 

[chr(int(b,16)) for b in line[2:].split()]

Python Challenge! 18 What's the difference?!

참고동영상

 

 

대부분 유투브 동영상의 힘을 빌렸지만 파이썬에서 이렇게 [] 안에서 사용된다는 것은 처음 알았다

 

16진수로 바꾸고 값을 문자로 변환해서 파일에 쓰는 것으로 파일에 데이터를 저장할 있었다

 

 

 

 

나온 결과 값은 이걸로

 

대입하면

 

http://www.pythonchallenge.com/pc/hex/bin.html

 

URL 로그인 있다

http://www.pythonchallenge.com/pc/return/romance.html

 

 

 

 

 

화면부터 이미지 두개… ㅡㅡ 심상치 않다

 

 

 

보라는 거지??

 

Title 먹는거냐는데? 아무래도 브라우져 쿠키를 말하는 같다

http://www.pythonchallenge.com/pc/return/cookies.jpg

 

쿠키는 없는뎅…..ㅠㅠㅠㅠㅠㅠㅠㅠㅠㅠ

 

Url 클릭하니 같은 화면이 나왓다 무슨 의미일까?

 

http://www.pythonchallenge.com/pc/return/cookies.html

 

오예 url 하나 찾았고

 

 

http://www.pythonchallenge.com/pc/return/chocolate.html

 

 

 

 

뭔가 계속 반복되는거같다

http://www.pythonchallenge.com/pc/return/play.html

 

 

 

 

드디어 쿠키를 찾았다….

 

삽질하고 있었는데

 

import re,urllib
#insert url *.html
def find_img_src(url):
html = urllib.urlopen(url).read().split()
for word in html:
  url = "http://huge:file@www.pythonchallenge.com/pc/return/"+str(word)+".jpg"
  print(url)
  word = re.findall(r'\ssrc="([^"]+)"', urllib.urlopen(url).read())
  word = ' '.join(word)
  if word!="":
    return "http://huge:file@www.pythonchallenge.com/pc/return/"+str(word)
#insert url *.jpg
def find_word(url):
  url = url[:-3]
  html = urllib.urlopen(url+"html").read().split()
  for word in html:
    url = "http://huge:file@www.pythonchallenge.com/pc/return/"+str(word)
    print(url)
    if not("404" in urllib.urlopen(url).read()):
      return url[:-3]+"html"
  print (end")
  url = "http://huge:file@www.pythonchallenge.com/pc/return/romance.html"

while 1:
  print(url)
  url=find_img_src(url)
  print(url)
  url = find_word(url)
pass

 

 

 

이렇게 코딩 짜면서……

 

부분은쓸모 없게 되었다

 

http://www.pythonchallenge.com/pc/return/cookies.jpg

 

링크에서 쿠키가 나왓으니 다시 삽질을 시작해보자

 

 

쿠키가 아니네…..wiki 쿠키 값이었다….

 

 

다시 원점으로 돌아와서 생각해보자

Cookie 있게 위해서는 html 로는 javascript 있지 않는 이상 set-cookie 있을 없다

 

그러므로 php 파일일 확률이 매우 높은데

 

왼쪽 하단 이미지를 보면 이전 단계인 것을 알수 있다

 

4단계로 가보자

 

http://www.pythonchallenge.com/pc/def/linkedlist.php

 

follow the chain

 

www.pythonchallenge.com

 

you+should+have+followed+busynothing…

 

 

 

쿠키 값을 확인 있었다

 

그렇다면 진행해보자

 

http://www.pythonchallenge.com/pc/def/linkedlist.php?busynothing=

 

 

다음 코드를 구할 있다 이걸로 게속 반복하는 코드를 보자

 

 

 

거나 삽질하고 있는데 안나온다

 

뭔가 다른게 있나보다

 

역시 쿠키값을 제대로 봐야하나??

 

소스코드를 수정했다

import urllib2,re,requests
url = url_tmp = "http://www.pythonchallenge.com/pc/def/linkedlist.php?busynothing="
code = ""
while 1:
	request = urllib2.Request(url)
	html = urllib2.urlopen(request).read()
	r = requests.get(url)
	try:
		print r.cookies['info']
		break
	except:
		pass
	if re.findall("[0-9]",html)=="":
		break
	code = "".join(re.findall("[0-9]",html))
	url=url_tmp+code
	print html
	pass

 

이렇게 해도 쿠키 값은 없었다…

근데 자꾸 문제가 특정 구간을 반복한다는 것이다

 

 

그렇다면 처음 시작하는 값이 잘못 되었음을 의심해본다

 

원래 단계에서는 처음 초기값은 무엇이었을까?

 

http://www.pythonchallenge.com/pc/def/linkedlist.php?nothing=12345

 

http://www.pythonchallenge.com/pc/def/linkedlist.php?nothing=12345

 

www.pythonchallenge.com

 

12345 였다

 

그러면 여기서도 값을 12345 해서 시작해보자

 

import urllib2,re,requests

url = url_tmp = "http://www.pythonchallenge.com/pc/def/linkedlist.php?busynothing=12345"
code = ""

while 1:
    request = urllib2.Request(url)
    html = urllib2.urlopen(request).read()
    r = requests.get(url)
    try:
        print r.cookies['info']
        break
    except:
        pass
    

    if re.findall("[0-9]",html)=="":
        break
    
    code = "".join(re.findall("[0-9]",html))
    
    url=url_tmp+code
    print html
    pass

 

이렇게 시작해보았다

그랫더니

 

오잉?

 

B 하나만 출력하고 멈추었다

 

그렇다면 쿠키값이 없을때까지 해보면 될거 같다

 

 

 

쿠키 값이 있는 것도 확인할 있었다

 

 

you+should+have+followed+busynothing…

 

숫자 없이 시작할때는 쿠키가 없었는데 말이다

 

젠장……. 문구에도 초기값은 없다

 

괜한 삽질이었다  놀아난 느낌에 기분이 별로 좋지 않지만 코드를 바꿔서 다시 진행해 보았다

 

이렇게 처음 부분부터 다름을 화인 있었다

 

If you came here from level 4 - go back!<br>You should follow the obvious chain...<br><br>and the next busynothing is 44827

 

진행해보자

 

http://www.pythonchallenge.com/pc/def/linkedlist.php?busynothing=1234

 

http://www.pythonchallenge.com/pc/def/linkedlist.php?busynothing=1234

 

www.pythonchallenge.com

 

신기하게 1234 입력해도 페이지가 나왓다 아무래도 입력값을 기반으로 값을 랜덤으로 돌리다가 정답을 뿌려주나 보다 페이지에 쿠키는 없었다

 

내가 코드에 문제가 있었다

 

 

If you came here from level 4 - go back!<br>You should follow the obvious chain...<br><br>and the next busynothing is 44827

 

여기서 숫자만 뽑다 보니까 level 4 여기서  숫자 4 뽑아 버리는 바람에 44827 되어 답을 찾지 못하고 계속 순환하는 문제가 있었던 같다

그리고 계속 디버깅을 하면서 cookies 부분의 info 값을 가져오던데 가져오나 찾아보니 내가 코드를 병신처럼 놓았다….

 

 

import urllib2,re,requests
url = "http://www.pythonchallenge.com/pc/def/linkedlist.php?busynothing="
code = "12345"
result = []
while 1:
	request = urllib2.Request(url+code)
	html = urllib2.urlopen(request).read()
	r = requests.get(url+code)
	next_num = html.split(" ")[len(html.split(" "))-1]
	try:
		cookies = r.cookies['info']
	except:
		if ((next_num=="") or (cookies=="")):
			tmp = ""
			for item in result:
				tmp+=item
				print tmp
			break
		else:
			result.append(cookies)
			code = next_num
			print url + " / " +cookies + " / "+html

 

코드를 위와 같이 수정하고 다시 보았다

 

 

쿠키를 모아본 결과는

 

 

BZh91AY%26SY%94%3A%E2I%00%00%21%19%80P%81%11%00%AFg%9E%A0+%00hE%3DM%B5%23%D0%D4%D1%E2%8D%06%A9%FA%26S%D4%D3%21%A1%EAi7h%9B%9A%2B%BF%60%22%C5WX%E1%ADL%80%E8V%3C%C6%A8%DBH%2632%18%A8x%01%08%21%8DS%0B%C8%AF%96KO%CA2%B0%F1%BD%1Du%A0%86%05%92s%B0%92%C4Bc%F1w%24S%85%09%09C%AE%24%90

 

BZh91AY%26SY%94%3A%E2I%00%00%21%19%80P%81%11%00%AFg%9E%A0+%00hE%3DM%B5%23%D0%D4%D1%E2%8D%06%A9%FA%26S%D4%D3%21%A1%EAi7h%9B%9A%2B%BF%60%22%C5WX%E1%ADL%80%E8V%3C%C6%A8%DBH%2632%18%A8x%01%08%21%8DS%0B%C8%AF%96KO%CA2%B0%F1%BD%1Du%A0%86%05%92s%B0%92%C4Bc%F1w%24S%85%09%09C%AE%24%90

이거다….. 이걸 어떻게 지지고 볶을까?

 

일단 % 0x 바꿔줘야 같다

그리고 bz 되어있는거보니까 bz2 모듈을 쓰라는 같은데

 

한번 해보자

 

 

https://stackoverflow.com/questions/28431359/how-to-decode-a-url-encoded-string-in-python

 

How to decode a (doubly) 'url-encoded' string in python

Tried decoding a url-encoded string in the following way some_string = 'FireShot3%2B%25282%2529.png' import urllib res = urllib.unquote(some_string).decode() res u'FireShot3+%282%29.png' Original

stackoverflow.com

 

Pythom 2.7 에서는 %26 & 파싱해주는 모듈이 따로 없어서 찾느라 먹었다 ㅜㅜㅜ

 

점점 푸는 시간도 느려지는 같다

 

값은 가져왓는데 복호화가 안되는 같았다…..

 

'BZh91AY&SY\x94:\xe2I\x00\x00!\x19\x80P\x81\x11\x00\xafg\x9e\xa0 \x00hE=M\xb5#\xd0\xd4\xd1\xe2\x8d\x06\xa9\xfa&S\xd4\xd3!\xa1\xeai7h\x9b\x9a+\xbf`"\xc5WX\xe1\xadL\x80\xe8V<\xc6\xa8\xdbH&32\x18\xa8x\x01\x08!\x8dS\x0b\xc8\xaf\x96KO\xca2\xb0\xf1\xbd\x1du\xa0\x86\x05\x92s\xb0\x92\xc4Bc\xf1w$S\x85\t\tC\xae$\x90'

 

 

#'BZh91AY&SY\x94:\xe2I\x00\x00!\x19\x80P\x81\x11\x00\xafg\x9e\xa0+\x00hE=M\xb5#\xd0\xd4\xd1\xe2\x8d\x06\xa9\xfa&S\xd4\xd3!\xa1\xeai7h\x9b\x9a+\xbf`"\xc5WX\xe1\xadL\x80\xe8V<\xc6\xa8\xdbH&32\x18\xa8x\x01\x08!\x8dS\x0b\xc8\xaf\x96KO\xca2\xb0\xf1\xbd\x1du\xa0\x86\x05\x92s\xb0\x92\xc4Bc\xf1w$S\x85\t\tC\xae$\x90' - replace + 제거하지 않은 경우

 

#'BZh91AY&SY\x94:\xe2I\x00\x00!\x19\x80P\x81\x11\x00\xafg\x9e\xa0 \x00hE=M\xb5#\xd0\xd4\xd1\xe2\x8d\x06\xa9\xfa&S\xd4\xd3!\xa1\xeai7h\x9b\x9a+\xbf`"\xc5WX\xe1\xadL\x80\xe8V<\xc6\xa8\xdbH&32\x18\xa8x\x01\x08!\x8dS\x0b\xc8\xaf\x96KO\xca2\xb0\xf1\xbd\x1du\xa0\x86\x05\x92s\xb0\x92\xc4Bc\xf1w$S\x85\t\tC\xae$\x90' - replace + 제거한 경우

 

처음에 생각한대로 알고리즘을 짜니 복호화 에러가 생겻다

 

그럴까 고민해보았는데 이해가 되지 않아서 관련 풀이들을 참고해보기로 했다

 

확인해보니 복호화 과정에서 문자열을 더하는 + 인해 공백이 없어지고 서로 더해져서 이부분이

 

복호화 과정에서 문제를 일으켯다 그래서 + 부분을

 

조금 살펴보니 문자열로 처리 하였을 + 부분 필터링이 두개인데 하나만 되는 것을 발견할 있었다

 

http://www.chengxuyuans.com/Python/64365.html

https://the-python-challenge-solutions.hackingnote.com/level-17.html

여러 풀이들을 참조한 결과 나만 살짝 이상한 것을 느낄 있었다

 

부분은 차후 그런지 2 코딩 간결화 최적화 작업을 진행하면서 조금 확인해보고자 한다

import urllib2,re,requests,bz2,urllib,os

url = "http://www.pythonchallenge.com/pc/def/linkedlist.php?busynothing="

code = "12345"

cookies = ""

tmp = 'BZh91AY&SY\x94:\xe2I\x00\x00!\x19\x80P\x81\x11\x00\xafg\x9e\xa0+\x00hE=M\xb5#\xd0\xd4\xd1\xe2\x8d\x06\xa9\xfa&S\xd4\xd3!\xa1\xeai7h\x9b\x9a+\xbf`"\xc5WX\xe1\xadL\x80\xe8V<\xc6\xa8\xdbH&32\x18\xa8x\x01\x08!\x8dS\x0b\xc8\xaf\x96KO\xca2\xb0\xf1\xbd\x1du\xa0\x86\x05\x92s\xb0\x92\xc4Bc\xf1w$S\x85\t\tC\xae$\x90'

#'BZh91AY&SY\x94:\xe2I\x00\x00!\x19\x80P\x81\x11\x00\xafg\x9e\xa0 \x00hE=M\xb5#\xd0\xd4\xd1\xe2\x8d\x06\xa9\xfa&S\xd4\xd3!\xa1\xeai7h\x9b\x9a+\xbf`"\xc5WX\xe1\xadL\x80\xe8V<\xc6\xa8\xdbH&32\x18\xa8x\x01\x08!\x8dS\x0b\xc8\xaf\x96KO\xca2\xb0\xf1\xbd\x1du\xa0\x86\x05\x92s\xb0\x92\xc4Bc\xf1w$S\x85\t\tC\xae$\x90'

#'BZh91AY&SY\x94:\xe2I\x00\x00!\x19\x80P\x81\x11\x00\xafg\x9e\xa0+\x00hE=M\xb5#\xd0\xd4\xd1\xe2\x8d\x06\xa9\xfa&S\xd4\xd3!\xa1\xeai7h\x9b\x9a+\xbf`"\xc5WX\xe1\xadL\x80\xe8V<\xc6\xa8\xdbH&32\x18\xa8x\x01\x08!\x8dS\x0b\xc8\xaf\x96KO\xca2\xb0\xf1\xbd\x1du\xa0\x86\x05\x92s\xb0\x92\xc4Bc\xf1w$S\x85\t\tC\xae$\x90'

#'BZh91AY&SY\x94:\xe2I\x00\x00!\x19\x80P\x81\x11\x00\xafg\x9e\xa0+\x00hE=M\xb5#\xd0\xd4\xd1\xe2\x8d\x06\xa9\xfa&S\xd4\xd3!\xa1\xeai7h\x9b\x9a+\xbf`"\xc5WX\xe1\xadL\x80\xe8V<\xc6\xa8\xdbH&32\x18\xa8x\x01\x08!\x8dS\x0b\xc8\xaf\x96KO\xca2\xb0\xf1\xbd\x1du\xa0\x86\x05\x92s\xb0\x92\xc4Bc\xf1w$S\x85\t\tC\xae$\x90'

#'BZh91AY&SY\x94:\xe2I\x00\x00!\x19\x80P\x81\x11\x00\xafg\x9e\xa0 \x00hE=M\xb5#\xd0\xd4\xd1\xe2\x8d\x06\xa9\xfa&S\xd4\xd3!\xa1\xeai7h\x9b\x9a+\xbf`"\xc5WX\xe1\xadL\x80\xe8V<\xc6\xa8\xdbH&32\x18\xa8x\x01\x08!\x8dS\x0b\xc8\xaf\x96KO\xca2\xb0\xf1\xbd\x1du\xa0\x86\x05\x92s\xb0\x92\xc4Bc\xf1w$S\x85\t\tC\xae$\x90'

urllib.unquote_plus(tmp)

#print bz2.decompress("".join(tmp.replace("+"," ")))

while 1:

	request = urllib2.Request(url+code)
	html = urllib2.urlopen(request).read()
	r = requests.get((url+code))
	next_num = html.split(" ")[len(html.split(" "))-1]

	try:
		cookies += r.cookies['info']
		if cookies=="+":
			break
		code = next_num
		print cookies+" / "+code
	except:
		result = urllib.unquote(urllib.unquote("".join(cookies.replace("+"," "))))
		print result
		print bz2.decompress(result)
		break

 

코드의 결과물이다

 

is it the 26th already? call his father and inform him that "the flowers are on their way". he'll understand.

 

 

결과로 얻은 문자열은 위와 같다

 

벌써 26번째냐고 그의 아버지에게 알려라 곳들은 그들 중에 있을 거라고 그러면 그는 이해할거라고

 

그러면 그의 아버지를 검색해보니

 

 

 

 

Leopold 라는 것을 있었다 그러면 이제 그에게 알려야 하는데

 

어떻게 알리나 고민해 보았더니 나는 전화번호부를 가지고 있었다

 

전화를 걸어 나온 결과는 이렇다

 

 

이동해보자

 

 

 

혹시 모르니 소스코드도 확인해보았다

 

http://www.pythonchallenge.com/pc//stuff/violin.php

 

 

 

이러한 화면을 있다... 뭘보라는거지? 뭔가 눈빛이 무서운데 ㅋㅋㅋㅋ

 

이럴땐 소스 코드를 보자

 

<html>
<head>
<title>it's me. what do you want?</title>
<link rel="stylesheet" type="text/css" href="../style.css">
</head>
<body>
<br><br>
<center><font color="gold">
<img src="leopold.jpg" border="0"/>
<br><br>
</font>
</body>
</html>

출처: <http://www.pythonchallenge.com/pc//stuff/violin.php>

 

 

 

무엇을 원하냐고 한다

 

나는 꽃이 그들 중에 있다는 것을 이야기하고자 한다

 

쿠키 문제이므로 쿠키를 살펴보자

 

오잉?

 

아무 값이 없다….뭐지?

 

 

하나만 있는데...더하라고?

 

Php이므로 응답을 할수 있으니까 쿠키 info 심어서 요청을 보내보자

 

그래도 할말이 무언인지 물어보니까 페이지가

 

print "------------------------------------"

cookie = {'info': 'the flowers are on their way'}

r = requests.get('http://www.pythonchallenge.com/pc/stuff/violin.php', cookies=cookie)

print r.text

 

실행하면 결과가 나온다

 

<html>

<head>

<title>it's me. what do you want?</title>

<link rel="stylesheet" type="text/css" href="../style.css">

</head>

<body>

<br><br>

<center><font color="gold">

<img src="leopold.jpg" border="0"/>

<br><br>

oh well, don't you dare to forget the balloons.</font>

</body>
</html>

 

아까와는 없던 문구가 생겼다...대박

 

oh well, don't you dare to forget the balloons.

 

잊지 말란다 ㅋㅋㅋㅋㅋ

 

http://www.pythonchallenge.com/pc/return/balloons.html

 

다음 단게로 가는 문이다!!!! 이번에는 정말 길고 힘들었던 삽질이었다 ㅜㅜㅜㅜㅜ

 

 

http://www.pythonchallenge.com/pc/return/mozart.html

 

 

level 16

 

<html>
<head>
<title>let me get this straight</title>
<link rel="stylesheet" type="text/css" href="../style.css">
</head>
<body>
<br><center>
<img src="mozart.gif"><br>
</body>
</html>

소스코드이다

 

색깔있는 부분만 모아 보라는 같다

 

부분의 RGB 값을 뽑아보자

 

 

코드를 출력해보니

 

102 라는 값이 많이 나온다

 

값을 키값으로 잡아야겠다

 

그러면 102 값을 빼고 파일을 만들고 그부분에 채워넣고 출력해보겠다

 

 

음… 일단 코딩은 나누어지는 같다 새로운 에디터라 적응하면서 문제를 풀도록 하겠다

 

 

 

보다 정확하게 하기 위하여 RGB 값을 이렇게 정의했다

 

255,0,255

 

 

빼보니 답은 아닌거 같다 오른쪽에 똑같은 이미지에서 보라부분을 뺏더니

 

동일한 부분이 남는 것을 있었다 부분을 조금 파보고자

 

양옆의 점같은 부분도 빼보고자 한다

 

별짓을 했는데 모르겟다 답도 안나온다 그래서 방법을 조금 변경하기로 햇다

 

 

처음에 내가 생각한대로 해보았으나 답이 나오지 않았고 계속 삽질한 결과

 

구현에 어려움이 있었다

 

다음번에 다시 나만의 방법으로 풀어보는 것을 고려하고

 

이번에는 해외 풀이자의 강의를 통해 풀어보며 내용을 이해하는데 집중했다

 

offset

 

imagechops.offset(image,xoffset,yoffset) == image

 

이번 문제에서는 동영상의 도움을 좀 많이 받았다

 

offset의 개념에 대해 알아야 했으며

 

imagechops 모듈에 대해서도 알아야 했다

 

그래서 소스 코드에 각 줄마다 코멘트를 달아 놓았다

 

근데 하나 궁금한게 있다 왜 offset 값에 -를 해야 하는 걸까?

 

이건 내가 알아내야 할 것 같다

 

 

 

 

 

참고 URL

 

http://effbot.org/imagingbook/imagechops.htm

 

The ImageChops Module

The ImageChops module contains a number of arithmetical image operations, called channel operations (“chops”). These can be used for various purposes, including special effects, image compositions, algorithmic painting, and more. For more pre-made oper

effbot.org

http://code.nabla.net/doc/PIL/api/PIL/PIL.ImageChops.html

 

PIL.ImageChops — PIL documentation

add(image1, image2[, scale, offset]) Add two images

code.nabla.net

http://effbot.org/imagingbook/image.htm

 

The Image Module

The Image module provides a class with the same name which is used to represent a PIL image. The module also provides a number of factory functions, including functions to load images from files, and to create new images. The following script loads an imag

effbot.org

https://pillow.readthedocs.io/en/3.0.0/_modules/PIL/ImageChops.html

 

PIL.ImageChops — Pillow (PIL Fork) 2.6.1 documentation

© Copyright 1995-2015, Fredrik Lundh and Contributors, Alex Clark and Contributors. Revision 0177ccea.

pillow.readthedocs.io

 

참고 영상

https://www.youtube.com/watch?v=k-bjhrnCSKo

 

 

 

코드가 주석이 많아 더럽다

 

 

from PIL import Image, ImageDraw,ImageChops
import subprocess, os

im = Image.open('mozart.gif')
width, height = im.size
#print im.info

offset_in = '\xc3'

frame = 0
#for y in range(1):
for y in range(height):
    crop_box =  (0 , y, width, y+1) #new make 1 line image
    row = im.crop(crop_box) #crop to image
    #row.show() #can see croped 1 line image
    #print repr(row.tobytes()) #print method change tostrig ==> tobyte
    row_byte = row.tobytes(); #save byte 
    #for i in range(len(row_byte)): # 1 line image proceed
    #    character = row_byte[i] #read 1 byte
    #    if character == row_byte[i+1] and character == row_byte[i+2] and character == row_byte[i+3]:
    #        #if same 3 pixel print byte value
    #        print repr(character)
    offset = row_byte.index(offset_in) - 1 #get index to start index
    row = ImageChops.offset(row, -offset) #offset split
    im.paste(row,crop_box) #using offset to image pink area replace
    im.save('frame'+str(frame).zfill(3)+".png") #file name upcount format
    frame+=1 #file name up count
    #file save

#make animation gif file
#using window
os.chdir(os.path.realpath(os.path.dirname(__file__))) #change dir
os.system('del animation.gif') #if have gif file then del
os.system("ffmpeg -i frame%03d.png animation.gif") #make animation gif file
os.system('del frame*.png') #del file

#using linux
#print subprocess.check_output('convert -delay 1 -loop 0 frame*.png animated.gif'.split()) # make anmation gif file
#im.show() #show file
im.close() #close file
os.system('animation.gif') #open file

 

코드는 이렇다

 

결과로

 

 

 

 

이걸로 다음 페이지 고고

http://www.pythonchallenge.com/pc/return/uzi.html

 

 

 

 

<html>	
	<head>
	<title>whom?</title>
	<link rel="stylesheet" type="text/css" href="../style.css">
	</head>
	<body>
	<br><center>
	<!-- he ain't the youngest, he is the second -->
	<img src="screen15.jpg"><br>
	</body>
	</html>
	<!-- todo: buy flowers for tomorrow -->

 

출처: <http://www.pythonchallenge.com/pc/return/uzi.html>

 

가장 젋은 것은 아니지만 그는 두번째입니다 라는데 두번째로 년도를 구하라는 건가?

 

내일은 꽃을 산다고 했다

 

도데체 어떻게 해야되지? 새로운 문제를 볼때마다 드는 생각이다

 

일단 구멍뚤린 년도부터 맞춰야 겟다

 

from datetime import date
import datetime
import calendar

#january 26-day find year
for x in range(1006,1996,10):
	my_date = datetime.date(x,01,26)
	if calendar.day_name[my_date.weekday()]=="Monday":
		print "find : "+str(x)
pass

 

 

1846 년도인걸 알수 있다

 

풀면서 본거지만

 

 

 

 

부분도 있는데 무얼 의미하는지 모르겠당…..

 

아하, 2월이 윤년 29일까지 있다

 

Calender.isleap() 통해서  윤년 우무를 확인할 있다

 

Title whom 이다 누구냐고 묻는거 같은데

 

일단 내일은 꽃을 사야 한다니까 좋은일이나 나쁜일이 있는 날인거같다

 

결혼 기념일 아니면 기일이거나 그래서 날짜를 검색해보자

 

상대를 찾으라는 같다

 

https://www.google.co.kr/search?newwindow=1&rlz=1C1NHXL_koKR700KR700&q=1846-01-27&oq=1846-01-27&gs_l=psy-ab.3...7322.14922.0.15497.11.10.0.0.0.0.204.1117.0j6j1.7.0....0...1.1.64.psy-ab..4.3.485...35i39k1.XFlXf8i7AnE

 

찾은 같다

 

죽은 사람을 위해 꽃을 사야 한다는 같다

 

 

답이 아니다….왜그런가 햇더니 윤년 계산을 빠트렷다

 

매번 연도에 따라 일수가 달라진다는 것을 고려하자

 

from datetime import date
import datetime
import calendar

#january 26-day find year
for x in range(1006,1996,10):
	#print my_date.weekday()
	if (calendar.weekday(x,1,26)==0 and calendar.isleap(x)):
		print "find : "+str(x)
	pass

 

이렇게 짜서

나온 리스트는

 

 

 

여기서 두번째는 1756년이다

 

 

 

바로 모차르트가 나오는 확인할 있다

http://www.pythonchallenge.com/pc/return/mozart.html

 

이렇게 답을 얻을 있다

 

 

 

 

 

http://www.pythonchallenge.com/pc/return/cat.html

 

 

 

 

 

이미지는 역시 별거 없다

 

<html>
<title>uzi</title>
<link rel="stylesheet" type="text/css" href="../style.css">
<body>
<center>
<br>
<font color="gold" size="+1">
and its name is <b>uzi</b>. you'll hear from him later.
<br><br><img src="uzi.jpg" width="640" height="480"/>
</body>
</html>

출처: <http://www.pythonchallenge.com/pc/return/cat.html>

 

Uzi 키워드로 힌트를 해석하면

고양이 이름은 uzi 이고 나중에 듣게 이야기를 듣게 된다고 한다

 

 

알겠으니까 넘어가자

 

Uzi 이게 키워드다

 

http://www.pythonchallenge.com/pc/return/uzi.html

 

다음으로 넘어갈 있었다

 

그냥 쉬어가기 코너인 듯

 

 

 

 

+ Recent posts