title: ePassport reading with PN532, Keep Getting SW1 SW2 = 0x69 0x88 (Incorrect Secure Messaging Data Objects)
body: <p>I'm trying to read the EF.COM file from an ePassport (a.k.a MRTD).  </p>
  
  <p>What I have successfully done:</p>
  
  <p>-Selected the ePassport application using the AID 0xA0,0x00,0x00,0x02,0x47,0x10,0x01
  -Requested a challenge nonce from the epassport chip
  -Successfully authenticated by responding to that challenge as per doc9303 appendix 5.
  Doc 9303 can be viewed here: <a href="http://www.icao.int/publications/Documents/9303_p1_v2_cons_en.pdf" rel="nofollow">http://www.icao.int/publications/Documents/9303_p1_v2_cons_en.pdf</a></p>
  
  <p>It worked and now I am attempting to read the EF.COM file using the secure messaging protocol as per ISO 7816-4 and I used the doc9303 appendix 6 examples as a guide. </p>
  
  <p>What my secure messaging code does correctly as per the examples in doc9303:</p>
  
  <p>-It generates the exact same secure APDUs, byte for byte, as those in the doc9303 examples given the same inputs.
  -I have verified that my encryption (3DES w/CBC) is working, as is my MAC algorithm </p>
  
  <p>What I have tried:</p>
  
  <p>So I searched and found two open source implementations of the ePassport/MRTD/doc9303.  One in Python (pyPassport-1.0) and the other in Java (JMRTD). I ordered the ACR122 reader (uses the same NFC chipset - PN532) to try it and it does work.  So I then looked at the code JMRTD and pyPassport use to generate the secure messaging APDUs and it appears as though I am doing the same thing.  Thankfully the JMRTD comes with an option to dump/trace the APDUs to a log file.  Sure enough I am creating the secure messaging APDUs exactly as JMRTD is, I even reverse engineered a session (decrypted the RND.IFD, RND.ICC, K.ICC, session keys, etc..), created a test case and my code does in fact generate the same secure APDU output.  </p>
  
  <p>So I think I am constructing the secure messaging APDUs and DOs (Data Objects) correctly, but after I perform BAC and authenticate and try to read the EF.COM file with a protected APDU I keep getting a 69 88 error (Incorrect secure messaging (SM) data object).  This is similar to the problem reported here although I am not using Android but my own embedded NFC stack: <a href="https://stackoverflow.com/questions/21849601/android-nfc-read-data-from-epassport">Android NFC read data from ePassport</a></p>
  
  <p>I think it may be a setting in the PN532 (NXP NFC Chip) that I need to change but I doubt that since I am authenticating correctly and sending and transmitting data without PN532 errors.  I tried raising the baud rate to 424 kbits/s but that did not fix it. </p>
  
  <p>Here is an example of a secure (protected) APDU that my code generates.  </p>
  
  <p>Raw (unsecured) APDU:<br>
  00 A4 02 0C 02 01 1E </p>
  
  <p>Protected (secure) APDU:
  0C A4 02 0C 15 87 09 01 5B B0 63 B9 2A 0D 71 C0 8E 08 E0 B6 68 D2 14 4F 28 B5 00 </p>
  
  <p>So as per the doc9303 I am constructing a DO87 since command parameters are present, and a DO8E since there is a checksum (MAC) present, but no DO97 since no response payload is expected.  I am using 87 09 01 for the DO87 since the 01 means padding type 80 00 00... and the L is 09 (I guess it includes the 01 - padding indicator byte, this is what is in the examples and APDU traces from JMRTD.)</p>
  
  <p>I have tried removing the Le=0x00 from the end since some language in the 7816-4 doc suggests that, as well as making Lc' 0x16 rather than 0x15 as shown above.  I have also tried making to DO87 to be 87 08 01 instead of 87 09 01 as shown above.  None of that has worked. </p>
  
  <p>I am really desperate here, I've been working on this for some time and just can't figure it out.  Is there something wrong with my protected APDU structure?  Is there a low level PN532 setting I need to change?</p>
  
  <p><em><strong>UPDATE ON 19-March-2014</em></strong>
  Here is the PN532 command/response trace (I annotated it so it's less gobedy gook):</p>
  
  <pre><code>-&gt; GetFirmwareVersion (test command to verify PN532 is awake and online):
  00FF02FED4022A0000 
  0000FF00FF0000 -&gt;ACK
  -&gt; Response to GetFirwareVersion:
  00FF06FAD50332010607E80000 
  
  -&gt; Diagnose, NumTst=0x00:
  00FF12EED400000102030405060708090A0B0C0D0E0FB40000 
  00FF00FF0000 -&gt;ACK
  -&gt; Successfull diagnostic (Data returned):
  00FF12EED501000102030405060708090A0B0C0D0E0FB20000 
  
  -&gt; Diagnose NumTst=0x01:
  00FF03FDD400012B0000 
  00FF00FF0000 -&gt;ACK
  -&gt; Successfull diagnostic (0x00):
  00FF03FDD501002A0000 
  
  -&gt; Diagnose NumTst=0x02:
  00FF03FDD400022A0000 
  00FF00FF0000 -&gt;ACK
  -&gt; Successfull diagnostic (0x00):
  00FF03FDD501002A0000 
  
  -&gt; InListPassiveTarget (max targets one, 106kbit/s Type A anticollision)
  00FF04FCD44A0100E10000 
  00FF00FF0000 -&gt;ACK
  -&gt; Found one target, Tg=0x01, SENS_RES=0x07,0x04, SEL_RES=0x20 
  -&gt; UID = 0x08,0x8B,0x05,0xCF, ATS = 0x05,0x78,0x77,0xB4,0x02 DCS=0x9E:
  00FF11EFD54B010107042004088B05CF057877B4029E0000 
  
  -&gt; inPSL (change baud to 424kbits/s)
  00FF05FBD44E010202D90000
  00FF00FF0000 -&gt; ACK
  00FF03FDD54F00DC0000 -&gt; Status = 0x00, success
  
  -&gt; inDataExchange (select ePassport application w/ AID in doc9303):
  00FF0FF1D4400100A4040C07A0000002471001360000
  00FF00FF0000 -&gt; ACK
  00FF05FBD5410090005A0000 -&gt; SW1SW2 = 9000 (success)
  
  -&gt; inDataExchange  (get nonce/challenge)
  00FF08F8D4400100840000085F0000
  00FF00FF0000 -&gt; ACK
  00FF0DF3D541008EAF826F89F1E5259000A80000 -&gt; SW1SW2 = 9000 (success), RND.ICC = 0x8E,0xAF,0x82,0x6F,0x89,0xF1,0xE5,0x25
  
  -&gt; inDataExchange  (mutual authenticate)
  00FF31CFD4400100820000284782B1700DD4F60373DA6632FCD1AB1E500D46FA11DEBDF9B88C39FCA7FDF8DBBE51F41D52D4B87928310000
  00FF00FF0000 -&gt; ACK
  00FF2DD3D5410055A930856698D46C2AEF3CEDF3C56E71668150F2FECC75E28F42AB2A57CD2BA2F42727AE656CB3F49000470000 -&gt; SW1SW2 = 9000 (success)
  
  -&gt; inDataExchange  (select EF.COM)
  00FF1EE2D440010CA4020C158709012CA8E7AB995D13248E0810061DDC725A159300DB0000
  00FF00FF0000 -&gt;ACK
  00FF05FBD541006988F90000 -&gt; SW1SW2 = 6988 (Incorrect SM Data Objects)..BAH!!
  </code></pre>
  
  <p>The Session details are below:</p>
  
  <pre><code>MRZ = GF043591&lt;586012072309062
  
  Computed values from MRZ:
  
  Kenc = BA 43 43 3B F4 7A AE F8 75 23 4F DF 32 08 20 6D
  Kmac = EA 64 45 CD 62 2C EA EC BF 7C 9B 7C B0 20 B9 5D
  
  
  RND.ICC = 8E AF 82 6F 89 F1 E5 25
  RND.IFD = 23 E8 5A 99 3A 9A C5 B4
  K.IFD = 75 DC 87 E5 0C 8E F3 00 47 D0 B5 32 5E 83 20 4D
  SSC = 89 F1 E5 25 3A 9A C5 B4
  
  The computed E.IFD = 47 82 B1 70 0D D4 F6 03 73 DA 66 32 FC D1 AB 1E 50 0D 46 FA 11 DE BD F9 B8 8C 39 FC A7 FD F8 DB
  
  The computed MAC of the above = BE 51 F4 1D 52 D4 B8 79
  
  The tag's response to the mutual authenticate was:
  
  E[Kenc](RND.ICC) =  55 A9 30 85 66 98 D4 6C
  E[Kenc](RND.IFD) =  2A EF 3C ED F3 C5 6E 71 
  E[Kenc](K.ICC)   =  66 81 50 F2 FE CC 75 E2 8F 42 AB 2A 57 CD 2B A2
  MAC              =  F4 27 27 AE 65 6C B3 F4
  
  The computed session keys:
  KSenc = 4C E6 EF A8 3D 3E DA FB FB 02 1A F2 D5 E0 6E 4F
  KSmac = EA C7 5B 64 D9 80 52 23 4F 64 7A 51 45 7F 40 1A
  </code></pre>