- consolidate login procedure into POP3-CONNECT
- logging goes to a port, not a file
- fix error-handling bug in pop3-login
- rename POP3-LOGIN/APOP -> POP3-APOP-LOGIN
- replace POSIX regexp for challenge by SRE
This commit is contained in:
sperber 2003-01-20 14:52:03 +00:00
parent 87deeee77b
commit 74f9e4f704
2 changed files with 50 additions and 50 deletions

View File

@ -45,20 +45,13 @@
;; at the beginning of a line by a single decimal point. ;; at the beginning of a line by a single decimal point.
;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
;;: [host x logfile] -> connection
(define (pop3-connect . args) (define (pop3-connect . args)
(let-optionals (let-optionals args ((host-arg #f)
args (login #f)
((host-arg #f) (password #f)
(logfile #f)) (log #f))
(let* ((host (or (getenv "MAILHOST") (let* ((host (or host-arg
host-arg)) (getenv "MAILHOST")))
(LOG (and logfile
(open-output-file logfile
(if (file-exists? logfile)
(bitwise-ior open/write open/append)
(bitwise-ior open/write open/create))
#o600)))
(hst-info (host-info host)) (hst-info (host-info host))
(hostname (host-info:name hst-info)) (hostname (host-info:name hst-info))
(srvc-info (service-info "pop3" "tcp")) (srvc-info (service-info "pop3" "tcp"))
@ -68,40 +61,51 @@
(service-info:port srvc-info))) (service-info:port srvc-info)))
(connection (make-pop3-connection hostname (connection (make-pop3-connection hostname
sock sock
LOG "" "" #f #f))) log "" "" #f #f)))
(pop3-log connection (pop3-log connection
(format #f "~%-- ~a: opened POP3 connection to ~a" (string-append "-- "
;; (date->string (date)) (date->string (date))
"Dummy date" ; (format-time-zone) is broken in v0.5.1 ": opened POP3 connection to "
hostname)) hostname))
;; read the challenge the server sends in its welcome banner ;; read the challenge the server sends in its welcome banner
(let* ((banner (pop3-read-response connection)) (let* ((banner (pop3-read-response connection))
(match (regexp-search (rx (posix-string "\\+OK .* (<[^>]+>)")) banner)) (match (regexp-search (rx (: "+OK " (* (~ #\<))
#\< (submatch (+ (~ #\>))) #\>))
banner))
(challenge (and match (match:substring match 1)))) (challenge (and match (match:substring match 1))))
(set-pop3-connection-challenge! connection challenge)) (set-pop3-connection-challenge! connection challenge))
connection))) (pop3-login connection login password)
connection)))
;; first try standard USER/PASS authentication, and switch to APOP ;; first try standard USER/PASS authentication, and switch to APOP
;; authentication if the server prefers. ;; authentication if the server prefers.
;;: [string x string] -> status
(define (pop3-login connection . args) (define (pop3-login connection login password)
(let ((netrc (and (< (length args) 2) (netrc-parse)))) (let* ((netrc-record #f)
(let-optionals (get-netrc-record
args (lambda ()
((login (or (netrc-lookup-login netrc (pop3-connection-host-name connection) #f) (cond
(call-error "must provide a login" pop3-login args))) (netrc-record)
(password (or (netrc-lookup-password netrc (else
(pop3-connection-host-name connection) #f) (set! netrc-record (netrc-parse))
(call-error "must provide a password" pop3-login args)))) netrc-record)))))
(with-handler (let ((login (or login
(netrc-lookup-login (get-netrc-record)
(pop3-connection-host-name connection)
#f)))
(password (or password
(netrc-lookup-password (get-netrc-record)
(pop3-connection-host-name connection)
#f))))
(with-fatal-error-handler*
(lambda (result punt) (lambda (result punt)
(if (-ERR? result) (cond
(if (pop3-connection-challenge connection) ((not (pop3-error? result)) (punt))
(pop3-login/APOP connection login password) ((pop3-connection-challenge connection)
(error "login failed")))) (pop3-apop-login connection login password))))
(lambda () (lambda ()
(pop3-send-command connection (format #f "USER ~a" login)) (pop3-send-command connection (format #f "USER ~a" login))
(pop3-send-command connection (format #f "PASS ~a" password)) (pop3-send-command connection (format #f "PASS ~a" password))
@ -109,7 +113,6 @@
(set-pop3-connection-password! connection password) (set-pop3-connection-password! connection password)
(set-pop3-connection-state! connection 'connected)))))) (set-pop3-connection-state! connection 'connected))))))
;; Login to the server using APOP authentication (no cleartext ;; Login to the server using APOP authentication (no cleartext
;; passwords are sent over the network). The server appends a token to ;; passwords are sent over the network). The server appends a token to
;; its welcome message, which is built from the server's fully ;; its welcome message, which is built from the server's fully
@ -133,7 +136,7 @@
;; c4c9334bac560ecc979e58001b3e22fb ;; c4c9334bac560ecc979e58001b3e22fb
;; ;;
;;: connection x string x string -> status ;;: connection x string x string -> status
(define (pop3-login/APOP connection login password) (define (pop3-apop-login connection login password)
(let* ((key (string-append (pop3-connection-challenge connection) (let* ((key (string-append (pop3-connection-challenge connection)
password)) password))
(digest (number->string (digest (number->string
@ -216,10 +219,8 @@
(challenge pop3-connection-challenge set-pop3-connection-challenge!) (challenge pop3-connection-challenge set-pop3-connection-challenge!)
(state pop3-connection-state set-pop3-connection-state!)) (state pop3-connection-state set-pop3-connection-state!))
;; cf /usr/local/src/scheme48-0.49/scheme/rts/condition.scm (define-condition-type 'pop3-error '(error))
(define-condition-type '-ERR '(error)) (define pop3-error? (condition-predicate 'pop3-error))
(define -ERR? (condition-predicate '-ERR))
(define (pop3-check-transaction-state connection caller) (define (pop3-check-transaction-state connection caller)
(if (not (eq? (pop3-connection-state connection) 'connected)) (if (not (eq? (pop3-connection-state connection) 'connected))

View File

@ -127,7 +127,6 @@
(define-interface pop3-interface (define-interface pop3-interface
(export pop3-connect (export pop3-connect
pop3-login
pop3-stat pop3-stat
pop3-get pop3-get
pop3-headers pop3-headers
@ -448,7 +447,7 @@
netrc netrc
define-record-types define-record-types
handle handle
conditions conditions handle-fatal-error
signals signals
(subset srfi-13 (string-index)) (subset srfi-13 (string-index))
let-opt let-opt