RFC2047: Message Header Ext for Non-ASCII

CSS Design Korean 게시판을 보다가 vBulletin 을 통해 발송된 메일의 문제점 관련된 글을 보게되었습니다… mail header 에 ASCII 가 아닌 글자가 들어가게 될 경우엔 오래된 시스템에서 문제를 일으킬 수도 있기 때문에… 한글과 같은 ASCII 영역 밖의 글자들을 사용하고 싶은 경우엔 RFC2047 에 따라 인코딩을 해줘야 합니다…

해당 쓰레드: http://forum.standardmag.org/viewtopic.php?id=189
Continue reading RFC2047: Message Header Ext for Non-ASCII

내가 사용하는 무료 프로그램들…

요 근래 사용가능한 오픈소스 & 프리웨어 & 에드웨어 들이 늘면서 상용 프로그램들을 깔지 않고서도 별로 불편한게 없는 듯 싶다. 뭐 하튼간에 개인적으로 포멧할 때마다 어떤 걸 안깔았더라 하면서 고민하는 일을 줄이게 위해 정리를 -_-!!
Continue reading 내가 사용하는 무료 프로그램들…

느린 SFTP 는 이제 안녕~

얼마 전 proftpd 패치를 한 김에 … [wikipedia:SFTP] (ftp over ssh) 대신 [wikipedia:FTPS] (ftp over ssl) 를 사용하기 위해 이래저래 삽질을 조금 해봤다… 뭐 결론은 파일질라에서 -_-;; passive 로 안하면 디렉토리 리스트를 못얻어오고 에러가 나는게 문제였지만… 하튼!!
[wikipedia:SFTP] 의 경우엔 라인이 꽤 좋음에도 불구하고 200~300K 정도가 나올가 말까 하는 극악한 속도를 자랑했었는데… proftpd + mod_tls 조합으로 ftps 를 사용해보니 무선랜 환경에서도 500~600K 정도는 나오는게 데스크탑에서는 훨씬 빠를 듯 싶다… (테스트해보니 1.6MB 이상도 나오는거 보면 [wikipedia:SFTP] 랑 속도비교는 무의미 할 듯)
[wikipedia:FTPS] 의 경우엔 이어받기 라던지… 예전 ftp 에서 지원하던 모든 것들을 지원하기 때문에 굳이 다시 [wikipedia:SFTP] 를 쓸 일은 없을 듯… 하튼 이제 느린 [wikipedia:SFTP] 는 안녕~
proftpd 의 옵션 중 TLSrequired 가 on 이면 data 채널과 control 채널 모두 암호화를 해서 전송을 하고 ctrl 이면 data 는 암호화 되지 않은 상태로 전송이 된다고 하는데… off 인 경우는 tls 를 사용하는지 마는지 궁금해졌다 -_-; sniffit 을 이용해서 21 번 포트로 들어오는 데이타를 스니핑 해보니… off 여도 확실히 암호화 되서 전송되는 거 같기는 해서 안심!

proftpd: codeconv module

사실 unfix 는 나 혼자 쓰는 서버가 아니고… 파일이름등을 unicode 로 관리할 경우 ms 윈도우와의 궁합이 그다지 좋지 않기 때문에… utf-8 환경을 갖추는 게 망설여지는게 사실이었다.
얼마 전 젠투 한국 사용자그룹의 유리님의 개인 portage-overlay 리스트를 보다가 proftpd 의 charset conversion 패치를 발견했다. 원 출처는 일본 쪽인 듯 싶은데, 이 패치를 적용하면 client 에서 사용하는 charset 과 server에서 사용하는 charset 을 설정하는게 가능해진다.

만약 중간에 charset conversion 에 실패했다거나 한 경우 어떻게 처리를 하나 봤더니, 변환에 실패한 글자를 ‘?’ 로 바꿔버리고 있었다. out_buffer size 를 in_buffer size 의 세 배 크기로 할당하고 중간에 에러가 발생하면 무조건 변환이 실패한 것으로 생각하기 때문에 한 글자를 표현하는데 3바이트보다 더 많은 바이트 수가 필요하다면 (ucs2 로는 표현 못하는 글자를 사용하는 경우), 버퍼 오버플로의 희생양이 될 수도 있을 듯 싶다. 그래도 원하는 코드를 삽입하는 건 힘들고 그저 segmentation error 를 부를 뿐이겠지만 찝찝한 건 사실이므로 에러가 발생할 경우 errno 를 참고하도록 패치를 해야겠다.

근데 실제 적용을 해보니 Directory 나 .ftpaccess 를 통한 지역 설정이 허용되지 않는다. 내가 사용하는 폴더들에 한해서 저 패치의 영향을 받게 하는게 목적이었기 때문에 결국 패치를 해버렸다. proftpd 개발자 문서는 서버가 다운되었었는지 참고를 할 수가 없었고, 그나마 미러링 된 곳도 찾을 수가 없어서 한참 헤매긴 했지만!! 결국!! 내가 원하는 데로 패치 성공 -_-v

mod_autoindex 도 몇 일전에 charset 을 설정해줄 수 있도록 패치했고, 그 외에는 이미 다 준비가 되어 있었기 때문에 누군가 mod_autoindex 의 새로운 테마만 만들어준다면 바로 utf-8 환경으로 넘어갈 수 있을 듯 싶다.

FTP 관련해선 RFC2640 에 있는 것을 구현하는 것이 옳다고 생각하지만 중간 단계로써 mod_codeconv 도 나름의 의미가 있을 듯 싶다.

p.s) 위의 사이트에 나와있는 메일 주소로 패치파일을 보내주려 했지만 메일주소가 죽어있네요.

php: mytrz-dviewer

예전에 수정해서 이쁘게 만들어 사용하고 있는 mod_autoindex 의 경우에는 아파치의 모듈이기 때문에 관리가 활성화 시켜주지 않으면 사용할 수 없는 단점이 있어서… 누군가에게 권하기도 그렇고… 수정하기도 매우 어려웠습니다…
심심하던 차에 아는 사람 부탁 겸… 해서 directory viewer 를 php 로 다시 작성했습니다… template 엔진으로 template_ 만 써보다가 smarty 를 처음 써봤는데 template_ 이 좀 더 쓰기 쉬운 듯 하기는 하지만… smarty 도 그런데로 쓸만한 것 같습니다…
[php:realpath] 란 함수를 사용해서 내가 지정해놓은 디렉토리 루트 밖으로는 나갈 수 없도록 해놓았고 수많은 버그가 있겠지만… 하튼 동작은 합니다…

데모:
http://mytears.org/tmp/dir/
다운로드 url:
http://mytears.org/resources/distfiles/directory-viewer-1.1.1.tar.gz
개발버젼:
http://trac.unfix.net/browser/mytrz-dviewer
라이센스: BSD License

참고로 템플릿 엔진은 smarty 를 쓰고 있는데, 제 서버에는 smarty 가 /usr/lib/php 밑에 설치되어 있기 때문에 따로 더 필요가 없었는데… 서버에 smarty 가 이미 깔려있지 않은 분들은 smarty 를 받아다가 풀어주는 센스가 필요합니다…
p.s) 혹시나 가져다가 새로운 디자인으로 고치신 분이 계시면 skin 관련해서 feedback 좀 부탁드리겠습니다 🙂
Change Log:
2006/8/29
1. 개인 Repository 를 하나로 통합하면서 svn 경로가 수정됨
2. 웹에서 svn 을 둘러보기 위한 툴을 trac 으로 변경
3. 프로젝트 이름을 mytrz-dviewer 로 변경
2006/06/27
1. fancy size bug 수정
2. 1.1.1 버젼 릴리즈
2005/08/24
1. 스킨에서 경로도 표시가능하게 수정
2. taeyoung 스킨 추가
3. web_basedir 에서는 Parent Direcory 링크를 보여주지 않게 고침
4. 1.1 버젼 릴리즈
2005/08/17
1. kirrie 님의 스킨 추가
2. kukie 스킨 업데이트 (I.E 호환성이 더 좋아짐)
2005/08/13
1. Filename / Size / Modification Time 으로 역순 정렬이 가능해짐 (내림차순)
2. 설정 가능한 변수들을 config.php 로 빼냄
3. 숨긴 파일( 파일 이름이 “.” 으로 시작하는 파일) 을 보여줄지 말지 설정 가능해짐
4. BSD License 로 정하고 소스에 라이센스를 명시
5. Encoding 도 설정가능하도록 수정
6. 1.0 버젼 릴리즈
2005/08/12
1. XHTML 표준에 맞지 않는 부분들을 수정 validation 을 통과
2005/08/09
1. template_c 디렉토리의 퍼미션을 바꿔주는 인스톨용 스크립트 추가 (정말 퍼미션만 딱 바꿔줌 -_-);;
2005/08/08
1. 숨긴 파일 (파일 이름이 “.” 으로 시작하는 파일) 을 보여주지 않도록 함
2005/08/04
1. Filename / Size / Modification Time 으로 정렬이 가능해짐 (오름차순만 지원)
2. Skin 기능이 추가됨
3. svn repository 에 import 하고 누구든지 받을 수 있도록 공개

apache: mod_autoindex hack!!

예전에 써놓은 글에서 구상해뒀던 것들을 전부 패치에 반영시켜버렸습니다… 예전 hack 은 정말 quick & dirty 가 무엇인지를 보여주는 진정한 HACK!! 이었는데… 요번 패치는 옵션에 크게 영향을 받지도 않고, 사용자가 설정할 건덕지가 많아졌다는 점에서 개인적으로 흐뭇합니다…

  1. CSSFile 옵션을 통해 css 파일 지정이 가능
  2. Encoding 옵션으로 meta 데이타로 charset 지정 가능
  3. html 소스를 아주 간단하게 변환
  4. XHTML 1.0 Strict!! (validation 도 통과-_-v)

뭐 이정도를 한 건데… 예전 핵은 정말 너무 지저분하길래 -_-;; 아예 첨부터 작업했습니다. 기본 mod_autoindex에서는 pre~/pre 로 열맞춤을 하고 있는데, 프레젠테이션을 CSS로 바꾸기가 쉽지 않을 것 같아서 table 기반으로 만들었습니다.
그리고 xhtml validation을 위해 모든 태그들을 소문자로 바꿔줬습니다.
패치 파일은 아래서 받을 수 있습니다…
For apache-1.x
http://mytears.org/resources/mysrc/c/patches/mod_autoindexhack-20050816.diff
For apache-2.x
http://mytears.org/resources/mysrc/c/patches/apache2-mod_autoindex-hack-20070922.diff
테스트 페이지는 여기…
http://mytears.org/resources/
ChangeLog:
2007년 9월 22일 – apache2 용 패치 생성

Sender Policy Framework

planet.findout.or.kr 이라던가 기타 여러 곳에서 spf 에 관련된 내용을 듣다가 spf filter 를 붙이면 얼마나 효과가 있을지 궁금해지길래 postfix 에 spf 패치를 해봤습니다. 정상적으로 spf 인증을 통과한 메일헤더에는 pass 했다는 표시가 붙고, 네임서버가 spf 를 지원하지 않는 곳이라면 none, 실패했을 경우엔 spf 정책에 따라 fail 이나 softfail 이라는 에러코드가 붙게 됩니다.
spf 는 Sender Policy Framework 의 약자로 메일에 붙은 return address 를 이용 메일이 인증받은 메일 서버를 통해 발송되었는지를 체크하는 방식입니다. dns(송신 측) 와 smtp server(수신 측) 모두 spf 를 지원하는 경우에 사용할 수 있습니다. (생각해보면 smtp server 대신 mta 에서 지원해도 안될 건 없을거라고 생각합니다.)

SPF makes it easy for a domain, whether it’s an ISP, a business, a school or a vanity domain, to say, “I only send mail from these machines. If any other machine claims that I’m sending mail from there, they’re lying.”

spf 의 원리를 아주 간단하게 표현해 놨길래 인용해봅니다… “난 이 메일서버를 통해서만 메일을 보내니까 만약 다른 메일 서버를 통해 이 메일주소로 메일이 온다면 그건 허위 메일이야!!” 뭐 이 정도로 이해하면 되겠습니다.
아래에 quote 된 결과와 같이, 2006년 9월 24일 현재 대부분의 이메일 서비스에서 spf 를 지원하고 있는 것을 확인할 수 있습니다. 다만 sk telecom 의 경우 이메일 고지서의 return address 가 emailadmin@emailrms.sktelecom.com 로 명시되어 있기 때문에 이메일 고지서는 spf 의 영향을 받지 않아 약간 아쉬움이 남네요. (사실 sk 에 아쉬운 부분은 그것 만이 아니죠. 괜히 ‘ass k’ 라고 부르는 게 아닙니다.)
yahoo 에서 spf 를 지원 안한다는 점 또한 무척이나 아쉬운 부분 중 하나입니다.
[spoiler ‘apblind”결과보기”결과 감추기’]

aqua@Macintosh aqua $ nslookup
> set q=txt
> unfix.net
unfix.net text = “v=spf1 a mx ptr ~all”
> dreamwiz.com
dreamwiz.com text = “v=spf1 ip4:211.39.128.0/24 ip4:211.39.129.0/24 ip4:222.122.42.0/25 ~all”
> korea.com
korea.com text = “v=spf1 mx ip4:211.49.224.0/24 ip4:211.109.1.0/24 ip4:211.49.227.32 ip4:211.49.227.33 ~all”
> hanmail.net
hanmail.net text = “v=spf1 ip4:211.43.197.0/24 ptr ~all”
> hotmail.com
hotmail.com text = “v=spf1 include:spf-a.hotmail.com include:spf-b.hotmail.com include:spf-c.hotmail.com include:spf-d.hotmail.com ~all”
> gmail.com
gmail.com text = “v=spf1 redirect=_spf.google.com”
> _spf.google.com
_spf.google.com text = “v=spf1 ip4:216.239.56.0/23 ip4:64.233.160.0/19 ip4:66.249.80.0/20 ip4:72.14.192.0/18 ?all”
> nate.com
nate.com text = “v=spf1 ip4:203.226.253.0/24 ip4:203.226.255.0/24 ~all”
> naver.com
naver.com text = “v=spf1 ip4:220.95.234.208 ip4:61.74.70.0/23 ip4:222.122.16.0/24 ip4:220.73.156.0/24 ip4:211.218.150.0/24 ip4:211.218.151.0/24 ip4:211.218.152.0/24 ip4:218.145.30.0/24 ip4:220.95.237.0/24 ~all”
> msn.co.kr
*** Can’t find msn.co.kr: No answer
> msn.com
msn.com text = “v=spf1 include:spf-a.hotmail.com include:spf-b.hotmail.com include:spf-c.hotmail.com include:spf-d.hotmail.com ~all”
> yahoo.com
*** Can’t find yahoo.com: No answer
> yahoo.co.kr
*** Can’t find yahoo.co.kr: No answer
> hitel.net
hitel.net text = “v=spf1 ip4:211.41.82.0/24 a mx ptr ~all”
> sktelecom.com
sktelecom.com text = “v=spf1 ip4:203.236.1.100 -all”
> emailrms.sktelecom.com
*** Can’t find emailrms.sktelecom.com: No answer

[/spoiler]
이번엔 대학 메일 서비스의 경우를 살펴보겠습니다. 결과부터 말하자면 아주 실망스럽습니다. 제가 테스트 해본 대학들의 경우 전부 spf 를 지원하지 않네요.
[spoiler ‘apblind”결과 보기”결과 감추기’]

aqua@Macintosh aqua $ nslookup
> set q=txt
> hongik.ac.kr
*** Can’t find hongik.ac.kr: No answer
> wow.hongik.ac.kr
*** Can’t find wow.hongik.ac.kr: No answer
> korea.ac.kr
*** Can’t find korea.ac.kr: No answer
> snu.ac.kr
*** Can’t find snu.ac.kr: No answer
> yonsei.ac.kr
*** Can’t find yonsei.ac.kr: No answer
> hanyang.ac.kr
*** Can’t find hanyang.ac.kr: No answer

[/spoiler]
spf 를 지원하기 위해선 네임서버의 zone 파일에 “IN TXT “v=spf1 a mx ptr ~all” 정도의 룰을 삽입하면 되며, 룰은 아래의 링크를 이용하면 쉽게 만들 수 있습니다.
http://www.openspf.org/wizard.html?mydomain=&x=21&y=7
p.s) 국내 포털이 spf 를 지원하기 시작한 이후로 스팸의 70% 이상은 spf 로 걸러낼 수 있게 되었습니다.

이미지만으로 도배된 스팸

스팸들을 보다보면.. 내용은 하나도 없이 이미지 만으로 혹은 첨부파일 하나 딸랑 오는 메일들이 상당히 많다. 당연히 이미지 안에 내용을 전부 넣어버리기 때문에 필터링할만한 문자열이 아예 없다 -_-!! 그래서 생각인데 tag 를 깨끗이 비워버리고 trim 을 해보면 이런 메일들을 쉽게 거를 수 있지 않을까 싶다.

  1. title,style,script,object ~ /title,style,script,object 를 제거..
  2. 나머지 태그들을 깨끗이 제거!!
  3. trim

이 정도로만 해도 이미지로 도배된 스팸들은 다 거를 수 있지 않을까 싶은데… 뭐 역시나 귀차니즘이 문제 (어제 12시에 자러간 이후 지금까지 내 메일계정으로 온 스팸 중엔 스팸필터를 통과한 게 하나도 없다.. 친구껄로 온건 몇 개 있는거 같지만 -_-!!)
또한 본문을 seperator 기준으로 잘라서 토큰으로 만든 후… 영어로만 이루어진 토큰에 한해 spellcheck (aspell 같은걸 쓰면 되니까) 를 하고, spell 에 맞지 않는 것들의 수가 일정 % 이상이라면 스팸이라고 판단하는 방식도 유용하지 않을까 싶다.

스팸과의 전쟁 -_-!!

우선 게시판 스팸은 회원제로 바꿔버리면 반 이상은 해결할 수 있을거 같으니 제껴두고, procmail 룰 강화로 인해 필터링되지 않아야 할 메일이 필터링 되는 일이 있는지 체크할 겸 해서 로그를 남겨 지켜보는 중인데.. “광고” 라는 문구를 넣으면서도 필터링에서 피하기 위해 노력한 흔적들이 상당히 많이 보인다 -_-!!

  • 제목에 “(광고)” 란 단어를 넣긴 했지만.. base64 로 인코딩해서 보냄
  • 역시 제목에 “(광고)”란 단어를 넣긴 했지만.. quoted print 로 인코딩해서 보냄
  • &#unicode;&#unicode; 식의 방식을 사용.. “(광고)” 를 표현..

그 중 2번째와 세번째 같은 경우는 아예 인코딩된 글자 자체를 필터에 추가시키면 완벽하게 차단이 가능하지만, 문제는 첫번째 방식! base64 인코딩의 경우 7bit 단위로 잘라서.. 테이블을 이용 변환시켜버리기 때문에 “(광고)”라는 글자가 나오는 위치에 따라 결과가 많이 달라지기 때문에.. 필터링 못하는 경우도 생길 듯 하다.. base64 나 qprint 로 인코딩되서 오는 경우엔.. 오히려 어떤 charset 으로 표현된 글자인지를 알 수 있는 장점이 있으므로.. 저렇게 인코딩 해서 보내는게 나쁜건 아니지만.. 뭐 하튼 그렇다는 얘기…
최적의 솔루션이라면 디코딩을 한 후 유니코드로 변환해서 문자열 필터를 통과시키는 방법이겠지만.. 그럴려면 간단한 프로그램을 새로 짜야 하기 때문에, 귀찮은게지 -_-;; 또 제목이 전혀 인코딩되서 오지 않은 경우엔 어떤 언어인지 모르기 때문에 유니코드로 변환하는 도중에 예외 상황이 만들어지는 것도 문제고.. (사실 대강 끼워맞추기로 해결은 가능하지만)
[spoiler ‘simple”그동안의 성과 보기”숨기기’]

unfix skel # cat /var/log/procmail.log |grep ^[Adv|wc -l
429
unfix skel # cat /var/log/procmail.log |grep ^[Fake|wc -l
1561
unfix skel # cat /var/log/procmail.log |grep ^[Spam|wc -l
unfix skel # cat /var/log/procmail.log |grep ^[Viagra|wc -l
1
unfix skel # cat /var/log/procmail.log |grep ^[Virus|wc -l
2
unfix skel # cat /var/log/procmail.log |grep ^[Empty|wc -l
27
unfix skel # cat /var/log/procmail.log |grep ^[Bad|wc -l
127
unfix skel # cat /var/log/procmail.log |grep ^From|wc -l
493

[/spoiler]
지금까지의 작은 노력만으로도 결과는 만족스럽다는 사실 🙂