- XMRPOP ;ISC-SF/GMB-POP3 Server (RFC 1939) ;05/20/2002 07:05
- ;;8.0;MailMan;;Jun 28, 2002
- ; Replaces the class III routines ^XMRPOPA, ^XMRPOPB, ^XMRPOPC,
- ; which were written by Chiao-Ming Wu, WASH-ISC.
- ;
- ; Implements RFC 1939 (replaces RFC 1725)
- ; Post Office Protocol - Version 3 (POP3) maildrop service
- ;
- ; Rather than locking the user's IN basket, which severely disrupts
- ; mail delivery, we take a snapshot of it, and keep the snapshot in
- ; a temp global. We then use the temp global during the session.
- ; Here is the layout of the global:
- ;
- ; ^TMP("XM",$J,"POP3")=# msgs^# octets ; total msgs in IN basket
- ; ; (updated if msgs are deleted)
- ; ^TMP("XM",$J,"POP3",1)=XMZ^# octets ; msgs 1 thru n are in
- ; ... ; IN basket.
- ; ^TMP("XM",$J,"POP3",i)=XMZ^# octets ;
- ; ^TMP("XM",$J,"POP3",j)=XMZ^# octets ;
- ; ... ;
- ; ^TMP("XM",$J,"POP3",n)=XMZ^# octets ;
- ; ;
- ; ^TMP("XM",$J,"POP3","D",i)=XMZ ; user deleted msg i
- ; ^TMP("XM",$J,"POP3","D",j)=XMZ ; user deleted msg j
- ENTRY ;
- N XMK,XMSTATE,XMCMDS,XMCMD,XMDUZ,XMACCESS,XMVERIFY,XMTRY,XMTMSGS,XMTOCTS,XMV
- I '$D(ZTQUEUED) S X=$S($D(^%ZOSF("ERRTN")):^("ERRTN"),1:"ERR^ZU"),@(^%ZOSF("TRAP"))
- I '$G(DUZ) S DUZ=.5
- I '$D(XMDUZ) S XMDUZ=DUZ
- I '$D(XMC("BATCH")) S XMC("BATCH")=0
- I $S('$D(XMCHAN):1,XMCHAN="":1,1:0) S XMCHAN="TCP/IP-MAILMAN"
- D OPEN^XML
- I $G(ER)=1 D ^%ZISC:IO'=$G(IO(0)) W !,"Device open failed !",$C(7) Q
- S:'$D(XM) XM=""
- I 'XMC("BATCH") X ^%ZOSF("EOFF") S X=255 X ^%ZOSF("RM"),^%ZOSF("TYPE-AHEAD")
- S ER=0
- S XMK=1
- S XMSG="+OK "_^XMB("NETNAME")_" POP3 server ready (Comments to: POSTMASTER@"_^XMB("NETNAME")_")" X XMSEN Q:ER
- S XMCMDS("AUTH")="^PASS^QUIT^USER^"
- S XMCMDS("TRAN")="^DELE^LIST^NOOP^QUIT^RETR^RSET^STAT^TOP^UIDL^"
- S XMSTATE="AUTH"
- F X XMREC Q:ER D Q:XMCMD="QUIT"!ER
- . I XMRG="" S ER=1,XMCMD="" Q
- . S XMCMD=$P(XMRG," ",1)
- . I $L(XMCMD)<3!($L(XMCMD)>4)!(XMCMD'?.U) S XMSG="-ERR no such command" X XMSEN Q
- . I $T(@XMCMD)'[";;" S XMSG="-ERR no such command" X XMSEN Q
- . I XMCMDS(XMSTATE)'[(U_XMCMD_U)="" S XMSG="-ERR no such command in "_XMSTATE_" state" X XMSEN Q
- . D @XMCMD
- I ER,$G(XMCMD)'="QUIT" D QUIT
- Q
- DELE ;;
- N XMID
- S XMID=$P(XMRG," ",2,999)
- Q:'$$OKID(XMID)
- N XMREC,XMZ,XMOCTS
- S XMZ=+^TMP("XM",$J,"POP3",XMID),XMOCTS=$P(^(XMID),U,2)
- S ^TMP("XM",$J,"POP3","D",XMID)=XMZ
- S XMREC=^TMP("XM",$J,"POP3")
- S ^TMP("XM",$J,"POP3")=($P(XMREC,U,1)-1)_U_($P(XMREC,U,2)-XMOCTS)
- S XMSG="+OK message "_XMID_" deleted" X XMSEN
- Q
- OKID(XMID) ;
- I XMID="" S XMSG="-ERR message-id required" X XMSEN Q 0
- I +XMID'=XMID S XMSG="-ERR improper message-id" X XMSEN Q 0
- I '$D(^TMP("XM",$J,"POP3",XMID)) S XMSG="-ERR no such message" X XMSEN Q 0
- I $D(^TMP("XM",$J,"POP3","D",XMID)) S XMSG="-ERR message "_XMID_" already deleted" X XMSEN Q 0
- Q 1
- LIST ;;
- N XMID,XMOCTS
- S XMID=$P(XMRG," ",2,999)
- I XMID="" D Q
- . S XMSG="+OK "_$P(^TMP("XM",$J,"POP3"),U,1)_" messages ("_$P(^("POP3"),U,2)_" octets)" X XMSEN Q:ER
- . F S XMID=$O(^TMP("XM",$J,"POP3",XMID)) Q:'XMID S XMOCTS=$P(^(XMID),U,2) D Q:ER
- . . Q:$D(^TMP("XM",$J,"POP3","D",XMID))
- . . S XMSG=XMID_" "_XMOCTS X XMSEN
- . S XMSG="." X XMSEN
- Q:'$$OKID(XMID)
- S XMSG="+OK "_XMID_" "_$P(^TMP("XM",$J,"POP3",XMID),U,2) X XMSEN
- Q
- NOOP ;;
- S XMSG="+OK" X XMSEN
- Q
- PASS ;;
- I '$D(XMACCESS) D LOGINERR("-ERR sorry, USER access code expected") Q
- S XMVERIFY=$P(XMRG," ",2,999)
- I XMVERIFY'="" D LOGIN Q
- D LOGINERR("-ERR sorry, PASS verify code expected")
- Q
- LOGIN ;
- N XMLOGIN
- S XMLOGIN=$$LOGINOK
- I 'XMLOGIN D LOGINERR("-ERR "_$P(XMLOGIN,U,2)) Q
- K XMACCESS,XMVERIFY
- S XMSTATE="TRAN"
- S XMDUZ=DUZ
- D INIT^XMVVITAE
- D MAILDROP
- D RSET
- Q
- LOGINOK() ;
- I $T(@"USERSET^XUSRA")="" Q $$OLDCHK
- Q $$USERSET^XUSRA(XMACCESS_";"_XMVERIFY)
- OLDCHK() ;
- N XUSER,XUF,%1,XMLOGIN
- S XUF=0
- S XMLOGIN=$$CHECKAV^XUS(XMACCESS_";"_XMVERIFY)
- I XMLOGIN S DUZ=XMLOGIN Q 1
- Q "0^Not a valid ACCESS CODE/VERIFY CODE pair"
- MAILDROP ;
- N XMKZ,XMZ,XMOCTS,XMID
- K ^TMP("XM",$J,"POP3")
- S (XMID,XMKZ,XMTOCTS)=0
- F S XMKZ=$O(^XMB(3.7,XMDUZ,2,XMK,1,"C",XMKZ)) Q:'XMKZ D
- . S XMZ=$O(^XMB(3.7,XMDUZ,2,XMK,1,"C",XMKZ,0))
- . I '$D(^XMB(3.7,XMDUZ,2,XMK,1,XMZ,0)) D ADDITC^XMUT4A(XMDUZ,XMK,XMZ,XMKZ)
- . I '$D(^XMB(3.9,XMZ,0)) D ZAPIT^XMXMSGS2(XMDUZ,XMK,XMZ) Q
- . S XMID=XMID+1
- . S XMOCTS=$$OCTETS(XMZ)
- . S XMTOCTS=XMTOCTS+XMOCTS
- . S ^TMP("XM",$J,"POP3",XMID)=XMZ_U_XMOCTS
- S XMTMSGS=XMID
- Q
- OCTETS(XMZ) ; Returns the number of 'octets' in a message.
- ; Basically, that's a count of the number of characters.
- ; We estimate it by multiplying the number of lines by 50.
- Q $P($G(^XMB(3.9,XMZ,2,0)),U,4)*50
- LOGINERR(XMSG) ;
- K XMACCESS,XMVERIFY
- S XMTRY=$G(XMTRY)+1
- I XMTRY<3 X XMSEN Q
- D SIGNOFF(XMSG_"; 3 tries and you're out!")
- S XMCMD="QUIT"
- Q
- QUIT ;;
- I XMSTATE="TRAN",'ER D UPDATE
- K ^TMP("XM",$J,"POP3")
- D SIGNOFF("")
- Q
- SIGNOFF(XMSG) ;
- S XMSG=$S(XMSG'="":XMSG_"; ",ER:"-ERR ",1:"+OK ")_^XMB("NETNAME")_" POP3 server signing off" X XMSEN
- Q
- RETR ;;
- N XMID
- S XMID=$P(XMRG," ",2,999)
- Q:'$$OKID(XMID)
- S XMSG="+OK "_$P(^TMP("XM",$J,"POP3",XMID),U,2)_" octets" X XMSEN Q:ER
- D RETRIEVE(XMID,"*")
- Q
- RSET ;;
- K ^TMP("XM",$J,"POP3","D")
- S ^TMP("XM",$J,"POP3")=XMTMSGS_U_XMTOCTS
- S XMSG="+OK maildrop has "_XMTMSGS_" messages ("_XMTOCTS_" octets)" X XMSEN
- Q
- STAT ;;
- S XMSG="+OK "_$P(^TMP("XM",$J,"POP3"),U,1)_" "_$P(^("POP3"),U,2) X XMSEN
- Q
- TOP ;;
- N XMID,XMLINES
- S XMID=$P(XMRG," ",2)
- Q:'$$OKID(XMID)
- S XMLINES=$P(XMRG," ",3,999)
- I +XMLINES'=XMLINES S XMSG="-ERR improper number of lines" X XMSEN Q
- S XMSG="+OK" X XMSEN Q:ER
- D RETRIEVE(XMID,XMLINES)
- Q
- UIDL ;;
- N XMID,XMZ
- S XMID=$P(XMRG," ",2,999)
- I XMID="" D Q
- . S XMSG="+OK" X XMSEN Q:ER
- . F S XMID=$O(^TMP("XM",$J,"POP3",XMID)) Q:'XMID S XMZ=+^(XMID) D Q:ER
- . . Q:$D(^TMP("XM",$J,"POP3","D",XMID))
- . . S XMSG=XMID_" "_XMZ X XMSEN
- . S XMSG="." X XMSEN
- Q:'$$OKID(XMID)
- S XMSG="+OK "_XMID_" "_+^TMP("XM",$J,"POP3",XMID) X XMSEN
- Q
- USER ;;
- S XMACCESS=$P(XMRG," ",2,999)
- I XMACCESS'="" S XMSG="+OK" X XMSEN Q
- D LOGINERR("-ERR sorry, USER access code expected")
- Q
- UPDATE ;
- N XMID,XMZ
- S XMID=0
- F S XMID=$O(^TMP("XM",$J,"POP3","D",XMID)) Q:'XMID S XMZ=+^(XMID) D DEL^XMXMSGS2(XMDUZ,"",XMZ)
- Q
- RETRIEVE(XMID,XMLINES) ;
- N XMZ,XMRESP,XMIM,XMINSTR,XMIU
- S XMZ=+^TMP("XM",$J,"POP3",XMID)
- D INMSG^XMXUTIL2(XMDUZ,"",XMZ,"","I",.XMIM,.XMINSTR,.XMIU)
- D RETRXMZ(XMZ,XMLINES,.XMIM) Q:ER
- I 'XMLINES,XMIM("RESPS") D Q:ER
- . F XMRESP=XMIU("RESP")+1:1:XMIM("RESPS") D Q:ER
- . . N XMIR
- . . D INRESP^XMXUTIL2(XMZ,XMRESP,"I",.XMIR) Q:'$D(XMIR)
- . . I XMIR("SUBJ")?1"R".N S XMIR("SUBJ")="Re: "_XMIM("SUBJ")
- . . S XMSG="" X XMSEN Q:ER ; just for visual separation
- . . D RETRXMZ(XMIR("XMZ"),"*",.XMIR,XMZ) Q:ER
- E S XMRESP=0
- S XMSG="." X XMSEN Q:ER
- D LASTACC^XMXUTIL(XMDUZ,XMK,XMZ,XMRESP,.XMIM,.XMINSTR,.XMIU)
- I $D(^XMB(3.7,XMDUZ,"N0",XMK,XMZ)),+XMRESP=+$P($G(^XMB(3.9,XMZ,3,0)),U,4) D NONEW^XMXUTIL(XMDUZ,XMK,XMZ,1)
- Q
- RETRXMZ(XMZ,XMLINES,XMIM,XMZO) ;
- N XMI
- I $O(^XMB(3.9,XMZ,2,0))'<1 D CRE8HDR(XMZ,.XMIM,.XMZO) Q:ER
- S XMI=0
- F S XMI=$O(^XMB(3.9,XMZ,2,XMI)) Q:'XMI S XMSG=^(XMI,0) S:$E(XMSG)="." XMSG="."_XMSG X XMSEN Q:ER I XMLINES,XMI'<XMLINES Q
- Q
- CRE8HDR(XMZ,XMIM,XMZO) ;
- S XMSG="Message-ID: <"_XMZ_"@"_^XMB("NETNAME")_">" X XMSEN Q:ER
- S XMSG="From: <"_$$NETNAME^XMXUTIL(XMIM("FROM"))_">" X XMSEN Q:ER
- S XMSG="To: <"_XMV("NETNAME")_">" X XMSEN Q:ER
- S XMSG="Subject: "_XMIM("SUBJ") X XMSEN Q:ER
- S XMSG="Date: "_$$INDT^XMXUTIL1(XMIM("DATE")) X XMSEN Q:ER
- S XMSG="" X XMSEN Q:ER
- Q
- XMRPOP ;ISC-SF/GMB-POP3 Server (RFC 1939) ;05/20/2002 07:05
- +1 ;;8.0;MailMan;;Jun 28, 2002
- +2 ; Replaces the class III routines ^XMRPOPA, ^XMRPOPB, ^XMRPOPC,
- +3 ; which were written by Chiao-Ming Wu, WASH-ISC.
- +4 ;
- +5 ; Implements RFC 1939 (replaces RFC 1725)
- +6 ; Post Office Protocol - Version 3 (POP3) maildrop service
- +7 ;
- +8 ; Rather than locking the user's IN basket, which severely disrupts
- +9 ; mail delivery, we take a snapshot of it, and keep the snapshot in
- +10 ; a temp global. We then use the temp global during the session.
- +11 ; Here is the layout of the global:
- +12 ;
- +13 ; ^TMP("XM",$J,"POP3")=# msgs^# octets ; total msgs in IN basket
- +14 ; ; (updated if msgs are deleted)
- +15 ; ^TMP("XM",$J,"POP3",1)=XMZ^# octets ; msgs 1 thru n are in
- +16 ; ... ; IN basket.
- +17 ; ^TMP("XM",$J,"POP3",i)=XMZ^# octets ;
- +18 ; ^TMP("XM",$J,"POP3",j)=XMZ^# octets ;
- +19 ; ... ;
- +20 ; ^TMP("XM",$J,"POP3",n)=XMZ^# octets ;
- +21 ; ;
- +22 ; ^TMP("XM",$J,"POP3","D",i)=XMZ ; user deleted msg i
- +23 ; ^TMP("XM",$J,"POP3","D",j)=XMZ ; user deleted msg j
- ENTRY ;
- +1 NEW XMK,XMSTATE,XMCMDS,XMCMD,XMDUZ,XMACCESS,XMVERIFY,XMTRY,XMTMSGS,XMTOCTS,XMV
- +2 IF '$DATA(ZTQUEUED)
- SET X=$SELECT($DATA(^%ZOSF("ERRTN")):^("ERRTN"),1:"ERR^ZU")
- SET @(^%ZOSF("TRAP"))
- +3 IF '$GET(DUZ)
- SET DUZ=.5
- +4 IF '$DATA(XMDUZ)
- SET XMDUZ=DUZ
- +5 IF '$DATA(XMC("BATCH"))
- SET XMC("BATCH")=0
- +6 IF $SELECT('$DATA(XMCHAN):1,XMCHAN="":1,1:0)
- SET XMCHAN="TCP/IP-MAILMAN"
- +7 DO OPEN^XML
- +8 IF $GET(ER)=1
- IF IO'=$GET(IO(0))
- DO ^%ZISC
- WRITE !,"Device open failed !",$CHAR(7)
- QUIT
- +9 IF '$DATA(XM)
- SET XM=""
- +10 IF 'XMC("BATCH")
- XECUTE ^%ZOSF("EOFF")
- SET X=255
- XECUTE ^%ZOSF("RM")
- XECUTE ^%ZOSF("TYPE-AHEAD")
- +11 SET ER=0
- +12 SET XMK=1
- +13 SET XMSG="+OK "_^XMB("NETNAME")_" POP3 server ready (Comments to: POSTMASTER@"_^XMB("NETNAME")_")"
- XECUTE XMSEN
- IF ER
- QUIT
- +14 SET XMCMDS("AUTH")="^PASS^QUIT^USER^"
- +15 SET XMCMDS("TRAN")="^DELE^LIST^NOOP^QUIT^RETR^RSET^STAT^TOP^UIDL^"
- +16 SET XMSTATE="AUTH"
- +17 FOR
- XECUTE XMREC
- IF ER
- QUIT
- Begin DoDot:1
- +18 IF XMRG=""
- SET ER=1
- SET XMCMD=""
- QUIT
- +19 SET XMCMD=$PIECE(XMRG," ",1)
- +20 IF $LENGTH(XMCMD)<3!($LENGTH(XMCMD)>4)!(XMCMD'?.U)
- SET XMSG="-ERR no such command"
- XECUTE XMSEN
- QUIT
- +21 IF $TEXT(@XMCMD)'[";;"
- SET XMSG="-ERR no such command"
- XECUTE XMSEN
- QUIT
- +22 IF XMCMDS(XMSTATE)'[(U_XMCMD_U)=""
- SET XMSG="-ERR no such command in "_XMSTATE_" state"
- XECUTE XMSEN
- QUIT
- +23 DO @XMCMD
- End DoDot:1
- IF XMCMD="QUIT"!ER
- QUIT
- +24 IF ER
- IF $GET(XMCMD)'="QUIT"
- DO QUIT
- +25 QUIT
- DELE ;;
- +1 NEW XMID
- +2 SET XMID=$PIECE(XMRG," ",2,999)
- +3 IF '$$OKID(XMID)
- QUIT
- +4 NEW XMREC,XMZ,XMOCTS
- +5 SET XMZ=+^TMP("XM",$JOB,"POP3",XMID)
- SET XMOCTS=$PIECE(^(XMID),U,2)
- +6 SET ^TMP("XM",$JOB,"POP3","D",XMID)=XMZ
- +7 SET XMREC=^TMP("XM",$JOB,"POP3")
- +8 SET ^TMP("XM",$JOB,"POP3")=($PIECE(XMREC,U,1)-1)_U_($PIECE(XMREC,U,2)-XMOCTS)
- +9 SET XMSG="+OK message "_XMID_" deleted"
- XECUTE XMSEN
- +10 QUIT
- OKID(XMID) ;
- +1 IF XMID=""
- SET XMSG="-ERR message-id required"
- XECUTE XMSEN
- QUIT 0
- +2 IF +XMID'=XMID
- SET XMSG="-ERR improper message-id"
- XECUTE XMSEN
- QUIT 0
- +3 IF '$DATA(^TMP("XM",$JOB,"POP3",XMID))
- SET XMSG="-ERR no such message"
- XECUTE XMSEN
- QUIT 0
- +4 IF $DATA(^TMP("XM",$JOB,"POP3","D",XMID))
- SET XMSG="-ERR message "_XMID_" already deleted"
- XECUTE XMSEN
- QUIT 0
- +5 QUIT 1
- LIST ;;
- +1 NEW XMID,XMOCTS
- +2 SET XMID=$PIECE(XMRG," ",2,999)
- +3 IF XMID=""
- Begin DoDot:1
- +4 SET XMSG="+OK "_$PIECE(^TMP("XM",$JOB,"POP3"),U,1)_" messages ("_$PIECE(^("POP3"),U,2)_" octets)"
- XECUTE XMSEN
- IF ER
- QUIT
- +5 FOR
- SET XMID=$ORDER(^TMP("XM",$JOB,"POP3",XMID))
- IF 'XMID
- QUIT
- SET XMOCTS=$PIECE(^(XMID),U,2)
- Begin DoDot:2
- +6 IF $DATA(^TMP("XM",$JOB,"POP3","D",XMID))
- QUIT
- +7 SET XMSG=XMID_" "_XMOCTS
- XECUTE XMSEN
- End DoDot:2
- IF ER
- QUIT
- +8 SET XMSG="."
- XECUTE XMSEN
- End DoDot:1
- QUIT
- +9 IF '$$OKID(XMID)
- QUIT
- +10 SET XMSG="+OK "_XMID_" "_$PIECE(^TMP("XM",$JOB,"POP3",XMID),U,2)
- XECUTE XMSEN
- +11 QUIT
- NOOP ;;
- +1 SET XMSG="+OK"
- XECUTE XMSEN
- +2 QUIT
- PASS ;;
- +1 IF '$DATA(XMACCESS)
- DO LOGINERR("-ERR sorry, USER access code expected")
- QUIT
- +2 SET XMVERIFY=$PIECE(XMRG," ",2,999)
- +3 IF XMVERIFY'=""
- DO LOGIN
- QUIT
- +4 DO LOGINERR("-ERR sorry, PASS verify code expected")
- +5 QUIT
- LOGIN ;
- +1 NEW XMLOGIN
- +2 SET XMLOGIN=$$LOGINOK
- +3 IF 'XMLOGIN
- DO LOGINERR("-ERR "_$PIECE(XMLOGIN,U,2))
- QUIT
- +4 KILL XMACCESS,XMVERIFY
- +5 SET XMSTATE="TRAN"
- +6 SET XMDUZ=DUZ
- +7 DO INIT^XMVVITAE
- +8 DO MAILDROP
- +9 DO RSET
- +10 QUIT
- LOGINOK() ;
- +1 IF $TEXT(@"USERSET^XUSRA")=""
- QUIT $$OLDCHK
- +2 QUIT $$USERSET^XUSRA(XMACCESS_";"_XMVERIFY)
- OLDCHK() ;
- +1 NEW XUSER,XUF,%1,XMLOGIN
- +2 SET XUF=0
- +3 SET XMLOGIN=$$CHECKAV^XUS(XMACCESS_";"_XMVERIFY)
- +4 IF XMLOGIN
- SET DUZ=XMLOGIN
- QUIT 1
- +5 QUIT "0^Not a valid ACCESS CODE/VERIFY CODE pair"
- MAILDROP ;
- +1 NEW XMKZ,XMZ,XMOCTS,XMID
- +2 KILL ^TMP("XM",$JOB,"POP3")
- +3 SET (XMID,XMKZ,XMTOCTS)=0
- +4 FOR
- SET XMKZ=$ORDER(^XMB(3.7,XMDUZ,2,XMK,1,"C",XMKZ))
- IF 'XMKZ
- QUIT
- Begin DoDot:1
- +5 SET XMZ=$ORDER(^XMB(3.7,XMDUZ,2,XMK,1,"C",XMKZ,0))
- +6 IF '$DATA(^XMB(3.7,XMDUZ,2,XMK,1,XMZ,0))
- DO ADDITC^XMUT4A(XMDUZ,XMK,XMZ,XMKZ)
- +7 IF '$DATA(^XMB(3.9,XMZ,0))
- DO ZAPIT^XMXMSGS2(XMDUZ,XMK,XMZ)
- QUIT
- +8 SET XMID=XMID+1
- +9 SET XMOCTS=$$OCTETS(XMZ)
- +10 SET XMTOCTS=XMTOCTS+XMOCTS
- +11 SET ^TMP("XM",$JOB,"POP3",XMID)=XMZ_U_XMOCTS
- End DoDot:1
- +12 SET XMTMSGS=XMID
- +13 QUIT
- OCTETS(XMZ) ; Returns the number of 'octets' in a message.
- +1 ; Basically, that's a count of the number of characters.
- +2 ; We estimate it by multiplying the number of lines by 50.
- +3 QUIT $PIECE($GET(^XMB(3.9,XMZ,2,0)),U,4)*50
- LOGINERR(XMSG) ;
- +1 KILL XMACCESS,XMVERIFY
- +2 SET XMTRY=$GET(XMTRY)+1
- +3 IF XMTRY<3
- XECUTE XMSEN
- QUIT
- +4 DO SIGNOFF(XMSG_"; 3 tries and you're out!")
- +5 SET XMCMD="QUIT"
- +6 QUIT
- QUIT ;;
- +1 IF XMSTATE="TRAN"
- IF 'ER
- DO UPDATE
- +2 KILL ^TMP("XM",$JOB,"POP3")
- +3 DO SIGNOFF("")
- +4 QUIT
- SIGNOFF(XMSG) ;
- +1 SET XMSG=$SELECT(XMSG'="":XMSG_"; ",ER:"-ERR ",1:"+OK ")_^XMB("NETNAME")_" POP3 server signing off"
- XECUTE XMSEN
- +2 QUIT
- RETR ;;
- +1 NEW XMID
- +2 SET XMID=$PIECE(XMRG," ",2,999)
- +3 IF '$$OKID(XMID)
- QUIT
- +4 SET XMSG="+OK "_$PIECE(^TMP("XM",$JOB,"POP3",XMID),U,2)_" octets"
- XECUTE XMSEN
- IF ER
- QUIT
- +5 DO RETRIEVE(XMID,"*")
- +6 QUIT
- RSET ;;
- +1 KILL ^TMP("XM",$JOB,"POP3","D")
- +2 SET ^TMP("XM",$JOB,"POP3")=XMTMSGS_U_XMTOCTS
- +3 SET XMSG="+OK maildrop has "_XMTMSGS_" messages ("_XMTOCTS_" octets)"
- XECUTE XMSEN
- +4 QUIT
- STAT ;;
- +1 SET XMSG="+OK "_$PIECE(^TMP("XM",$JOB,"POP3"),U,1)_" "_$PIECE(^("POP3"),U,2)
- XECUTE XMSEN
- +2 QUIT
- TOP ;;
- +1 NEW XMID,XMLINES
- +2 SET XMID=$PIECE(XMRG," ",2)
- +3 IF '$$OKID(XMID)
- QUIT
- +4 SET XMLINES=$PIECE(XMRG," ",3,999)
- +5 IF +XMLINES'=XMLINES
- SET XMSG="-ERR improper number of lines"
- XECUTE XMSEN
- QUIT
- +6 SET XMSG="+OK"
- XECUTE XMSEN
- IF ER
- QUIT
- +7 DO RETRIEVE(XMID,XMLINES)
- +8 QUIT
- UIDL ;;
- +1 NEW XMID,XMZ
- +2 SET XMID=$PIECE(XMRG," ",2,999)
- +3 IF XMID=""
- Begin DoDot:1
- +4 SET XMSG="+OK"
- XECUTE XMSEN
- IF ER
- QUIT
- +5 FOR
- SET XMID=$ORDER(^TMP("XM",$JOB,"POP3",XMID))
- IF 'XMID
- QUIT
- SET XMZ=+^(XMID)
- Begin DoDot:2
- +6 IF $DATA(^TMP("XM",$JOB,"POP3","D",XMID))
- QUIT
- +7 SET XMSG=XMID_" "_XMZ
- XECUTE XMSEN
- End DoDot:2
- IF ER
- QUIT
- +8 SET XMSG="."
- XECUTE XMSEN
- End DoDot:1
- QUIT
- +9 IF '$$OKID(XMID)
- QUIT
- +10 SET XMSG="+OK "_XMID_" "_+^TMP("XM",$JOB,"POP3",XMID)
- XECUTE XMSEN
- +11 QUIT
- USER ;;
- +1 SET XMACCESS=$PIECE(XMRG," ",2,999)
- +2 IF XMACCESS'=""
- SET XMSG="+OK"
- XECUTE XMSEN
- QUIT
- +3 DO LOGINERR("-ERR sorry, USER access code expected")
- +4 QUIT
- UPDATE ;
- +1 NEW XMID,XMZ
- +2 SET XMID=0
- +3 FOR
- SET XMID=$ORDER(^TMP("XM",$JOB,"POP3","D",XMID))
- IF 'XMID
- QUIT
- SET XMZ=+^(XMID)
- DO DEL^XMXMSGS2(XMDUZ,"",XMZ)
- +4 QUIT
- RETRIEVE(XMID,XMLINES) ;
- +1 NEW XMZ,XMRESP,XMIM,XMINSTR,XMIU
- +2 SET XMZ=+^TMP("XM",$JOB,"POP3",XMID)
- +3 DO INMSG^XMXUTIL2(XMDUZ,"",XMZ,"","I",.XMIM,.XMINSTR,.XMIU)
- +4 DO RETRXMZ(XMZ,XMLINES,.XMIM)
- IF ER
- QUIT
- +5 IF 'XMLINES
- IF XMIM("RESPS")
- Begin DoDot:1
- +6 FOR XMRESP=XMIU("RESP")+1:1:XMIM("RESPS")
- Begin DoDot:2
- +7 NEW XMIR
- +8 DO INRESP^XMXUTIL2(XMZ,XMRESP,"I",.XMIR)
- IF '$DATA(XMIR)
- QUIT
- +9 IF XMIR("SUBJ")?1"R".N
- SET XMIR("SUBJ")="Re: "_XMIM("SUBJ")
- +10 ; just for visual separation
- SET XMSG=""
- XECUTE XMSEN
- IF ER
- QUIT
- +11 DO RETRXMZ(XMIR("XMZ"),"*",.XMIR,XMZ)
- IF ER
- QUIT
- End DoDot:2
- IF ER
- QUIT
- End DoDot:1
- IF ER
- QUIT
- +12 IF '$TEST
- SET XMRESP=0
- +13 SET XMSG="."
- XECUTE XMSEN
- IF ER
- QUIT
- +14 DO LASTACC^XMXUTIL(XMDUZ,XMK,XMZ,XMRESP,.XMIM,.XMINSTR,.XMIU)
- +15 IF $DATA(^XMB(3.7,XMDUZ,"N0",XMK,XMZ))
- IF +XMRESP=+$PIECE($GET(^XMB(3.9,XMZ,3,0)),U,4)
- DO NONEW^XMXUTIL(XMDUZ,XMK,XMZ,1)
- +16 QUIT
- RETRXMZ(XMZ,XMLINES,XMIM,XMZO) ;
- +1 NEW XMI
- +2 IF $ORDER(^XMB(3.9,XMZ,2,0))'<1
- DO CRE8HDR(XMZ,.XMIM,.XMZO)
- IF ER
- QUIT
- +3 SET XMI=0
- +4 FOR
- SET XMI=$ORDER(^XMB(3.9,XMZ,2,XMI))
- IF 'XMI
- QUIT
- SET XMSG=^(XMI,0)
- IF $EXTRACT(XMSG)="."
- SET XMSG="."_XMSG
- XECUTE XMSEN
- IF ER
- QUIT
- IF XMLINES
- IF XMI'<XMLINES
- QUIT
- +5 QUIT
- CRE8HDR(XMZ,XMIM,XMZO) ;
- +1 SET XMSG="Message-ID: <"_XMZ_"@"_^XMB("NETNAME")_">"
- XECUTE XMSEN
- IF ER
- QUIT
- +2 SET XMSG="From: <"_$$NETNAME^XMXUTIL(XMIM("FROM"))_">"
- XECUTE XMSEN
- IF ER
- QUIT
- +3 SET XMSG="To: <"_XMV("NETNAME")_">"
- XECUTE XMSEN
- IF ER
- QUIT
- +4 SET XMSG="Subject: "_XMIM("SUBJ")
- XECUTE XMSEN
- IF ER
- QUIT
- +5 SET XMSG="Date: "_$$INDT^XMXUTIL1(XMIM("DATE"))
- XECUTE XMSEN
- IF ER
- QUIT
- +6 SET XMSG=""
- XECUTE XMSEN
- IF ER
- QUIT
- +7 QUIT