Example #1
0
        private void buttonXmlToTlv_Click(object sender, EventArgs e)
        {
            TlvData tlv = null;

            var isDone = TryAndOutput(() =>
            {
                var serializer = new XmlSerializer(typeof(TlvData));
                tlv            = (TlvData)serializer.Deserialize(new StringReader(textSource.Text));
            });

            if (!isDone)
            {
                return;
            }

            ConvertAndOutput(() => tlv.ToByteArray().ToHexa());
        }
Example #2
0
        /// <summary>
        /// Builds DGI to be used with STORE DATA command for given records having the same index.
        /// </summary>
        /// <param name="sfi"></param>
        /// <param name="index"></param>
        /// <param name="records"></param>
        /// <returns></returns>
        public string BuildDgi(byte sfi, byte index, IEnumerable <PseRecord> records)
        {
            var tlv70 = new TlvData(0x70, new List <TlvData>());

            foreach (var record in records)
            {
                var tlvs = new List <TlvData> {
                    new TlvData {
                        Tag = 0x4F, Value = record.AdfName.FromHexa()
                    },
                    new TlvData {
                        Tag = 0x50, Value = record.ApplicationLabel.FromString()
                    }
                };

                if (!String.IsNullOrWhiteSpace(record.PreferredName))
                {
                    tlvs.Add(new TlvData {
                        Tag = 0x9F12, Value = record.PreferredName.FromString()
                    });
                }

                if (record.PriorityIndicator.HasValue)
                {
                    tlvs.Add(new TlvData {
                        Tag = 0x87, Value = record.PriorityIndicator.Value.ToByteArray()
                    });
                }

                if (!String.IsNullOrWhiteSpace(record.DiscretionaryData))
                {
                    tlvs.Add(new TlvData {
                        Tag = 0x73, Value = record.DiscretionaryData.FromHexa()
                    });
                }

                var tlv61 = new TlvData(0x61, tlvs);
                tlv70.InnerTlvs.Add(tlv61);
            }

            var dgiLength = TlvDataHelper.ToBerEncodedL((uint)tlv70.Length / 2);

            return($"{sfi:X2}{index:X2}{dgiLength.ToHexa('\0')}{tlv70.ToByteArray().ToHexa()}");
        }
Example #3
0
        /// <summary>
        /// Process the GET PROCESSING OPTIONS phase of an EMV transaction.
        /// </summary>
        /// <returns>Last status word.</returns>
        public UInt16 GetProcessingOptions()
        {
            BeforeGetProcessingOptionsEvent.Raise(this, new EmvEventArgs());

            // If PDOL 9F38 is not supplied in FCI, then used 8300 as UDC; if supplied: build the PDOL in tag 83 L V
            byte[] pdolDataValue;
            if (TlvFci.HasTag(0x9F38))
            {
                // Use PDOL to build tag 83 value
                var pdol   = new DataObjectList(TlvFci.GetTag(0x9F38).Value);
                var tlvAll = new List <TlvData> {
                    TlvFci
                };
                tlvAll.AddRange(TlvTerminalData);
                pdolDataValue = pdol.BuildData(tlvAll);
            }
            else
            {
                pdolDataValue = new byte[0];
            }
            // Build tag 83 with computed value
            var tlvPdolData = new TlvData(0x83, (uint)pdolDataValue.Length, pdolDataValue);

            // Execute GET PROCESSING OPTIONS
            var cAPDU = new CommandAPDU(0x80, 0xA8, 0x00, 0x00, tlvPdolData.Length + 2, tlvPdolData.ToByteArray(), 0);
            var crp   = new CommandResponsePair(cAPDU);

            crp.Transmit(_cardChannel);

            _lastStatusWord = crp.RApdu.StatusWord;

            // If GET RESPONSE needed, do it
            if (crp.RApdu.Sw1 == 0x61)
            {
                _tlvProcessingOptions = new TlvData();

                crp = new CommandResponsePair(new GetResponseCommand(crp.RApdu.Sw2));
                crp.Transmit(_cardChannel);
                _lastStatusWord = crp.RApdu.StatusWord;
            }

            // Finally, store result
            if (crp.RApdu.StatusWord == 0x9000)
            {
                _tlvProcessingOptions = new TlvData(crp.RApdu.Udr);
            }

            AfterGetProcessingOptionsEvent.Raise(this, new EmvEventArgs());

            return(_lastStatusWord);
        }