Difference between revisions of "Android Software Card Emulation"

From YobiWiki
Jump to navigation Jump to search
m
Line 83: Line 83:
 
$DEV_HOME/bin/AndroidTest.apk || exit 1
 
$DEV_HOME/bin/AndroidTest.apk || exit 1
 
</source>
 
</source>
  +
====Install application====
  +
<source lang=bash>
  +
sudo adb install $DEV_HOME/bin/AndroidTest.apk
  +
</source>
  +
====Create certificate====
  +
As this example is using a certificate to sign data, we need to create it.
  +
<source lang=bash>
  +
cd virtual-pki-card
  +
mkdir cert
  +
cd cert
  +
</source>
  +
Create a template '''mykey.conf''':
  +
<source lang=properties>
  +
[ req ]
  +
default_bits = 1024
  +
distinguished_name = req_distinguished_name
  +
prompt = no
  +
output_password = 1234
  +
  +
[ req_distinguished_name ]
  +
C = BE
  +
ST = MyCity
  +
O = MyOrg
  +
</source>
  +
Create certificate:
  +
<source lang=bash>
  +
openssl req -new -x509 -keyout mykey.pem -out mycert.pem -config mykey.conf
  +
openssl pkcs12 -export -in mycert.pem -inkey mykey.pem -passin pass:1234 -passout pass: > mykey.pfx
  +
</source>
  +
Install it:
  +
<source lang=bash>
  +
sudo adb push mykey.pfx /sdcard/
  +
cp mycert.pem ../se-pki-client/
  +
</source>
  +
On the phone:
  +
<br>Run application "PKI Applet Emulator"
  +
* Install PKCS#12
  +
** no passwd
  +
** if needed create a lock PIN on the phone (to be able to store certs)
  +
** choose cert: select this one, ok
  +
* Set PIN=1234
  +
====Reader application====
  +
Compile:
  +
<source lang=bash>
  +
cd se-pki-client
  +
javac src/org/nick/sepkiclient/Main.java
  +
</source>
  +
Execute:
  +
<source lang=bash>
  +
java -cp src org.nick.sepkiclient.Main 1234 mycert.pem
  +
</source>
  +
<pre>
  +
Place phone/card on reader to start
  +
--> 00A4040006A0000000010101
  +
<-- 9000
  +
--> 800100000431323334
  +
<-- 9000
  +
--> 80020000087369676E206D6521
  +
<-- 7C19AAE869DD6C2A9C4AAB98E65FEFDF88C0764EDDAD1BE660BBA220237BA7F4D46B08080E925737D7DC56A1437C72236C60C17678642450F0EEC178B95A1465BA5B002802D467A03B71506D7C9F69380FBB0ADE8AA346D5FDD4E37D4E22EB193986298AFC4C9BF6B5DDAF060DA0E30CF2219DE173AF04E16678A21B94897769 9000 (128)
  +
  +
Got signature from card: 7C19AAE869DD6C2A9C4AAB98E65FEFDF88C0764EDDAD1BE660BBA220237BA7F4D46B08080E925737D7DC56A1437C72236C60C17678642450F0EEC178B95A1465BA5B002802D467A03B71506D7C9F69380FBB0ADE8AA346D5FDD4E37D4E22EB193986298AFC4C9BF6B5DDAF060DA0E30CF2219DE173AF04E16678A21B94897769
  +
Will use certificate from 'mycert.pem' to verify signature
  +
Issuer: O=MyOrg, ST=MyCity, C=BE
  +
Subject: O=MyOrg, ST=Mycity, C=BE
  +
Not Before: Thu Sep 05 11:46:55 CEST 2013
  +
Not After: Sat Oct 05 11:46:55 CEST 2013
  +
  +
Signature is valid: true
  +
</pre>

Revision as of 09:52, 9 September 2013

Software Card Emulation on Android

Software CE is not possible yet on stock Android but patches have been made for CyanogenMod and they are integrated in the official release since v10.1.

Requirements

Android phone with a PN544 NFC chipset

Installation

Easiest is to install cyanogenmod 10.1 (or more recent if available), see instructions

Example

This example is taken from this very interesting post and its source code, adapted for CyanogenMod 10.1 and compiled under Linux in command line.
It's a small example emulating a card able to do a PIN verify then a signature, a bit like some eIDs.

Compile application

Following instructions how to compile Android app in command line

git clone https://github.com/nelenkov/virtual-pki-card
cd virtual-pki-card/se-emulator
JAVA_HOME=/usr/lib/jvm/java-6-sun-1.6.0.26/
ANDROID_HOME=/your_path_to/android-sdk-linux_x86/
PACKAGE=org.nick.se.emulator
PACKAGE_SLASH=${PACKAGE//.//}
DEV_HOME=$(pwd)
TARGET=android-17
mkdir -p $DEV_HOME/obj
mkdir -p $DEV_HOME/bin
mkdir -p $DEV_HOME/lib

Create dummy keystore

$JAVA_HOME/bin/keytool -genkeypair \
                -validity 10000 \
                -dname "CN=company name,
                        OU=organisational unit,
                        O=organisation,
                        L=location,
                        S=state,
                        C=country code" \
                -keystore $DEV_HOME/AndroidTest.keystore \
                -storepass password \
                -keypass password \
                -alias AndroidTestKey \
                -keyalg RSA \
                -v

Create R.java

$ANDROID_HOME/platform-tools/aapt package -v -f -m \
    -S $DEV_HOME/res -J $DEV_HOME/src -M $DEV_HOME/AndroidManifest.xml \
    -I $ANDROID_HOME/platforms/$TARGET/android.jar || exit 1

Compile Java

$JAVA_HOME/bin/javac -verbose -d $DEV_HOME/obj \
    -classpath "$ANDROID_HOME/platforms/$TARGET/android.jar:$DEV_HOME/obj" \
    -sourcepath $DEV_HOME/src \
    $DEV_HOME/src/$PACKAGE_SLASH/*.java || exit 1

Create DEX

$ANDROID_HOME/platform-tools/dx --dex --verbose \
    --output=$DEV_HOME/bin/classes.dex \
    $DEV_HOME/obj $DEV_HOME/lib || exit 1

Create APK

$ANDROID_HOME/platform-tools/aapt package -v -f \
    -S $DEV_HOME/res -M $DEV_HOME/AndroidManifest.xml \
    -I $ANDROID_HOME/platforms/$TARGET/android.jar \
    -F $DEV_HOME/bin/AndroidTest.unsigned.apk \
    $DEV_HOME/bin || exit 1

Sign APK

$JAVA_HOME/bin/jarsigner -verbose \
    -keystore $DEV_HOME/AndroidTest.keystore \
    -storepass password \
    -keypass password \
    -signedjar $DEV_HOME/bin/AndroidTest.signed.apk \
    $DEV_HOME/bin/AndroidTest.unsigned.apk \
    AndroidTestKey || exit 1

Zip-align APK

$ANDROID_HOME/tools/zipalign -v -f 4 \
    $DEV_HOME/bin/AndroidTest.signed.apk \
    $DEV_HOME/bin/AndroidTest.apk || exit 1

Install application

sudo adb install $DEV_HOME/bin/AndroidTest.apk

Create certificate

As this example is using a certificate to sign data, we need to create it.

cd virtual-pki-card
mkdir cert
cd cert

Create a template mykey.conf:

[ req ]
default_bits           = 1024
distinguished_name     = req_distinguished_name
prompt                 = no
output_password        = 1234

[ req_distinguished_name ]
C                      = BE
ST                     = MyCity
O                      = MyOrg

Create certificate:

openssl req -new -x509 -keyout mykey.pem -out mycert.pem -config mykey.conf
openssl pkcs12 -export -in mycert.pem -inkey mykey.pem -passin pass:1234 -passout pass: > mykey.pfx

Install it:

sudo adb push mykey.pfx /sdcard/
cp mycert.pem ../se-pki-client/

On the phone:
Run application "PKI Applet Emulator"

  • Install PKCS#12
    • no passwd
    • if needed create a lock PIN on the phone (to be able to store certs)
    • choose cert: select this one, ok
  • Set PIN=1234

Reader application

Compile:

cd se-pki-client
javac src/org/nick/sepkiclient/Main.java

Execute:

java -cp src org.nick.sepkiclient.Main 1234 mycert.pem
Place phone/card on reader to start
--> 00A4040006A0000000010101
<-- 9000
--> 800100000431323334
<-- 9000
--> 80020000087369676E206D6521
<-- 7C19AAE869DD6C2A9C4AAB98E65FEFDF88C0764EDDAD1BE660BBA220237BA7F4D46B08080E925737D7DC56A1437C72236C60C17678642450F0EEC178B95A1465BA5B002802D467A03B71506D7C9F69380FBB0ADE8AA346D5FDD4E37D4E22EB193986298AFC4C9BF6B5DDAF060DA0E30CF2219DE173AF04E16678A21B94897769 9000 (128)

Got signature from card: 7C19AAE869DD6C2A9C4AAB98E65FEFDF88C0764EDDAD1BE660BBA220237BA7F4D46B08080E925737D7DC56A1437C72236C60C17678642450F0EEC178B95A1465BA5B002802D467A03B71506D7C9F69380FBB0ADE8AA346D5FDD4E37D4E22EB193986298AFC4C9BF6B5DDAF060DA0E30CF2219DE173AF04E16678A21B94897769
Will use certificate from 'mycert.pem' to verify signature
	Issuer: O=MyOrg, ST=MyCity, C=BE
	Subject: O=MyOrg, ST=Mycity, C=BE
	Not Before: Thu Sep 05 11:46:55 CEST 2013
	Not After: Sat Oct 05 11:46:55 CEST 2013

Signature is valid: true