2012-09-16

mail]sendmail 이야기


sendmail]sendmail 이야기


sendmail 이야기

장우현(Woohyun JANG), louis@mizi.co.kr

1998년 12월 4일
본 글에서는 MTA중의 하나인(하지만 가장 유명하고, 가장 많이 사용되는) sendmail에 관한 얘기를 하고 있습니다. 보시고 의문점이나 틀린글 모호한 글은 저에게 메일로 알려주시기 바랍니다.

1. sendmail이란?

인터넷을 조금이라도 써 보신분은 sendmail이란 말을 들어보셨을 껍니다. 아니 요즘 같이 책들이 많이 나왔을때는 인터넷을 쓰지 않으셔도 sendmail이란 말은 들어보셨을 지도 모릅니다. 아마 대부분의 사람들은 과연 sendmail이 무엇이길래 사람들의 입에 오르내리는지?, 꼭 써야 하는건지? 라는 생각을 해 보셨을텐데요 여기에서는 sendmail이 무엇이며 어떻게 설치하고 sendmail에서 야기되는 몇가지 문제점들에 대해 이야기를 해 보도록 하겠습니다.
우선 sendmail은 인터넷에서 전자메일을 전송하기 위해 사용되는 프로그램이라고 생각하시면 됩니다. 그럼 이렇게 대답하시는 분들이 계실꺼예요. "어! 저는 전자메일을 보내고 받는데 Netscape Messanger를 쓰는데요! 그럼 sendmail은 몰라도 되겠네요!" 하지만 지금까지 모르셨을지 모르지만 Netscape Messanger같은 메일프로그램을 사용하시더라도 sendmail은 사용해 오셨을 겁니다. 전자메일 시스템에서 사용되는 용어중 Netscape Messanger와 같은 프로그램은 MUA(Mail User Agent)라고 부릅니다. 그에 비해 sendmail은 MTA(Mail Transfer Agent)라고 부릅니다.
우선 인터넷으로 편지를 보냈을때 어떤 경로로 전달되는지 알아보도록 하죠. 여기에서 메일서버로 taegu.ac.kr를 사용하는 whjang이라는 사용자가 kebi.com 컴퓨터에 있는 peach란 사용자에게 메일을 보낸다고 가정해보죠. 우선 사용하는 MUA(여기에서는 Netscape Messanger, 줄여서 NM이라고 부르겠습니다.)는 메일서버의 25번 포트에 접속을 합니다. 메일서버의 25번 포트에서는 MTA(여기에서 설명하는 sendmail이 해당됩니다. 이하 sendmail이라고 언급하겠습니다.)가 대기하고 있다가 NM이 보내고자 하는 메일을 받습니다. 그러면 sendmail은 스풀디렉토리(시스템 마다 조금씩 틀립니다. 제가 사용하는 Solaris 2.x에서는 /var/spool/mqueue를 사용합니다.)에 메일을 저장해 둔 후 kebi.com의 25번 포트로 접속합니다. kebi.com에도 sendmail이 25번 포트에서 대기하고 있겠죠. 정상적으로 접속을 한 후 taegu.ac.kr에 있는 sendmail은 kebi.com에 있는 sendmail에게 메일을 전송한 후 자신의 스풀에 저장된 메일을 삭제합니다. taegu.ac.kr에 있는 sendmail은 더이상 할 일이 없는거죠. 만일 kebi.com에 이상이 있어서 접속할 수 없다면 어떻게 될까요? taegu.ac.kr에 있는 sendmail은 메일을 스풀 디렉토리에 계속 가지고 있으며 수시로 접속을 시도합니다. 그러다가 며칠이 지나도 보낼 수 없다면 처음에 메일을 보낸 사람에게 메일을 보낼 수 없다고 되돌려 줍니다.
이제 메일을 받은 kebi.com에 있는 sendmail이 하는일을 차례대로 살펴보죠. 메일을 받은 sendmail은 메일의 도착지가 자신인지 확인을 합니다.(sendmail.cw파일 참조) 만일 도착지가 자신이 아니라면 도착지로 메일을 다시 전송합니다. (이 경우에는 아래에 설명드리겠지만 relay를 허용하는 호스트로만 전달할 수 있습니다. 그렇지 않은경우에는 에러를 출력합니다.) 만일 자신이 메일의 도착지라면 메일을 MDA(Mail Delivery Agent)에게 넘겨줍니다. MDA는 메일을 MTA로부터 받아서 메일박스등에 저장하거나 원하는 필터링을 할 수 있는 프로그램입니다. 보통 기본적으로 사용하는 MDA프로그램은 /bin/mail이며, 한글 처리를 위해 procmail을 이용하는 서버도 많이 있습니다. 메일을 받은 MDA는 필터링 과정을 거친 후 사용자의 메일박스에 저장합니다.
이제 메일의 전송은 완료되었습니다. 사용자는 mutt나 pine등의 MUA를 이용하여 메일을 확인할 수 있으며 외부에서 메일을 확인하는 경우 POP3나 IMAP프로토콜을 이용하여 메일박스를 가져갈 수 있습니다. POP3나 IMAP에 관한 내용은 본 글의 범위를 벗어나므로 설명은 하지 않겠습니다.
이상에서 보듯이 sendmail은 MTA의 역활을 합니다. 사용자로부터 메일을 전달받아 다른 컴퓨터의 MTA에게 넘겨주고, 다른 MTA로 부터 받은 메일을 MDA에게 넘겨주는 인터넷 전자메일의 가장 중심부에 위치하고 있습니다. 물론 MTA에는 다양한 프로그램이 있지만 sendmail은 카테고리 킬러(해당분야의 다른 프로그램들은 아예 잊혀져 버릴 만한 경쟁력을 갖추고 자신의 지위를 확고히 하는 최고 수준의 프로그램)가 될 수 있는 능력을 갖추었고, 현재 UNIX기반 메일서버의 거의 대부분이 MTA로 sendmail을 쓰고 있습니다.

2. 컴파일 및 설치

2.1 가져오기

http://www.sendmail.org에 서 배포하는 sendmail의 배포판은 1998년 10월 31일 현재 8.9.1a이 최신입니다. (이는 sendmail 8.9.1과 8.9.1a로의 패치로 이루어져 있습니다.) 우선 파일을 다운로드 받아서 풀어둡니다.
          temp $ gzip -dc sendmail.8.9.1.tar.gz | tar xvf -

          temp $ cd sendmail-8.9.1/src

          src $ patch < ../../sendmail.8.9.1a.patch
          
** Solaris등에 기본적으로 들어있는 patch를 사용하면 잘 되지 않습니다. GNU patch를 설치하셔서 사용하시기 바랍니다.

2.2 컴파일

주의**) http://www.sendmail.org/compiling.html에서는 src디렉토리에서 직접 make를 이용해서 컴파일 하지 말도록 하고 있습니다. 이 대신 Build 쉘스크립트를 사용하도록 권하고 있습니다.
가장 쉬운 방법은 Build스크립트를 사용하는 것입니다. 단순히 sh Build 라고 치면 컴파일 작업을 수행합니다. (기존에 sendmail을 설치했던 사람들중에는 makesendmail 스크립트를 사용한 사람들이 많은데 이는 Build 스크립트와 동일한 프로그램을 가리키고 있으므로 Build를 사용해도 무방합니다. 따라서 makesendmail대신에 Build를 사용하기를 권합니다.)
          sendmail 8.9.1 $ cd src

          src $ sh Build

          Configuration: os=SunOS, rel=5.6, rbase=5, rroot=5.6, arch=sun4, sfx=

          Using M4=/usr/ccs/bin/m4

          Creating obj.SunOS.5.6.sun4 using ../BuildTools/OS/SunOS.5.6

          Making dependencies in obj.SunOS.5.6.sun4

          gcc -M -I.  -DNDBM -DNIS -DNISPLUS -DMAP_REGEX -DSOLARIS=20600  *.c >> Makefile

          Making in obj.SunOS.5.6.sun4

          gcc -O -I.  -DNDBM -DNIS -DNISPLUS -DMAP_REGEX -DSOLARIS=20600    -c alias.c -o alias.o
          
위의 메시지를 잠시 살펴보면 현재 시스템이 사용하고 있는 운영체제(os)는 SunOS이며 release는 5.6임을 알 수 있습니다. 또한 시스템의 아키텍쳐는 sun4입니다. 나중에 sendmail.cf파일을 만들때 사용하는 m4는 /usr/ccs/bin/m4를 사용하고 현재 디렉토리 아래에 obj.SunOS.5.6.sun4 디렉토리에 바이너리 파일들을 생성하며 컴파일 때 사용하는 파일은 ../BuildTools/OS/SunOS.5.6 임을 알 수 있습니다.
우선 Makefile에 소스파일의 의존관계를 추가하고 본격적인 컴파일을 시작합니다. (의존관계의 생성에 관한 내용은 Makefile에 관련된 자료를 참고하기 바랍니다.)
sendmail은 다양한 설정을 가지는데 주로 매크로를 사용하여 설정합니다. 위에서 사용된 -DNBDM -DNIS -DNISPLUS -DMAP_REGEX등이 그것입니다. 이것 이외에도 많은 매크로가 있으며 여기에서는 그중에서 중요한것만 설명하겠습니다.
  • -DNEWDB : Berkeley DB패키지를 사용할 때 사용합니다. sendmail에서는 alias와 일반적인 맵(map)을 위해서 DB패키지를 이용하는데 이 DB패키지 중 Berkeley DB패키지를 사용함을 의미하는 매크로입니다. 만일 설치하고자 하는 시스템에 Berkeley DB패키지가 설치되어 있지 않다면 http://www.sleepycat.com에 서 최신 버전의 패키지를 가져다 설치하시기 바랍니다. sendmail에서는 DB패키지로 Berkeley DB를 사용기를 권하고 있습니다. 물론 다른 패키지를 사용할 수 있으나 Berkeley DB패키지를 구해서 설치하는게 여러모로 좋습니다. 필자도 처음에 gdbm을 사용하다가 Berkeley DB로 바꾸었습니다.
  • -DNDBM : DB패키지로 옛날에 사용되었던 NDBM패키지를 사용할 때 사용합니다. (NDBM매크로를 정의했을때 gdbm라이브러리를 링크합니다.) 이 NDBM패키지는 더 이상 사용되지 않으며 따라서 설치자는 NDBM대신에 NEWDB를 사용하는게 좋습니다.
  • -DNIS, -DNISPLUS : 각각 NIS와 NIS+를 지원하기 위해 사용합니다. 만일 시스템에서 NIS와 NIS+를 지원한다면 이 매크로를 정의해서 쓰는게 좋습니다.
  • -DMAP_REGEX : 스팸메일등을 필터링할 때 정규식(Regular Expression)을 사용할 수 있도록 합니다. 이 매크로를 사용하려면 POSIX의 regex()루틴이 있거나, FSF에서 만든 regexp 라이브러리가 설치되어 있어야 합니다.
이 매크로들은 여러개를 한꺼번에 정의해서 사용할 수 있습니다. (심지어는 -DNEWDB와 -DNDBM도 한꺼번에 정의해서 사용할 수 있습니다. 물론 이 경우에는 처음에 NDBM으로 만들어진 alias파일을 읽어 Berkeley DB형태로 바꾸고 Berkeley DB형태로 계속 사용합니다.) 하지만 -DNDBM은 쓰지 말기를 필자는 추천합니다. 그리고 만일 -DNEWDB가 Build 스크립트에 의해서 자동적으로 추가되지 않았다면 직접 Makefile을 수정해서 추가하도록 합니다.
이렇게 Makefile을 수정한 경우 새로 컴파일 하는 것이 좋습니다. 만일 프로그램에 익숙하다면 필자가 직접 언급하지 않아도 잘 알겠지만, 그렇지 않은 경우 -DNEWDB와 같이 매크로를 수정했다면 모든 이진파일인 *.o와 sendmail바이너리를 삭제한 후 다시 Build를 실행하고, -ldb등으로 라이브러리를 추가했다면 sendmail바이너리만 삭제한 후 다시 Build를 실행하면 됩니다.
만일 Solaris 2.6을 사용한다면 -DNEWDB -DNIS -DNISPLUS -DMAP_REGEX를 MAPDEF에 정의하고, LIBS는 -lresolv -lsocket -lnsl -lkstat -ldb을 사용하는 것을 추천합니다. 필자는 Solaris 2.6에서 위와같이 설정한 후 잘 쓰고 있습니다. 물론 이 설정을 사용해서 컴파일 하려면 Berkeley DB가 이미 설치되어 있어야 합니다. 아직 Berkeley DB패키지를 설치하지 않았다면 우선 그것부터 설치하시기 바랍니다.

2.3 설치 및 sendmail.cf생성

프로그램의 생성이 끝나면 obj.$os.$rel.$arch 디렉토리(예를들어 필자의 경우 SunOS.5.6.sun4)에 들어가서 수퍼유저의 권한으로 make install을 실행하면 매뉴얼등의 파일이 인스톨 됩니다. 기본적으로 sendmail 바이너리는 /usr/lib/ 디렉토리에 설치됩니다. 설치된 sendmail바이너리의 모드와 소유자등은 아래와 같아야 합니다.
          / $ ls -l /usr/lib/sendmail

          -r-sr-x--x   1 root     bin       412896  6월  5일  18:04 /usr/lib/sendmail
          
만일 위와 다르다면 아래와 같이 입력하여 정확하게 만드시기 바랍니다.
          / $ chown root /usr/lib/sendmail

          / $ chgrp bin /usr/lib/sendmail

          / $ chmod 4555 /usr/lib/sendmail
          
** GNU groff가 없는 시스템에서는 메뉴얼을 만들때 에러가 납니다. GNU groff를 설치하면 깔끔하게(?) 해결이 되지만, 여의치 않을때는 메뉴얼을 설치하지 않고 sendmail바이너리를 수작업으로 설치하여도 상관이 없습니다.
이제 sendmail 바이너리 파일은 설치를 했으므로 sendmail.cf 파일을 만들어야 합니다. sendmail.cf파일은 직접 수정할 수 있으나 m4를 이용해서 생성하는게 쉽습니다. cf/cf 디렉토리에는 다양한 mc파일이 있으므로 자신의 시스템에 가장 적당한 mc파일을 선택합니다. 예를들어 필자의 경우는 Solaris 2.6이므로 genric-solaris2.mc 파일을 사용했습니다. 이 mc파일을 이용해서 sendmail.cf파일을 생성하는 방법은 아래와 같습니다.
          sendmail $ cd cf/cf

          cf $ m4 ../m4/cf.m4 generic-solaris2.mc > sendmail.cf
          
이 sendmail.cf를 /etc/mail 에 복사한 후 /etc/sendmail.cf를 /etc/mail/sendmail.cf로 심볼릭 링크를 생성합니다. (ln -s /etc/mail/sendmail.cf /etc/sendmail.cf)
** Linux의 경우에는 mc파일이 없습니다. 이때는 다른 mc파일에서 OSTYPE만 linux로 변경한 후 생성하면 됩니다. Linux에서 local mailer로 procmail을 사용하는 시스템에서 일반적인 mc파일은 아래와 같습니다.
          VERSIONID(`linux for smtp-only setup with procmail for korean mail`)dnl

          OSTYPE(linux)dnl

          FEATURE(nouucp)dnl

          FEATURE(local_procmail)dnl

          FEATURE(access_db)dnl

          MAILER(local)dnl

          MAILER(smtp)dnl
          

3. 추가적인 작업들

3.1 sendmail.cw의 생성

/etc/mail/sendmail.cw에 메일을 받을 수 있는 호스트 이름을 적습니다. 이곳에 적은 이름으로 메일이 들어오면 더 이상 다른곳으로 메일을 보내지 않고 MDA(Mail Delivery Agent, 메일을 MTA에게서 받아 메일박스에 저장하는 프로그램)로 전달합니다. 보통 FQDN(Fully Qualified Domain Name)을 적고 만일 여러개의 호스트 이름을 사용한다면 모두 적어줘야 합니다.
          / $ cd /etc/mail

          mail $ cat sendmail.cw

          hostname.domain.com

          hostname2.domain.com
          

3.2 디렉토리 모드변환

sendmail 8.9.x 에서는 보안상 몇가지 디렉토리의 모드를 검사해서 적당하지 않다면 sendmail자체가 실행이 안됩니다. 따라서 아래와 같이 입력해 주어야 합니다. 자세한 내용은 DontBlameSendmail and Enhanced File Security를 참고하시기 바랍니다.
          / $ chmod go-w / /etc /etc/mail /usr /var /var/spool /var/spool/mqueue

          / $ chown root / /etc /etc/mail /usr /var /var/spool /var/spool/mqueue
          
이것 외에도 유저디렉토리에 그룹이 쓰기가능하거나, other가 쓰기 가능하다면 .forward가 작동하지 않습니다. 만일 일반 사용자의 .forward파일이 작동하지 않으면 그 사용자 홈 디렉토리의 모드를 확인하시기 바랍니다.

3.3 /etc/hosts파일

참고로 /etc/hosts 파일의 형태가 대부분 아래와 같이 되어있습니다.
          / $ cat /etc/hosts

          127.0.0.1       localhost       

          155.230.28.125  khaki   loghost

          155.230.28.115  purple
          
하지만 이 파일을 아래와 같이 수정하시기 바랍니다. (차이점은 아시겠죠? ^^)
          / $ cat /etc/hosts

          127.0.0.1       localhost       

          155.230.28.125  khaki.ce.kyungpook.ac.kr        khaki   loghost

          155.230.28.115  purple.ce.kyungpook.ac.kr       purple
          

3.4 테스트

이렇게 설정을 모두 마치셨다면 다음과 같이 해서 에러 메시지가 없는지를 확인해 보시기 바랍니다.
          / $ /usr/lib/sendmail -bi
          
이 때 에러 메시지가 없어야 합니다. 만일 에러 메시지가 났다면 /var/log/syslog 화일의 뒷부분을 보시기 바랍니다. 만일 별 문제가 없다면 이제 sendmail을 다시 띄우시면 됩니다.

3.5 데몬 띄우기

          / $ /usr/lib/sendmail -bd -q1h
          
그리고 반드시 /var/log/syslog 를 확인하시고, 메일을 보내고 받는 테스트를 지금 바로 해 주세요. 그리고 /var/log/syslog 에 에러 메시지가 있는지도 살펴 보시기 바랍니다.

4. 한글지원

메일에서 사용되는 SMTP프로토콜은 기본적으로 7bit문자만을 기반으로 제작되었습니다. 하지만 한글의 경우 EUC-KR로 표현하면 8bit를 사용하기 때문에 문제가 생길 수 있습니다. 따라서 메일에서 사용하기 위해 한글의 7bit 표현방법인 ISO-2022-kr(RFC 1557)이 만들어 졌고 메일의 본문에 사용되었습니다(헤더에는 EUC-KR을 B나 Q인코딩 방법으로 인코딩해서 사용했습니다.). 하지만 대부분의 프로그램에서는 한글을 8bit표현방법인 EUC-KR을 사용했으므로 이 두 표현간의 변환을 해 주는 프로그램이 필요했습니다. 이 작업은 크게 MTA, MDA, MUA에서 해 줄 수 있습니다. MTA에서 변환을 해 주는 대표적인 프로그램이 sendmail 8.6.12h2입니다. 이 프로그램은 프로그램으로부터 8bit표현을 입력으로 받아서 다른 곳으로 전송할때 ISO-2022-kr로 변환한 후 전송을 하고, 네트웍을 통해 받은 ISO-2022-kr로 표현된 메일을 EUC-KR로 변환 후 메일박스에 저장하도록 만들어 졌습니다. 그래서 몇년전까지만 해도 대부분의 메일서버에서 sendmail 8.6.12h2를 사용했었습니다.
하지만 SMTP 프로토콜이 8bit문자를 지원하는 ESMTP 프로토콜로 변하면서 본문에서도 ISO-2022-kr대신에 EUC-KR을 사용하도록 표준이 바뀌었습니다. 하지만 이 안을 정식 표준으로 공표하지 않았고, 아직까지 인터넷에는 ISO-2022-kr 로 표현된 메일이 돌아다니기 때문에 이 메일을 EUC-KR로 변환해 주는 작업이 추가적으로 필요하게 되었습니다.
ISO-2022-kr을 EUC-KR로 변환해 주는 프로그램들은 UNIX환경에서는 많이 만들어 졌습니다. hconv와 hmconv가 대표적인 프로그램입니다. 이제 관리자가 해 줘야 하는일은 sendmail이 받은 메일을 메일박스로 저장하기 전에 이 프로그램을 통과하게 만들어서 ISO-2022-kr을 EUC-KR로 변환만 해 주면 되게 되었습니다. 이렇게 필터링을 가능하게 해 주는 대표적인 프로그램이 procmail입니다.
여기에서는 procmail을 이용하여 한글 메일을 처리하는 과정을 설명드리겠습니다. 여기에서 알아두셔야 할 내용중에 중요한 내용으로 MDA에 대한 이해입니다. MDA(Mail Delivery Agent)는 MTA(Mail Transfer Agent, 대표적인 예는 sendmail입니다.)가 받은 메일의 최종적인 도착지가 현재 호스트인경우(sendmail의 경우 sendmail.cw를 참고하여 결정합니다.) 메일을 MDA에게 넘겨줍니다. 보통 시스템의 기본적인 MDA는 /bin/mail입니다. procmail은 /bin/mail대신에 사용할 수 있는 프로그램으로 필터링 기능이 강력하여 한글처리에 이용할 수 있습니다.
또 잘못 이해하시는 분들중에 procmail자체가 한글 디코딩을 해준다고 알고 계신분들이 많습니다. 이것은 잘못된 것입니다. 실재로 procmail도 한글 디코딩을 위해 다른 프로그램(보통 hcode나 hmconv를 이용합니다.)을 이용합니다. procmail이 하는일은 단순히 어떤 헤더가 있을때 적당한 프로그램을 불러 한글 디코딩을 해 줍니다.
따라서 procmail뿐만 아니라 한글 디코딩을 위한 프로그램을 설치하셔야 합니다. 여기에서는 hcode를 사용하도록 하겠습니다.
hcode는 ftp://ftp.kaist.ac.kr/hangul/code/hcode/에서 구할 수 있습니다. 가져온 프로그램을 적당한 디렉토리에 풀고 소스 디렉토리에서 단순히 make를 입력하면 컴파일이 완료됩니다. 컴파일 결과로 생긴 hcode를 /usr/local/bin 에 복사해 둡니다.(다른 디렉토리도 상관없습니다.)
그다음 procmail을 설치합니다. procmail은 대부분의 ftp서버에서 구할 수 있습니다. (저의 경우ftp://ftp.kreonet.re.kr/pub/tools/mail/procmail/에 서 구했습니다.) 프로그램을 구한 후 디렉토리에서 make를 입력한 후 메시지에 나온대로 대답하면 설치할 수 있습니다. 만들어진 procmail을 역시 /usr/local/bin에 설치합니다.
그런다음 /etc/procmailrc를 아래와 같이 만들어 둡니다.
          LOGFILE=/var/log/procmail

          VERBOSE=no

          PATH=/usr/local/bin:/usr/bin:/bin

          SHELL=/bin/sh 

          

          :0 B

          *^.\$\)C

          {

            :0 fbw

            |hmconv -u

          

            :0 fhw

            * ^Content-Type: text/plain

            |formail -c -I "Content-Type: text/plain; charset=EUC-KR" -I \

            "Content-Transfer-Encoding: 8bit"

          

            :0 Efhw

            * ^Content-Type: text/html

            |formail -c -I "Content-Type: text/html; charset=EUC-KR" -I \

            "Content-Transfer-Encoding: 8bit"

          

            :0 Efhw

            * !^Content-Type:

            |formail  -c -I "Content-Type: text/plain; charset=EUC-KR" -I \

            "Content-Transfer-Encoding: 8bit"

          

            # Note that '-c' flag has been added to formail invocation.

            # It concatenates a  header of multiple lines into a single line

            # so that a bug in 'hcode -dk -m' dealing with RFC 2047 encoded header

            # has less 'harmful' effect.

          

            :0 fhw

            | formail -A  \

            "X-Automatic-Korean-Mail-Conversion: iso-2022-kr to euc-kr" 

          

          }

          

          DROPPRIVS=yes

          

          :0 fhw

          *Content-Type:.+; charset="?EUC-KR

          | formail -c | hcode -dk -m 

          

          :0 Efhw

          *^(Subject|From|Cc):.*=\?EUC-KR\?(B|Q)\?

          | formail -c | hcode -dk -m
          
그다음 sendmail에서 MDA로 procmail을 사용할 수 있도록 sendmail.cf파일을 수정해 줘야 합니다. sendmail.cf파일에서 Mlocal부분을 찾아서 아래와 같이 수정하시면 됩니다.
          Mlocal,         P=/usr/local/bin/procmail, F=lsDFMAw5:/|@qSPfhn9, S=10/30, R=20/40,

                          T=DNS/RFC822/X-Unix,

                          A=procmail -Y -a $h -d $u
          
하지만 이 방법보다는 mc파일에 FEATURE(local_procmail)을 추가하여 sendmail.cf를 생성하는 방법이 좋습니다.
제가 여기에서는 간단하게 설명을 드렸지만 좀더 자세한 내용이 필요하신 분은 신정식님의 Sendmail 8.8.x 이후 판과 Procmail을 이용한 한글 메일 처리를 참고하시기 바랍니다.
이 작업이 귀찮게 느껴지신다면 위에서 하는작업과 동일한 일을 하는 한 글 sendmail을 설치하시면 됩니다. 하지만 한글 sendmail은 영문 sendmail에 비해 버전도 낮고, 또다른 오류가 생길 확률이 높기때문에 위의 방법을 사용하시기 바랍니다.

5. sendmail.cf에 관한 얘기

sendmail프로그램은 그 자체로 매우 복잡한 프로그램입니다. 또한 프로그램의 설정파일인 sendmail.cf자체도 복잡하기 그지 없습니다. ^^ 이 프로그램에 대한 얘기는 여기에서 설명하기 힘드므로 (솔직히 기존의 글보다 더 잘 설명할 자신도 없습니다. ^^) 이상로님의 http://trade.chonbuk.ac.kr/~leesl/mail/를 참고하시거나 sendmail의 저자가 직접 저술한 책(책 제목이 금방 떠오르지 않네요. 그냥 sendmail이지 싶은데.. ^^)을 참고하시기 바랍니다.
복잡한 설정이 싫다면 위에서 만들었던 m4를 이용해서 만든 sendmail.cf를 그대로 이용하셔도 됩니다.

6. Third Party Relay

6.1 Third Party Relay란?

Third Party Relay란 간단하게 말해서 SMTP서버의 사용자가 아닌 사람(보통 스팸을 뿌리기 위한 악의로)이 SMTP서버를 이용하는 것입니다. 따라서 A 컴퓨터의 SMTP서버를 C 컴퓨터에 있는 사용자가 B 컴퓨터로 메일을 보내기 위해 이용하는경우를 말합니다. 좀더 자세한 설명은 What is Third-Party Mail Relay?를 참고하시기 바랍니다.
아직까지 많은 서버들이 Third Party Relay를 허용하고 있으며, 이때문에 자신이 관리하는 호스트가 스팸 사이트로 인식되는것도 모르고 있는 경우가 허다합니다. 우선 자신이 관리하는 호스트의 SMTP서버가 Third Party Relay를 허용하는지를 체크하려면 Is My Mailer Vulnerable?에서 하실 수 있습니다. 꼭 해보시기 바랍니다.

6.2 설정방법

sendmail 8.7.x 이하

Third Party Relay를 막으려면 적어도 sendmail 8.8.x 가 되어야 합니다. 따라서 최신의 sendmail로 업그레이드를 하시기 바랍니다.

sendmail 8.8.x

sendmail.cf에 아래와 같은 Rule set을 넣고 sendmail.cR파일에 relay를 허용하는 호스트의 FQDN이나 IP address를 입력하면 됩니다. ( http://www.sendmail.org/antispam.html에 서는 IP address를 권하고 있습니다.)
          FR-o /etc/sendmail.cR

          

          Scheck_rcpt

          # anything terminating locally is ok

          R< $+ @ $=w >           $@ OK

          R< $+ @ $=R >           $@ OK

          

          # anything originating locally is ok

          R$*                     $: $(dequote "" $&{client_name} $)

          R$=w                    $@ OK

          R$=R                    $@ OK

          R$@                     $@ OK

          

          # anything else is bogus

          R$*                     $#error $: "550 Relaying Denied"
          
그리고 /etc/sendmail.cR의 설정은 아래와 유사하게 하시면 됩니다.
          / $ cat /etc/sendmail.cR

          155.230.28.117

          155.230.28.118
          

sendmail 8.9.x

sendmail 8.9.x에서는 기본적으로 third party relay를 금지하고 있습니다. 만일 third party relay를 허용하려면 promiscuous_relay FEATURE를 mc파일에 추가하고 sendmail.cf를 생성하면 됩니다. (하지만 이렇게 할 사람이 있나요? ^^)
따라서 sendmail 8.9.x에서는 sendmail.cf에 특별한 수정없이 relay에 관한 파일만 수정하면 됩니다. 아래에서는 사용하고 있는 도메인 이름이 company.co.kr 이고, 호스트 이름이 myhost, ip address가 203.123.45.67 인 경우라고 가정합니다.
/etc/mail/access : 누가 이 메일 서버를 릴레이 서버로 지정해서 사용할 수 있는가, 어떤 주소에서 오는 메일은 거절할 것인가를 설정하는 파일입니다.
          mail $ cat access

          203.123.45      RELAY

          209.1.2.3       RELAY

          cyberpromo.com  REJECT
          
이렇게 설정한 경우 myhost와 같은 서브넷에 있는 컴퓨터들와 209.1.2.3을 사용하는 컴퓨터에서만 myhost.company.co.kr을 SMTP 서버로 지정해서 메일을 보낼 수 있습니다. 그리고 cyberpromo.com과 cyperpromo.com 도메인에 속하는 모든 호스트에서 오는 메일은 거절합니다. 일단 이 화일을 만드셨다면 이제는 DB 화일을 만드셔야 합니다.
          / $ cd /etc/mail

          mail $ makemap hash access < access
          
그리고 /etc/mail/access 화일을 수정을 할 때마다 반드시 이 작업을 해 주셔야 합니다. 하지만 이 작업을 후에 sendmail을 죽이고 다시 띄울 필요는 없습니다.
그리고 access파일을 사용할 경우에는 sendmail.cf를 생성할 때 mc파일에 FEATURE(access_db)를 추가해야 합니다.
또한 makemap의 버전이 낮은경우 작동을 하지 않는 경우가 있습니다. 이때는 sendmail 패키지와 함께 딸려나오는 makemap을 컴파일 한 후 시도해 보시기 바랍니다. makemap도 sendmail과 마찬가지로 -DNEWDB를 선택해 주셔야 합니다.
/etc/mail/relay-domains : 위의 /etc/mail/access에서 지정한 곳 외에서 메일 서버로 지정하는 경우에도, relay-domains 에 등록한 도메인의 호스트에 대해서는 허용합니다. relay-domains와 access파일의 큰 차이점의 하나는 access파일의 경우 수정후 sendmail을 다시 실행할 필요가 없지만 relay-domains파일은 수정후 sendmail을 다시 실행해야 바뀐 내용을 인식합니다. 편한 파일을 하나 정해서 사용하시면 됩니다. 저의 경우 access파일은 RELAY-FROM에 해당하는 호스트에 relay-domains는 RELAY-TO에 해당하는 호스트를 설정합니다.
          mail $ cat relay-domains

          company.co.kr
          
이 경우 company.co.kr 도메인에서 오는 메일은 모두 중계를 허용합니다. 만일 이 메일 서버로만 오는 메일을 받고 싶다면(대부분의 경우가 여기에 속합니다) access 화일과 relay-domains 화일을 0바이트짜리 화일로 만들면 됩니다.
이렇게 설정한 후 SMTP서버가 third party relay를 허용하는지 테스트해 보시기 바랍니다.

7. 난 SPAM이 싫어요!

인터넷이 생활 깊숙히 들어가면 갈수록 편해지는 점이 있는것처럼 가끔은 사람을 짜증나게(?) 만드는 일들이 있습니다. 메일도 마찬가지인데요. 그중에서 사람을 열받게(?) 만드는 대표적인 메일은 스팸메일입니다. 따라서 메일서버의 관리자라면 스패머(Spammer, 스팸메일을 보내는 사람)가 보내는 스팸메일을 차단할 수 있어야 합니다. 여기에서는 스팸메일이 무엇이고, 어떻게 막을것인가에 관한 얘기를 하고자 합니다.

7.1 SPAM 메일이란?

가능한 빨리 추가할께요. 죄송 ^^

7.2 SPAM 메일을 막으려면?

만일 님이 관리하고 있는 메일서버의 사용자한명이 info@cyberpromo.com 에서 계속 SPAM메일을 보낸다고 항의를 해 온다면 /etc/mail/access 에 아래와 같이 추가하고 makemap으로 access DB를 재 생성하세요.
          info@cyberpromo.com REJECT
          
근데 좀 지나보니 info2@cyberpromo.com 으로 이름을 바꾸어서 SPAM메일을 계속 보내는군요. 열받아서 cyberpromo.com 에서 오는 메일을 모두 거부하고 싶다면 아래와 같이 추가하세요.
          cyberpromo.com REJECT
          
좀 지나고 생각을 해 보니 그냥 거부만 하니까 너무 싱겁군요. 메시지를 하나 띄워주고 싶다면 아래와 같이 access파일을 만드세요.
          cyberpromo.com 550 Spammers couldn't see sunlight here
          
이제 좀 시원하군요. ^^

8. 가상 호스트

다음과 같은 상황을 가정해 보죠. 갑은 현재 을과 병에게 호스트를 임대해 주고 있습니다. 한대의 유닉스 시스템에 각각 ul.co.kr과 byung.co.kr이라는 도메인을 할당해서 웹서비스와 메일서비스를 해 주고 있습니다. 현재 웹서비스는 apache서버의 가상 호스트기능을 이용해서 잘 서비스를 하고 있었는데 갑자기 을과 병이 webmaster라는 메일계정을 똑같이 요구했습니다. 즉 을은webmaster@ul.co.kr을 병은 webmaster@byung.co.kr을 요구했죠. 갑은 고민을 합니다. 어떻게 할까? 만일 이글을 보고 계신분이 갑과 같은 상황이라면 어떻게 해결을 했을까요?
sendmail에서는 이와 같은 문제를 해결하기 위해 가상 호스트를 제공합니다. 자세한 내용은 Virtual Hosting with Sendmail을 참고하시기 바랍니다. 여기에서는 간단하게 설명을 드리겠습니다.
위와 같은경우 이미 Name Server에는 정상적으로 설정되어 있을것이므로 Name Server 설정방법은 생략하겠습니다. 우선 sendmail.cf를 다시 만들어야 합니다. 이미 만들었던 mc파일에 FEATURE(virtusertable, hash /etc/mail/virtusertable)을 추가하고 sendmail.cf를 다시 생성하시기 바랍니다.(이 글에서는 sendmail이 사용하는 DB는 Berkeley DB라고 가정합니다.)
이제 을이 사용하는 계정인 webul을 만듭니다.(이름은 상관이 없습니다. 여기에서는 편의상 제가 이렇게 지었습니다.) 그리고 병이 사용하는 webbyung을 만듭니다. 그다음 /etc/mail/virtusertable.src 파일을 아래와 같이 만듭니다.
          webmaster@ul.co.kr    webul

          webmaster@byung.co.kr webbyung
          
그다음 makemap으로 아래와 같이 DB파일을 만들면 됩니다.
          makemap hash /etc/mail/virtusertable < /etc/mail/virtusertable.src
          
이렇게 해 두면 webmaster@ul.co.kr으로 오는 메일은 을에게 webmaster@byung.ac.kr로 오는메일은 병에게 갈 수 있습니다. 어때요? 간단하죠? virtusertable을 이용하면 위와 같은 단순한 기능외에도 다양한 기능을 사용할 수 있습니다. 자세한 내용은 위에서 언급했던 Virtual Hosting with Sendmail을 참고하시기 바랍니다.

9. 문제 해결

사용자명에 대문자가 들어있는경우 메일을 받으려면?
sendmail을 MTA로 사용하시는 경우에 sendmail.cf의 Mlocal로 시작하는 부분에 보시면 F=이라고 된 부분이 있습니다. 이곳에 u를 추가하면 대문자로 된 계정에서도 메일을 받아볼 수 있습니다. 하지만 계정에는 대문자를 안 쓰시는게 좋습니다. (특히 NIS+를 쓸경우 말썽을 많이 부립니다.)
.forward가 작동하지 않습니다.
Sendmail 8.9.x 부터는 sendmail이 읽어들이는 파일의 모드를 검사합니다. 예를들어 .forward가 있는 디렉토리(일반적으로 홈 디렉토리)의 모드가 그룹에게 쓰기가능하도록 설정되어 있으면 .forward파일자체를 읽지않습니다. 이때문에 .forward가 작동하지 않는다고 투덜대는 사람들이 많습니다. 지금 사용하고 계신 sendmail이 8.9.0이상이라면 자신의 홈디렉토리와 그 상위디렉토리가 그룹에게 쓰기가능하도록 되어있는지 확인해 보시기 바랍니다. 자세한 얘기는 DontBlameSendmail and Enhanced File Security를 참고하시기 바랍니다.
뉴스그룹에 김경욱님이 아래와 같은 글을 올려주셨습니다. 역시 .forward가 작동하지 않는경우를 설명하고 있습니다. 참고하세요.
          sendmail.cf에서, .forward에 영향을 미치는 부분은 두군데입니다.

          

          # Forward file search path

          O ForwardPath=$z/.forward.$w:$z/.forward

          

          $z (/etc/passwd를 lookup 해서 얻은 유저 디렉토리의 path) 밑의

          .forward가 ForwardPath로 잡혀 있습니다. 이 옵션을 disable(#)시키면

          forwarding이 되지 않습니다.

          

          다음, 여기서 $z 값을 얻기 위해서 Local delivery agent는 /etc/passwd를

          lookup 합니다. 그러나 Mlocal에서 F=w flag가 없으면 Mlocal은

          /etc/passwd 를 lookup 하지 않습니다.

          

          Mlocal,         P=/usr/local/bin/procmail, F=lsDFMAw5:/|@qSPfhn9,

          S=10/30, R=20/ 40,

                          T=DNS/RFC822/X-Unix,

                          A=procmail -Y -a $h -d $u

          

          위 두가지 사항을 확인해 보세요.

          

          --

          김경욱
          
access가 작동하지 않습니다.
일단 sendmail.cf를 만든 mc에 FEATURE(access_db, hash -o /etc/mail/access)를 추가하셨는지 검사해 보시고 만일 넣지 않았었다면 추가한 후 다시 sendmail을 생성해 보시기 바랍니다.
가끔 makemap의 버전이 낮아서 안되는 경우가 있습니다. 위와같이 했는경우에도 작동하지 않는다면 sendmail에 같이 들어있는 makemap을 컴파일해서 사용하시면 됩니다. (makemap에서도 사용할 DB등을 명시합니다. sendmail의 컴파일과 동일하게 하시면 됩니다.)

10. 참고글

1. 이석찬님의 Solaris 2.5.1용 sendmail 8.9.0 패키지의 README파일
3. 이상로님의 Sendmail and Hangul Code

댓글 없음:

댓글 쓰기