public TLVObject SendAPDU(IAPDUMessage message, out ushort sw12) { using (var ms = new MemoryStream()) { message.WriteRawData(ms); var dataToSend = ms.ToArray(); #if DEBUG System.Diagnostics.Debug.WriteLine( string.Format("C-APDU => {0}", string.Join(" ", dataToSend.Select(x => x.ToString("X2"))))); #endif var resp = SendCommand(dataToSend); #if DEBUG System.Diagnostics.Debug.WriteLine( string.Format("R-APDU <= {0}", string.Join(" ", resp.Select(x => x.ToString("X2"))))); #endif if (resp == null || resp.Length < 2) { throw new InvalidOperationException("APDU Response is null or empty"); } sw12 = (ushort)((ushort)(resp[resp.Length - 2] << 8) | (ushort)(resp[resp.Length - 1])); if (resp.Length == 2) { return(null); } using (var respMs = new MemoryStream(resp)) using (var reader = new TLVReader(respMs) { RemoveEMVPadding = IsEmv }) { var res = reader.PeekTagAndLength(); if (res.Item2 > resp.Length - 2) { System.Diagnostics.Debug.WriteLine("Too short result, readjusting length"); message.ExpectedResponseLength = res.Item2 + (int)respMs.Position; return(SendAPDU(message, out sw12)); } respMs.Position = 0; return(reader.ReadTags().First()); } } }
public TLVObject SendAPDU(IAPDUMessage message) { ushort sw12 = 0; var retVal = SendAPDU(message, out sw12); if (sw12 == 0x9000) { return(retVal); } else if (sw12 == 0x6700 && !message.ExpectedResponseLength.HasValue) //Wrong length maybe need to try set expected lenght { message.ExpectedResponseLength = 0xF; return(SendAPDU(message)); } else if (sw12 == 0x6700 && message.ExpectedResponseLength.HasValue && message.ExpectedResponseLength.Value < 0xFFFFFF) { message.ExpectedResponseLength = (message.ExpectedResponseLength << 4) & 0xF; return(SendAPDU(message)); } else { throw new SmartCardReaderException($"SW Status is not OK ({sw12.ToString("X2")})", sw12); } }