public void onSaslError(string errMsg, SASLState newState) { Task.Run(async() => { Logger.Error(errMsg); await XMPP_CONNECTION.OnMessageProcessorFailedAsync(new ConnectionError(ConnectionErrorCode.SASL_FAILED, errMsg), true); state = newState; }); }
private void selectMechanism(ArrayList mechanisms) { string selected = null; foreach (string s in OFFERED_MECHANISMS) { foreach (string m in mechanisms) { if (m.ToLower().Equals(s)) { selected = s; break; } } if (selected != null) { break; } } XMPPAccount sCC = XMPP_CONNECTION.account; switch (selected) { case "scram-sha-1": selectedMechanism = new ScramSHA1SASLMechanism(sCC.user.userId, sCC.user.userPassword); break; case "plain": selectedMechanism = new PlainSASLMechanism(sCC.user.userId, sCC.user.userPassword); break; default: state = SASLState.NO_VALID_MECHANISM; Logger.Error("Failed to select authentication mechanism. No supported mechanism available!"); Task t = XMPP_CONNECTION.onMessageProcessorFailedAsync(new ConnectionError(ConnectionErrorCode.SASL_FAILED, "Failed to select authentication mechanism. No supported mechanism available!"), true); break; } }
//--------------------------------------------------------Misc Methods:---------------------------------------------------------------\\ #region --Misc Methods (Public)-- public override void reset() { state = SASLState.DISCONNECTED; selectedMechanism = null; startListeningForMessages(); }
protected async override Task processMessageAsync(NewValidMessageEventArgs args) { AbstractMessage msg = args.MESSAGE; if (msg.isProcessed()) { return; } switch (state) { case SASLState.DISCONNECTED: if (msg is StreamFeaturesMessage || msg is OpenStreamAnswerMessage) { StreamFeaturesMessage features = null; if (msg is OpenStreamAnswerMessage) { features = (msg as OpenStreamAnswerMessage).getStreamFeaturesMessage(); } else { features = msg as StreamFeaturesMessage; } if (features is null) { return; } ArrayList mechanisms = getMechanisms(features); if (mechanisms is null) { return; } setMessageProcessed(args); selectMechanism(mechanisms); if (selectedMechanism is null) { state = SASLState.ERROR; await XMPP_CONNECTION.OnMessageProcessorFailedAsync(new ConnectionError(ConnectionErrorCode.SASL_FAILED, "selectedMechanism is null"), true); return; } await XMPP_CONNECTION.SendAsync(selectedMechanism.getSelectSASLMechanismMessage(), true); state = SASLState.REQUESTED; } break; case SASLState.REQUESTED: case SASLState.CHALLENGING: if (msg is ScramSHAChallengeMessage) { state = SASLState.CHALLENGING; setMessageProcessed(args); AbstractMessage response = selectedMechanism.generateResponse(msg); if (!(response is null)) { await XMPP_CONNECTION.SendAsync(response, true); } } else if (msg is SASLSuccessMessage) { state = SASLState.CONNECTED; msg.setRestartConnection(AbstractMessage.SOFT_RESTART); setMessageProcessed(args); stopListeningForMessages(); } else if (msg is SASLFailureMessage) { stopListeningForMessages(); SASLFailureMessage saslFailureMessage = msg as SASLFailureMessage; state = SASLState.ERROR; Logger.Error("Error during SASL authentication: " + saslFailureMessage.ERROR_TYPE + "\n" + saslFailureMessage.ERROR_MESSAGE); if (saslFailureMessage.ERROR_TYPE == SASLErrorType.UNKNOWN_ERROR) { await XMPP_CONNECTION.OnMessageProcessorFailedAsync(new ConnectionError(ConnectionErrorCode.SASL_FAILED, "SASL: " + saslFailureMessage.ERROR_MESSAGE), true); } else { await XMPP_CONNECTION.OnMessageProcessorFailedAsync(new ConnectionError(ConnectionErrorCode.SASL_FAILED, "SASL: " + saslFailureMessage.ERROR_TYPE), true); } } break; case SASLState.CONNECTED: break; default: throw new InvalidOperationException("Unexpected value for state: " + state); } }