private bool AuthenticateContinue() { for (;;) { // We don't need credential on the continued auth assuming they were captured on the first call. // That should always work, otherwise what if a new credential has been returned? Authorization auth = _connection._authenticationModules[_currentModule].Authenticate(_authResponse, null, _connection, _connection._client.TargetName, _connection._channelBindingToken); if (auth == null) { throw new SmtpException(string.Format(Strings.SmtpAuthenticationFailed)); } IAsyncResult result = AuthCommand.BeginSend(_connection, auth.Message, s_authenticateContinueCallback, this); if (!result.CompletedSynchronously) { return(false); } LineInfo info = AuthCommand.EndSend(result); if ((int)info.StatusCode == 235) { _connection._authenticationModules[_currentModule].CloseContext(_connection); _connection._isConnected = true; InvokeCallback(); return(false); } else if ((int)info.StatusCode != 334) { return(true); } _authResponse = info.Line; } }
private void Authenticate() { //if no credentials were supplied, try anonymous //servers don't appear to anounce that they support anonymous login. if (_connection._credentials != null) { while (++_currentModule < _connection._authenticationModules.Length) { //only authenticate if the auth protocol is supported ISmtpAuthenticationModule module = _connection._authenticationModules[_currentModule]; if (!_connection.AuthSupported(module)) { continue; } NetworkCredential credential = _connection._credentials.GetCredential(_host, _port, module.AuthenticationType); if (credential == null) { continue; } Authorization auth = _connection.SetContextAndTryAuthenticate(module, credential, _outerResult); if (auth != null && auth.Message != null) { IAsyncResult result = AuthCommand.BeginSend(_connection, _connection._authenticationModules[_currentModule].AuthenticationType, auth.Message, s_authenticateCallback, this); if (!result.CompletedSynchronously) { return; } LineInfo info = AuthCommand.EndSend(result); if ((int)info.StatusCode == 334) { _authResponse = info.Line; if (!AuthenticateContinue()) { return; } } else if ((int)info.StatusCode == 235) { module.CloseContext(_connection); _connection._isConnected = true; break; } } } } _connection._isConnected = true; InvokeCallback(); }