private void ConsumeParameters(TextBuffer inParameters, TextBuffer outParameters) { PropertyInfo[] properties = GetType().GetProperties(BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic); foreach (var propInfo in properties) { ProtocolKeyAttribute attr = (ProtocolKeyAttribute)Attribute.GetCustomAttribute(propInfo, typeof(ProtocolKeyAttribute)); if (attr != null && (attr.Sender & KeySender.Target) != 0) { if (inParameters[attr.Name] != null) { object value = ProtocolKeyAttribute.GetValueAsObject(inParameters[attr.Name], propInfo.PropertyType); propInfo.GetSetMethod(true).Invoke(this, new object[] { value }); inParameters.Remove(attr.Name); if (attr.Type == KeyType.Negotiated && !_negotiatedParameters.ContainsKey(attr.Name)) { value = propInfo.GetGetMethod(true).Invoke(this, null); outParameters.Add(attr.Name, ProtocolKeyAttribute.GetValueAsString(value, propInfo.PropertyType)); _negotiatedParameters.Add(attr.Name, string.Empty); } } } } _session.ConsumeParameters(inParameters, outParameters); foreach (var param in inParameters.Lines) { outParameters.Add(param.Key, "NotUnderstood"); } }
public override bool GetParameters(TextBuffer textBuffer) { switch (_state) { case State.SendAlgorithm: textBuffer.Add("CHAP_A", "5"); _state = State.ReceiveChallenge; return(false); case State.SendResponse: textBuffer.Add("CHAP_N", _name); textBuffer.Add("CHAP_R", CalcResponse()); _state = State.Finished; return(true); default: throw new InvalidOperationException("Unknown authentication state: " + _state); } }
private void GetParametersToNegotiate(TextBuffer parameters, KeyUsagePhase phase, SessionType sessionType) { PropertyInfo[] properties = GetType().GetProperties(BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic); foreach (var propInfo in properties) { ProtocolKeyAttribute attr = (ProtocolKeyAttribute)Attribute.GetCustomAttribute(propInfo, typeof(ProtocolKeyAttribute)); if (attr != null) { object value = propInfo.GetGetMethod(true).Invoke(this, null); if (attr.ShouldTransmit(value, propInfo.PropertyType, phase, sessionType == SessionType.Discovery)) { parameters.Add(attr.Name, ProtocolKeyAttribute.GetValueAsString(value, propInfo.PropertyType)); _negotiatedParameters.Add(attr.Name, string.Empty); } } } }
private void NegotiateSecurity() { _loginStage = LoginStages.SecurityNegotiation; // // Establish the contents of the request // TextBuffer parameters = new TextBuffer(); GetParametersToNegotiate(parameters, KeyUsagePhase.SecurityNegotiation, _session.SessionType); _session.GetParametersToNegotiate(parameters, KeyUsagePhase.SecurityNegotiation); string authParam = _authenticators[0].Identifier; for (int i = 1; i < _authenticators.Length; ++i) { authParam += "," + _authenticators[i].Identifier; } parameters.Add(AuthMethodParameter, authParam); // // Send the request... // byte[] paramBuffer = new byte[parameters.Size]; parameters.WriteTo(paramBuffer, 0); LoginRequest req = new LoginRequest(this); byte[] packet = req.GetBytes(paramBuffer, 0, paramBuffer.Length, true); _stream.Write(packet, 0, packet.Length); _stream.Flush(); // // Read the response... // TextBuffer settings = new TextBuffer(); ProtocolDataUnit pdu = ReadPdu(); LoginResponse resp = ParseResponse <LoginResponse>(pdu); if (resp.StatusCode != LoginStatusCode.Success) { throw new LoginException("iSCSI Target indicated login failure: " + resp.StatusCode); } if (resp.Continue) { MemoryStream ms = new MemoryStream(); ms.Write(resp.TextData, 0, resp.TextData.Length); while (resp.Continue) { pdu = ReadPdu(); resp = ParseResponse <LoginResponse>(pdu); ms.Write(resp.TextData, 0, resp.TextData.Length); } settings.ReadFrom(ms.GetBuffer(), 0, (int)ms.Length); } else if (resp.TextData != null) { settings.ReadFrom(resp.TextData, 0, resp.TextData.Length); } Authenticator authenticator = null; for (int i = 0; i < _authenticators.Length; ++i) { if (settings[AuthMethodParameter] == _authenticators[i].Identifier) { authenticator = _authenticators[i]; break; } } settings.Remove(AuthMethodParameter); settings.Remove("TargetPortalGroupTag"); if (authenticator == null) { throw new LoginException("iSCSI Target specified an unsupported authentication method: " + settings[AuthMethodParameter]); } parameters = new TextBuffer(); ConsumeParameters(settings, parameters); while (!resp.Transit) { // // Send the request... // parameters = new TextBuffer(); authenticator.GetParameters(parameters); paramBuffer = new byte[parameters.Size]; parameters.WriteTo(paramBuffer, 0); req = new LoginRequest(this); packet = req.GetBytes(paramBuffer, 0, paramBuffer.Length, true); _stream.Write(packet, 0, packet.Length); _stream.Flush(); // // Read the response... // settings = new TextBuffer(); pdu = ReadPdu(); resp = ParseResponse <LoginResponse>(pdu); if (resp.StatusCode != LoginStatusCode.Success) { throw new LoginException("iSCSI Target indicated login failure: " + resp.StatusCode); } if (resp.TextData != null && resp.TextData.Length != 0) { if (resp.Continue) { MemoryStream ms = new MemoryStream(); ms.Write(resp.TextData, 0, resp.TextData.Length); while (resp.Continue) { pdu = ReadPdu(); resp = ParseResponse <LoginResponse>(pdu); ms.Write(resp.TextData, 0, resp.TextData.Length); } settings.ReadFrom(ms.GetBuffer(), 0, (int)ms.Length); } else { settings.ReadFrom(resp.TextData, 0, resp.TextData.Length); } authenticator.SetParameters(settings); } } if (resp.NextStage != NextLoginStage) { throw new LoginException("iSCSI Target wants to transition to a different login stage: " + resp.NextStage + " (expected: " + NextLoginStage + ")"); } _loginStage = resp.NextStage; }
public TargetInfo[] EnumerateTargets() { TextBuffer parameters = new TextBuffer(); parameters.Add(SendTargetsParameter, "All"); byte[] paramBuffer = new byte[parameters.Size]; parameters.WriteTo(paramBuffer, 0); TextRequest req = new TextRequest(this); byte[] packet = req.GetBytes(0, paramBuffer, 0, paramBuffer.Length, true); _stream.Write(packet, 0, packet.Length); _stream.Flush(); ProtocolDataUnit pdu = ReadPdu(); TextResponse resp = ParseResponse <TextResponse>(pdu); TextBuffer buffer = new TextBuffer(); if (resp.TextData != null) { buffer.ReadFrom(resp.TextData, 0, resp.TextData.Length); } List <TargetInfo> targets = new List <TargetInfo>(); string currentTarget = null; List <TargetAddress> currentAddresses = null; foreach (var line in buffer.Lines) { if (currentTarget == null) { if (line.Key != TargetNameParameter) { throw new InvalidProtocolException("Unexpected response parameter " + line.Key + " expected " + TargetNameParameter); } currentTarget = line.Value; currentAddresses = new List <TargetAddress>(); } else if (line.Key == TargetNameParameter) { targets.Add(new TargetInfo(currentTarget, currentAddresses.ToArray())); currentTarget = line.Value; currentAddresses.Clear(); } else if (line.Key == TargetAddressParameter) { currentAddresses.Add(TargetAddress.Parse(line.Value)); } } if (currentTarget != null) { targets.Add(new TargetInfo(currentTarget, currentAddresses.ToArray())); } return(targets.ToArray()); }