Merge branch 'master' of ssh://down/oryx/aox
[aox:aox.git] / sasl / plain.cpp
1 // Copyright Oryx Mail Systems GmbH. All enquiries to info@oryx.com, please.
2
3 /*! \class Plain plain.h
4     Implements plain-text authentication (RFC 2595 section 6)
5
6     SASL permits a distinction between the authentication ID (which
7     credentials are checked) and the authorization ID (which is logged
8     in). This class firmly insists that the two be the same.
9
10     Note that there is also a different, incompatible plain-text
11     mechanism offered by some servers and supported by some clients
12     "AUTH=LOGIN", implemented by SaslLogin.
13 */
14
15 #include "plain.h"
16
17 #include "estringlist.h"
18
19
20 /*! Creates a plain-text SASL authentication object on behalf of \a c */
21
22 Plain::Plain( EventHandler *c )
23     : SaslMechanism( c, SaslMechanism::Plain )
24 {
25     setState( AwaitingInitialResponse );
26 }
27
28
29 void Plain::parseResponse( const EString & response )
30 {
31     EString authorizeId;
32     EString authenticateId;
33     EString secret;
34
35     bool ok = parse( authorizeId, authenticateId, secret, response );
36     if ( !ok || authenticateId != authorizeId ) {
37         setState( Failed );
38
39         if ( !ok )
40             log( "PLAIN: Parse error for (?)", Log::Error );
41         else
42             log( "PLAIN: Client supplied two identities: " +
43                  authenticateId.quoted() + ", " +
44                  authorizeId.quoted(), Log::Error );
45         return;
46     }
47
48     setState( Authenticating );
49     setLogin( authenticateId );
50     setSecret( secret );
51     execute();
52 }
53
54
55 /*! Parses an AUTH=PLAIN \a response to extract the \a authenticateId,
56     \a authorizeId, and \a pw.
57 */
58
59 bool Plain::parse( EString & authorizeId, EString & authenticateId,
60                    EString & pw, const EString & response )
61 {
62     EStringList * l = EStringList::split( 0, response );
63     if ( !l || l->count() != 3 )
64         return false;
65
66     EStringList::Iterator i( l );
67     authorizeId = *i;
68     ++i;
69     authenticateId = *i;
70     ++i;
71     pw = *i;
72
73     if ( authenticateId.isEmpty() || pw.isEmpty() )
74         return false;
75
76     if ( authorizeId.isEmpty() )
77         authorizeId = authenticateId;
78
79     return true;
80 }