Index: java/net/deterlab/abac/Credential.java
===================================================================
--- java/net/deterlab/abac/Credential.java	(revision 7ef13e3cc81eaa60349fd3c9d82f156e48d74d19)
+++ java/net/deterlab/abac/Credential.java	(revision 9725efbecb6c75c9087fde12143bd00bce50c796)
@@ -7,4 +7,5 @@
 import java.security.cert.*;
 
+import net.deterlab.abac.Identity;
 
 import org.bouncycastle.asn1.*;
@@ -15,6 +16,5 @@
 
 public class Credential {
-    protected static Vector<X509CertificateObject> s_ids = 
-	new Vector<X509CertificateObject>();
+    protected static Vector<Identity> s_ids = new Vector<Identity>();
     /**
      * Create a credential from a head and tail role. This is only for testing.
@@ -37,14 +37,11 @@
 	m_id = null;
 
-	for (X509CertificateObject id: s_ids) {
+	for (Identity id: s_ids) {
 	    try {
-		m_ac.verify(id.getPublicKey(), "BC");
+		m_ac.verify(id.getCertificate().getPublicKey(), "BC");
 		m_id = id;
 		break;
 	    }
-	    // catch (InvalidKeyException e) { 
-	    catch (Exception e) { 
-		System.err.println("validate" + e);
-	    }
+	    catch (InvalidKeyException e) { }
 	}
 	if (m_id == null) throw new InvalidKeyException("Unknown identity");
@@ -129,28 +126,7 @@
 
     private X509V2AttributeCertificate m_ac;
-    private X509CertificateObject m_id;
+    private Identity m_id;
 
-    public static boolean addIdentity(String filename) throws 
-	CertificateException, NoSuchAlgorithmException,InvalidKeyException,
-	NoSuchProviderException, SignatureException, FileNotFoundException,
-	IOException {
-	    PEMReader pr = new PEMReader(new FileReader(filename));
-	    Object c = pr.readObject();
-
-	    if (c instanceof X509CertificateObject) {
-		X509CertificateObject cert = (X509CertificateObject) c;
-
-		cert.verify(cert.getPublicKey());
-		s_ids.add(cert);
-		return true;
-	    }
-	    else return false;
-    }
-    public static boolean addIdentity(File file) throws 
-	CertificateException, NoSuchAlgorithmException,InvalidKeyException,
-	NoSuchProviderException, SignatureException, FileNotFoundException,
-	IOException {
-	    return addIdentity(file.getPath());
-    }
-
+    public static void addIdentity(Identity id) { s_ids.add(id); }
+    public static Collection<Identity> identities() { return s_ids; }
 }
Index: java/net/deterlab/abac/Identity.java
===================================================================
--- java/net/deterlab/abac/Identity.java	(revision 9725efbecb6c75c9087fde12143bd00bce50c796)
+++ java/net/deterlab/abac/Identity.java	(revision 9725efbecb6c75c9087fde12143bd00bce50c796)
@@ -0,0 +1,73 @@
+package net.deterlab.abac;
+
+import java.io.*;
+
+import java.util.*;
+import java.security.*;
+import java.security.cert.*;
+
+
+import org.bouncycastle.asn1.*;
+import org.bouncycastle.asn1.util.*;
+import org.bouncycastle.asn1.x509.*;
+import org.bouncycastle.x509.*;
+import org.bouncycastle.jce.provider.X509AttrCertParser;
+import org.bouncycastle.jce.provider.X509CertificateObject;
+import org.bouncycastle.openssl.PEMReader;
+
+public class Identity {
+    private X509CertificateObject m_cert;
+    private String m_keyid;
+    private String m_cn;
+
+    public void init(String filename) throws 
+	CertificateException, NoSuchAlgorithmException,InvalidKeyException,
+	NoSuchProviderException, SignatureException, FileNotFoundException,
+	IOException {
+	    PEMReader pr = new PEMReader(new FileReader(filename));
+	    Object c = pr.readObject();
+
+	    if (c instanceof X509CertificateObject) {
+		m_cert = (X509CertificateObject) c;
+		m_cert.verify(m_cert.getPublicKey());
+
+		// Cert is valid, fill in the CN and keyid
+		//
+		//  This little rigamarole is to get to the SHA1 hash of the
+		//  key.
+		PublicKey k = m_cert.getPublicKey();
+		ASN1Sequence seq = (ASN1Sequence) new ASN1InputStream(
+			k.getEncoded()).readObject();
+		SubjectPublicKeyInfo ki = new SubjectPublicKeyInfo(seq);
+		SubjectKeyIdentifier id = 
+		    SubjectKeyIdentifier.createSHA1KeyIdentifier(ki);
+
+		// Now format it into a string for keeps
+		Formatter fmt = new Formatter(new StringWriter());
+		for (byte b: id.getKeyIdentifier())
+		    fmt.format("%02x", b);
+		m_keyid = fmt.out().toString();
+
+		m_cn = m_cert.getSubjectDN().getName();
+		/// XXX: better parse
+		if (m_cn.startsWith("CN=")) m_cn = m_cn.substring(3);
+	    }
+	    else throw new CertificateException("Not an identity certificate");
+    }
+
+    public Identity(String filename) throws 
+	CertificateException, NoSuchAlgorithmException,InvalidKeyException,
+	NoSuchProviderException, SignatureException, FileNotFoundException,
+	IOException { init(filename); }
+
+
+    public Identity(File file) throws 
+	CertificateException, NoSuchAlgorithmException,InvalidKeyException,
+	NoSuchProviderException, SignatureException, FileNotFoundException,
+	IOException { init(file.getPath()); }
+
+    public String getKeyID() { return m_keyid; }
+    public String getName() { return m_cn; }
+    public String toString() { return m_keyid + " (" + m_cn + ")"; }
+    public X509CertificateObject getCertificate() { return m_cert; }
+};
