From 32d17447a258188b2d534bcb0bf65a659ba7b7d0 Mon Sep 17 00:00:00 2001
From: mcentner
Date: Fri, 29 Aug 2008 12:11:34 +0000
Subject: Initial import.
git-svn-id: https://joinup.ec.europa.eu/svn/mocca/trunk@1 8a26b1a7-26f0-462f-b9ef-d0e30c41f5a4
---
.../test/java/at/gv/egiz/smcc/SMCCApplication.java | 46 ++++++++++++++++
smcc/src/test/java/at/gv/egiz/smcc/SWCardTest.java | 63 ++++++++++++++++++++++
2 files changed, 109 insertions(+)
create mode 100644 smcc/src/test/java/at/gv/egiz/smcc/SMCCApplication.java
create mode 100644 smcc/src/test/java/at/gv/egiz/smcc/SWCardTest.java
(limited to 'smcc/src/test/java')
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/SMCCApplication.java b/smcc/src/test/java/at/gv/egiz/smcc/SMCCApplication.java
new file mode 100644
index 00000000..5f4bb67e
--- /dev/null
+++ b/smcc/src/test/java/at/gv/egiz/smcc/SMCCApplication.java
@@ -0,0 +1,46 @@
+/*
+* Copyright 2008 Federal Chancellery Austria and
+* Graz University of Technology
+*
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+package at.gv.egiz.smcc;
+
+import java.util.Locale;
+
+import at.gv.egiz.smcc.util.SMCCHelper;
+
+public class SMCCApplication {
+
+ /**
+ * @param args
+ */
+ public static void main(String[] args) {
+
+ SignatureCard sc = null;
+ SMCCHelper smccHelper = new SMCCHelper();
+ while (smccHelper.getResultCode() != SMCCHelper.CARD_FOUND) {
+ System.out.println("Did not get a signature card ... "+smccHelper.getResultCode());
+ smccHelper.update();
+ try {
+ Thread.sleep(1000);
+ } catch (InterruptedException e) {
+ // TODO Auto-generated catch block
+ e.printStackTrace();
+ }
+ }
+ sc = smccHelper.getSignatureCard(Locale.getDefault());
+ System.out.println("Found supported siganture card: "+sc);
+ }
+
+}
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/SWCardTest.java b/smcc/src/test/java/at/gv/egiz/smcc/SWCardTest.java
new file mode 100644
index 00000000..5448fee2
--- /dev/null
+++ b/smcc/src/test/java/at/gv/egiz/smcc/SWCardTest.java
@@ -0,0 +1,63 @@
+/*
+* Copyright 2008 Federal Chancellery Austria and
+* Graz University of Technology
+*
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+package at.gv.egiz.smcc;
+
+import java.math.BigInteger;
+import java.security.MessageDigest;
+import java.security.NoSuchAlgorithmException;
+
+import at.gv.egiz.smcc.SignatureCard.KeyboxName;
+
+public class SWCardTest implements PINProvider {
+
+ SWCard swCard = new SWCard();
+
+ public static void main(String[] args) throws Exception {
+
+ SWCardTest swCardTest = new SWCardTest();
+ swCardTest.test();
+
+ }
+
+ public void test() throws SignatureCardException, NoSuchAlgorithmException {
+
+ swCard.getCertificate(KeyboxName.CERITIFIED_KEYPAIR);
+ swCard.getCertificate(KeyboxName.SECURE_SIGNATURE_KEYPAIR);
+
+ BigInteger t = BigInteger.valueOf(System.currentTimeMillis());
+
+ MessageDigest messageDigest = MessageDigest.getInstance("SHA-1");
+ byte[] hash = messageDigest.digest(t.toByteArray());
+
+ byte[] signature;
+ signature = swCard.createSignature(hash, KeyboxName.CERITIFIED_KEYPAIR, this);
+ System.out.println(SignatureCardFactory.toString(signature));
+
+ signature = swCard.createSignature(hash, KeyboxName.SECURE_SIGNATURE_KEYPAIR, this);
+ System.out.println(SignatureCardFactory.toString(signature));
+
+ byte[] infobox = swCard.getInfobox("IdentityLink", this, null);
+ System.out.println(SignatureCardFactory.toString(infobox));
+
+ }
+
+ @Override
+ public String providePIN(PINSpec spec, int retries) {
+ return "buerger";
+ }
+
+}
--
cgit v1.2.3
From c2ae3db1bc6dcb8ba3eb3461c05e293917c004ca Mon Sep 17 00:00:00 2001
From: mcentner
Date: Thu, 30 Oct 2008 10:33:29 +0000
Subject: Updated SMCC to use exclusive access and to throw exceptions upon
locked or not activated cards. Improved locale support in the security layer
request and response processing. Fixed issue in STAL which prevented the use
of RSA-SHA1 signatures. Added additional parameters to the applet test pages.
git-svn-id: https://joinup.ec.europa.eu/svn/mocca/trunk@128 8a26b1a7-26f0-462f-b9ef-d0e30c41f5a4
---
.../main/java/at/gv/egiz/bku/gui/PinDocument.java | 2 +-
.../egiz/bku/online/webapp/BKURequestHandler.java | 20 +-
BKUOnline/src/main/webapp/HTTP-ohne.html | 11 +-
BKUOnline/src/main/webapp/appletPage.jsp | 29 +-
.../at/gv/egiz/stal/util/JCEAlgorithmNames.java | 4 +-
.../gv/egiz/bku/binding/HTTPBindingProcessor.java | 3 +-
.../gv/egiz/bku/slcommands/SLCommandContext.java | 17 +-
.../impl/CreateXMLSignatureCommandImpl.java | 4 +-
.../egiz/bku/slcommands/impl/ErrorResultImpl.java | 42 ++-
.../slcommands/impl/InfoboxReadCommandImpl.java | 2 +-
.../gv/egiz/bku/slcommands/impl/SLResultImpl.java | 8 +-
.../bku/slcommands/impl/ErrorResultImplTest.java | 3 +-
smcc/src/main/java/at/gv/egiz/smcc/ACOSCard.java | 348 ++++++++++++---------
.../at/gv/egiz/smcc/AbstractSignatureCard.java | 169 +++++++---
.../at/gv/egiz/smcc/FileNotFoundException.java | 38 +++
.../main/java/at/gv/egiz/smcc/LockedException.java | 38 +++
.../at/gv/egiz/smcc/NotActivatedException.java | 44 +++
.../src/main/java/at/gv/egiz/smcc/STARCOSCard.java | 339 ++++++++++++--------
smcc/src/main/java/at/gv/egiz/smcc/SWCard.java | 79 ++++-
.../at/gv/egiz/smcc/SignatureCardException.java | 2 +-
.../java/at/gv/egiz/smcc/SignatureCardFactory.java | 223 +++++++++++--
.../java/at/gv/egiz/smcc/util/SmartCardIO.java | 3 +-
.../test/java/at/gv/egiz/smcc/STARCOSCardTest.java | 92 ++++++
.../bku/smccstal/InfoBoxReadRequestHandler.java | 8 +
.../gv/egiz/bku/smccstal/SignRequestHandler.java | 10 +-
25 files changed, 1149 insertions(+), 389 deletions(-)
create mode 100644 smcc/src/main/java/at/gv/egiz/smcc/FileNotFoundException.java
create mode 100644 smcc/src/main/java/at/gv/egiz/smcc/LockedException.java
create mode 100644 smcc/src/main/java/at/gv/egiz/smcc/NotActivatedException.java
create mode 100644 smcc/src/test/java/at/gv/egiz/smcc/STARCOSCardTest.java
(limited to 'smcc/src/test/java')
diff --git a/BKUCommonGUI/src/main/java/at/gv/egiz/bku/gui/PinDocument.java b/BKUCommonGUI/src/main/java/at/gv/egiz/bku/gui/PinDocument.java
index 8ae9d7a3..2054ae86 100644
--- a/BKUCommonGUI/src/main/java/at/gv/egiz/bku/gui/PinDocument.java
+++ b/BKUCommonGUI/src/main/java/at/gv/egiz/bku/gui/PinDocument.java
@@ -46,7 +46,7 @@ class PINDocument extends PlainDocument {
@Override
public void insertString(int offs, String str, AttributeSet a) throws BadLocationException {
- if (pinSpec.getMaxLength() >= (getLength() + str.length())) {
+ if (pinSpec.getMaxLength() < 0 || pinSpec.getMaxLength() >= (getLength() + str.length())) {
boolean matches = true;
for (int i = 0; i < str.length(); i++) {
Matcher m = pinPattern.matcher(str.substring(i, i + 1));
diff --git a/BKUOnline/src/main/java/at/gv/egiz/bku/online/webapp/BKURequestHandler.java b/BKUOnline/src/main/java/at/gv/egiz/bku/online/webapp/BKURequestHandler.java
index 6f3b9d7f..9092e3f9 100644
--- a/BKUOnline/src/main/java/at/gv/egiz/bku/online/webapp/BKURequestHandler.java
+++ b/BKUOnline/src/main/java/at/gv/egiz/bku/online/webapp/BKURequestHandler.java
@@ -44,6 +44,8 @@ import at.gv.egiz.org.apache.tomcat.util.http.AcceptLanguage;
*/
public class BKURequestHandler extends SpringBKUServlet {
+ private static final long serialVersionUID = 1L;
+
public final static String REDIRECT_URL = "appletPage.jsp";
protected Log log = LogFactory.getLog(BKURequestHandler.class);
@@ -105,6 +107,8 @@ public class BKURequestHandler extends SpringBKUServlet {
String width = getStringFromStream(bindingProcessor.getFormData("appletWidth"), charset);
String height = getStringFromStream(bindingProcessor.getFormData("appletHeight"), charset);
String background = getStringFromStream(bindingProcessor.getFormData("appletBackground"), charset);
+ String guiStyle = getStringFromStream(bindingProcessor.getFormData("appletGuiStyle"), charset);
+ String hashDataDisplay = getStringFromStream(bindingProcessor.getFormData("appletHashDataDisplay"), charset);
if (width != null) {
try {
log.trace("Found applet width parameter: " + width);
@@ -124,12 +128,16 @@ public class BKURequestHandler extends SpringBKUServlet {
}
}
if (background != null) {
- try {
- log.trace("Found applet background parameter: " + background);
- session.setAttribute("appletBackground", background);
- } catch (NumberFormatException nfe) {
- log.warn(nfe);
- }
+ log.trace("Found applet background parameter: " + background);
+ session.setAttribute("appletBackground", background);
+ }
+ if (guiStyle != null) {
+ log.trace("Found applet GUI style parameter: " + guiStyle);
+ session.setAttribute("appletGuiStyle", guiStyle);
+ }
+ if (hashDataDisplay != null) {
+ log.trace("Found applet hash data display parameter: " + hashDataDisplay);
+ session.setAttribute("appletHashDataDisplay", hashDataDisplay);
}
resp.sendRedirect(REDIRECT_URL);
diff --git a/BKUOnline/src/main/webapp/HTTP-ohne.html b/BKUOnline/src/main/webapp/HTTP-ohne.html
index 1923113e..044432ce 100644
--- a/BKUOnline/src/main/webapp/HTTP-ohne.html
+++ b/BKUOnline/src/main/webapp/HTTP-ohne.html
@@ -92,8 +92,17 @@ legend {
name="appletHeight" value="130" id="appletHeight">
+
+
+ simple
+ advanced
+
+
+
+ external
+ internal
+
-
at.gv.egiz
BKUApplet
+ true
true
diff --git a/BKUOnline/src/main/java/at/gv/egiz/bku/online/webapp/BKURequestHandler.java b/BKUOnline/src/main/java/at/gv/egiz/bku/online/webapp/BKURequestHandler.java
index 3aa6bc19..12166a5a 100644
--- a/BKUOnline/src/main/java/at/gv/egiz/bku/online/webapp/BKURequestHandler.java
+++ b/BKUOnline/src/main/java/at/gv/egiz/bku/online/webapp/BKURequestHandler.java
@@ -24,6 +24,7 @@ import java.util.HashMap;
import java.util.Locale;
import java.util.Map;
+import javax.servlet.RequestDispatcher;
import javax.servlet.ServletException;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
@@ -32,12 +33,12 @@ import javax.servlet.http.HttpSession;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
+import at.gv.egiz.bku.binding.BindingProcessor;
import at.gv.egiz.bku.binding.HTTPBindingProcessor;
import at.gv.egiz.bku.binding.HttpUtil;
import at.gv.egiz.bku.binding.IdFactory;
import at.gv.egiz.bku.utils.StreamUtil;
import at.gv.egiz.org.apache.tomcat.util.http.AcceptLanguage;
-import javax.servlet.RequestDispatcher;
/**
* Handles SL requests and instantiates BindingProcessors
@@ -52,7 +53,8 @@ public class BKURequestHandler extends SpringBKUServlet {
protected Log log = LogFactory.getLog(BKURequestHandler.class);
- private static String getStringFromStream(InputStream is, String encoding) throws IOException {
+ private static String getStringFromStream(InputStream is, String encoding)
+ throws IOException {
if (is == null) {
return null;
}
@@ -63,8 +65,7 @@ public class BKURequestHandler extends SpringBKUServlet {
StreamUtil.copyStream(is, os);
return new String(os.toByteArray(), encoding);
}
-
-
+
protected void doPost(HttpServletRequest req, HttpServletResponse resp)
throws ServletException, java.io.IOException {
log.debug("Got new request");
@@ -75,21 +76,28 @@ public class BKURequestHandler extends SpringBKUServlet {
HttpSession session = req.getSession(false);
if (session != null) {
log.warn("Already a session with id: " + session.getId()
- + " active, continuing");
- RequestDispatcher dispatcher = getServletContext().getNamedDispatcher(BKU_APPLET_JSP);
- log.debug("forward to applet");
- dispatcher.forward(req, resp);
- return;
+ + " active, trying to get Bindingprocessor");
+ BindingProcessor bp = getBindingProcessorManager().getBindingProcessor(
+ IdFactory.getInstance().createId(session.getId()));
+ if (bp != null) {
+ log.debug("Found binding processor, using this one");
+ RequestDispatcher dispatcher = getServletContext().getNamedDispatcher(
+ BKU_APPLET_JSP);
+ log.debug("forward to applet");
+ dispatcher.forward(req, resp);
+ return;
+ }
+ log.debug("Did not find a binding processor, creating new ...");
}
session = req.getSession(true);
if (log.isDebugEnabled()) {
log.debug("Using session id: " + session.getId());
}
-
- HTTPBindingProcessor bindingProcessor;
+ HTTPBindingProcessor bindingProcessor;
bindingProcessor = (HTTPBindingProcessor) getBindingProcessorManager()
- .createBindingProcessor(req.getRequestURL().toString(), session.getId(), locale);
+ .createBindingProcessor(req.getRequestURL().toString(),
+ session.getId(), locale);
Map headerMap = new HashMap();
for (Enumeration headerName = req.getHeaderNames(); headerName
@@ -109,14 +117,20 @@ public class BKURequestHandler extends SpringBKUServlet {
bindingProcessor.consumeRequestStream(req.getInputStream());
req.getInputStream().close();
getBindingProcessorManager().process(bindingProcessor);
-
+
log.trace("Trying to find applet parameters in request");
- String width = getStringFromStream(bindingProcessor.getFormData("appletWidth"), charset);
- String height = getStringFromStream(bindingProcessor.getFormData("appletHeight"), charset);
- String background = getStringFromStream(bindingProcessor.getFormData("appletBackground"), charset);
- String guiStyle = getStringFromStream(bindingProcessor.getFormData("appletGuiStyle"), charset);
- String hashDataDisplay = getStringFromStream(bindingProcessor.getFormData("appletHashDataDisplay"), charset);
- String localeFormParam = getStringFromStream(bindingProcessor.getFormData("locale"), charset);
+ String width = getStringFromStream(bindingProcessor
+ .getFormData("appletWidth"), charset);
+ String height = getStringFromStream(bindingProcessor
+ .getFormData("appletHeight"), charset);
+ String background = getStringFromStream(bindingProcessor
+ .getFormData("appletBackground"), charset);
+ String guiStyle = getStringFromStream(bindingProcessor
+ .getFormData("appletGuiStyle"), charset);
+ String hashDataDisplay = getStringFromStream(bindingProcessor
+ .getFormData("appletHashDataDisplay"), charset);
+ String localeFormParam = getStringFromStream(bindingProcessor
+ .getFormData("locale"), charset);
if (width != null) {
try {
log.trace("Found applet width parameter: " + width);
@@ -148,7 +162,8 @@ public class BKURequestHandler extends SpringBKUServlet {
session.setAttribute("appletHashDataDisplay", hashDataDisplay);
}
if (localeFormParam != null) {
- log.debug("overrule accept-language locale " + locale + " with form param " + localeFormParam);
+ log.debug("overrule accept-language locale " + locale
+ + " with form param " + localeFormParam);
locale = new Locale(localeFormParam);
}
if (locale != null) {
@@ -156,8 +171,9 @@ public class BKURequestHandler extends SpringBKUServlet {
session.setAttribute("locale", locale.toString());
}
- //TODO error if no dispatcher found
- RequestDispatcher dispatcher = getServletContext().getNamedDispatcher(BKU_APPLET_JSP);
+ // TODO error if no dispatcher found
+ RequestDispatcher dispatcher = getServletContext().getNamedDispatcher(
+ BKU_APPLET_JSP);
log.debug("forward to applet");
dispatcher.forward(req, resp);
}
diff --git a/BKUOnline/src/main/webapp/applet/BKUApplet-1.0.2-SNAPSHOT.jar b/BKUOnline/src/main/webapp/applet/BKUApplet-1.0.2-SNAPSHOT.jar
deleted file mode 100644
index 74f00509..00000000
Binary files a/BKUOnline/src/main/webapp/applet/BKUApplet-1.0.2-SNAPSHOT.jar and /dev/null differ
diff --git a/BKUOnline/src/main/webapp/appletPage.jsp b/BKUOnline/src/main/webapp/appletPage.jsp
index ee5f429c..b73ed2f4 100644
--- a/BKUOnline/src/main/webapp/appletPage.jsp
+++ b/BKUOnline/src/main/webapp/appletPage.jsp
@@ -47,7 +47,7 @@
var attributes = {
codebase :'applet',
code :'at.gv.egiz.bku.online.applet.BKUApplet.class',
- archive :'BKUApplet-1.0.2-SNAPSHOT.jar, commons-logging-1.1.1.jar, iaik_jce_me4se-3.04.jar',
+ archive :'BKUApplet.jar, commons-logging-1.1.1.jar, iaik_jce_me4se-3.04.jar',
width : <%=width%>,
height :<%=height%>
};
diff --git a/bkucommon/src/main/java/at/gv/egiz/bku/accesscontroller/AuthenticationClassifier.java b/bkucommon/src/main/java/at/gv/egiz/bku/accesscontroller/AuthenticationClassifier.java
index ed4b9bda..61d3d7a5 100644
--- a/bkucommon/src/main/java/at/gv/egiz/bku/accesscontroller/AuthenticationClassifier.java
+++ b/bkucommon/src/main/java/at/gv/egiz/bku/accesscontroller/AuthenticationClassifier.java
@@ -65,7 +65,8 @@ public class AuthenticationClassifier {
} catch (CertificateParsingException e) {
log.error(e);
}
- if (cert.getExtensionValue("1.2.40.0.10.1.1.1") != null) {
+ if ((cert.getExtensionValue("1.2.40.0.10.1.1.1") != null)
+ || (cert.getExtensionValue("1.2.40.0.10.1.1.2") != null)) {
return true;
}
return false;
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/SMCCApplication.java b/smcc/src/test/java/at/gv/egiz/smcc/SMCCApplication.java
deleted file mode 100644
index 4835865f..00000000
--- a/smcc/src/test/java/at/gv/egiz/smcc/SMCCApplication.java
+++ /dev/null
@@ -1,49 +0,0 @@
-/*
-* Copyright 2008 Federal Chancellery Austria and
-* Graz University of Technology
-*
-* Licensed under the Apache License, Version 2.0 (the "License");
-* you may not use this file except in compliance with the License.
-* You may obtain a copy of the License at
-*
-* http://www.apache.org/licenses/LICENSE-2.0
-*
-* Unless required by applicable law or agreed to in writing, software
-* distributed under the License is distributed on an "AS IS" BASIS,
-* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-* See the License for the specific language governing permissions and
-* limitations under the License.
-*/
-package at.gv.egiz.smcc;
-
-import java.util.Locale;
-
-import org.junit.Ignore;
-
-import at.gv.egiz.smcc.util.SMCCHelper;
-
-@Ignore
-public class SMCCApplication {
-
- /**
- * @param args
- */
- public static void main(String[] args) {
-
- SignatureCard sc = null;
- SMCCHelper smccHelper = new SMCCHelper();
- while (smccHelper.getResultCode() != SMCCHelper.CARD_FOUND) {
- System.out.println("Did not get a signature card ... "+smccHelper.getResultCode());
- smccHelper.update();
- try {
- Thread.sleep(1000);
- } catch (InterruptedException e) {
- // TODO Auto-generated catch block
- e.printStackTrace();
- }
- }
- sc = smccHelper.getSignatureCard(Locale.getDefault());
- System.out.println("Found supported siganture card: "+sc);
- }
-
-}
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/STARCOSCardTest.java b/smcc/src/test/java/at/gv/egiz/smcc/STARCOSCardTest.java
deleted file mode 100644
index 7f421474..00000000
--- a/smcc/src/test/java/at/gv/egiz/smcc/STARCOSCardTest.java
+++ /dev/null
@@ -1,121 +0,0 @@
-/*
-* Copyright 2008 Federal Chancellery Austria and
-* Graz University of Technology
-*
-* Licensed under the Apache License, Version 2.0 (the "License");
-* you may not use this file except in compliance with the License.
-* You may obtain a copy of the License at
-*
-* http://www.apache.org/licenses/LICENSE-2.0
-*
-* Unless required by applicable law or agreed to in writing, software
-* distributed under the License is distributed on an "AS IS" BASIS,
-* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-* See the License for the specific language governing permissions and
-* limitations under the License.
-*/
-package at.gv.egiz.smcc;
-
-import java.io.BufferedReader;
-import java.io.IOException;
-import java.io.InputStreamReader;
-import java.io.OutputStream;
-import java.io.PrintWriter;
-import java.security.MessageDigest;
-import java.security.NoSuchAlgorithmException;
-import java.util.Locale;
-
-import javax.smartcardio.CardException;
-import javax.smartcardio.CommandAPDU;
-import javax.smartcardio.ResponseAPDU;
-
-import org.junit.Ignore;
-
-import sun.misc.HexDumpEncoder;
-
-import at.gv.egiz.smcc.SignatureCard.KeyboxName;
-import at.gv.egiz.smcc.util.SMCCHelper;
-
-@Ignore
-public class STARCOSCardTest {
-
- /**
- * @param args
- * @throws Exception
- */
- public static void main(String[] args) throws Exception {
-
- SMCCHelper helper = new SMCCHelper();
- while (helper.getResultCode() != SMCCHelper.CARD_FOUND) {
- System.out.println("Did not get a signature card ... " + helper.getResultCode());
- helper.update();
- try {
- Thread.sleep(1000);
- } catch (InterruptedException e) {
- e.printStackTrace();
- }
- }
-
- SignatureCard signatureCard = helper.getSignatureCard(Locale.getDefault());
-
- System.out.println("Found '" + signatureCard + "'.");
-
- try {
-// printJavaByteArray(
-// signatureCard.getCertificate(KeyboxName.SECURE_SIGNATURE_KEYPAIR), System.out);
-// printJavaByteArray(
-// signatureCard.getCertificate(KeyboxName.CERITIFIED_KEYPAIR), System.out);
-// System.out. println(new String(signatureCard.getInfobox("IdentityLink", new CommandLinePINProvider(), null)));
-// byte[] infobox = signatureCard.getInfobox("Status", new CommandLinePINProvider(), null);
-// printJavaByteArray(infobox, System.out);
- MessageDigest messageDigest = MessageDigest.getInstance("SHA-1");
- byte[] digest = messageDigest.digest("test".getBytes());
- byte[] signature = signatureCard.createSignature(digest, KeyboxName.SECURE_SIGNATURE_KEYPAIR, new CommandLinePINProvider());
- printJavaByteArray(signature, System.out);
- } catch (SignatureCardException e) {
- e.printStackTrace();
- }
-
- }
-
- public static void printJavaByteArray(byte[] bytes, OutputStream os) {
-
- PrintWriter w = new PrintWriter(os);
-
- w.write("new byte[] {");
- for (int i = 0; i < bytes.length;) {
- if (i % 8 == 0) {
- w.write("\n ");
- }
- w.write("(byte) 0x" + Integer.toHexString(0x0F & (bytes[i] >> 4)) + Integer.toHexString(0x0F & bytes[i]));
- if (++i < bytes.length) {
- w.write(", ");
- }
- }
- w.write("\n};");
- w.flush();
- }
-
- private static class CommandLinePINProvider implements PINProvider {
-
- @Override
- public String providePIN(PINSpec spec, int retries) {
-
- InputStreamReader inputStreamReader = new InputStreamReader(System.in);
- BufferedReader in = new BufferedReader(inputStreamReader);
-
- System.out.print("Enter " + spec.getLocalizedName() + " ["
- + spec.getMinLength() + "-" + spec.getMaxLength() + "] (" + retries
- + " retries):");
-
- try {
- return in.readLine();
- } catch (IOException e) {
- return null;
- }
-
- }
-
- }
-
-}
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/SWCardTest.java b/smcc/src/test/java/at/gv/egiz/smcc/SWCardTest.java
deleted file mode 100644
index 115edc16..00000000
--- a/smcc/src/test/java/at/gv/egiz/smcc/SWCardTest.java
+++ /dev/null
@@ -1,66 +0,0 @@
-/*
-* Copyright 2008 Federal Chancellery Austria and
-* Graz University of Technology
-*
-* Licensed under the Apache License, Version 2.0 (the "License");
-* you may not use this file except in compliance with the License.
-* You may obtain a copy of the License at
-*
-* http://www.apache.org/licenses/LICENSE-2.0
-*
-* Unless required by applicable law or agreed to in writing, software
-* distributed under the License is distributed on an "AS IS" BASIS,
-* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-* See the License for the specific language governing permissions and
-* limitations under the License.
-*/
-package at.gv.egiz.smcc;
-
-import java.math.BigInteger;
-import java.security.MessageDigest;
-import java.security.NoSuchAlgorithmException;
-
-import org.junit.Ignore;
-
-import at.gv.egiz.smcc.SignatureCard.KeyboxName;
-
-@Ignore
-public class SWCardTest implements PINProvider {
-
- SWCard swCard = new SWCard();
-
- public static void main(String[] args) throws Exception {
-
- SWCardTest swCardTest = new SWCardTest();
- swCardTest.test();
-
- }
-
- public void test() throws SignatureCardException, NoSuchAlgorithmException, InterruptedException {
-
- swCard.getCertificate(KeyboxName.CERITIFIED_KEYPAIR);
- swCard.getCertificate(KeyboxName.SECURE_SIGNATURE_KEYPAIR);
-
- BigInteger t = BigInteger.valueOf(System.currentTimeMillis());
-
- MessageDigest messageDigest = MessageDigest.getInstance("SHA-1");
- byte[] hash = messageDigest.digest(t.toByteArray());
-
- byte[] signature;
- signature = swCard.createSignature(hash, KeyboxName.CERITIFIED_KEYPAIR, this);
- System.out.println(SignatureCardFactory.toString(signature));
-
- signature = swCard.createSignature(hash, KeyboxName.SECURE_SIGNATURE_KEYPAIR, this);
- System.out.println(SignatureCardFactory.toString(signature));
-
- byte[] infobox = swCard.getInfobox("IdentityLink", this, null);
- System.out.println(SignatureCardFactory.toString(infobox));
-
- }
-
- @Override
- public String providePIN(PINSpec spec, int retries) {
- return "buerger";
- }
-
-}
--
cgit v1.2.3
From 616e06910051528674165319a1d6d161dff5859c Mon Sep 17 00:00:00 2001
From: clemenso
Date: Fri, 27 Mar 2009 17:33:11 +0000
Subject: 1.1-RC6 (pinpad, pinmgmt, secureviewer)
git-svn-id: https://joinup.ec.europa.eu/svn/mocca/trunk@323 8a26b1a7-26f0-462f-b9ef-d0e30c41f5a4
---
.../gv/egiz/bku/online/applet/AppletBKUWorker.java | 5 +-
.../egiz/bku/online/applet/AppletSecureViewer.java | 79 +--
.../at/gv/egiz/bku/online/applet/BKUApplet.java | 10 +-
.../java/at/gv/egiz/bku/gui/PINManagementGUI.java | 26 +-
.../at/gv/egiz/bku/gui/PINManagementGUIFacade.java | 9 +-
.../java/at/gv/egiz/bku/gui/PINStatusRenderer.java | 2 -
.../smccstal/ext/ManagementPINProviderFactory.java | 13 +-
.../bku/smccstal/ext/PinpadPINProviderFactory.java | 45 +-
.../gv/egiz/bku/gui/ActivationMessages.properties | 6 +-
.../egiz/bku/gui/ActivationMessages_en.properties | 6 +-
.../main/java/at/gv/egiz/bku/gui/BKUGUIFacade.java | 40 +-
.../main/java/at/gv/egiz/bku/gui/BKUGUIImpl.java | 603 +++++++++++++--------
.../java/at/gv/egiz/bku/gui/HashDataViewer.java | 293 ----------
.../at/gv/egiz/bku/gui/SecureViewerDialog.java | 371 +++++++++++++
.../at/gv/egiz/bku/gui/Messages.properties | 3 +-
.../at/gv/egiz/bku/gui/Messages_en.properties | 1 +
.../src/main/resources/images/ChipperlingLogo.png | Bin 0 -> 4035 bytes
.../test/java/at/gv/egiz/bku/gui/BKUGUITest.java | 5 +-
.../test/java/at/gv/egiz/bku/gui/BKUGUIWorker.java | 4 +-
.../at/gv/egiz/bku/local/stal/BKUGuiProxy.java | 8 +
.../at/gv/egiz/bku/local/stal/LocalBKUWorker.java | 3 +-
.../gv/egiz/bku/local/stal/LocalSecureViewer.java | 109 ++++
.../bku/local/stal/LocalSignRequestHandler.java | 83 +--
.../gv/egiz/bku/online/conf/defaultConf.properties | 3 +
BKUOnline/src/main/resources/log4j.properties | 2 +-
BKUOnline/src/main/webapp/SLRequestForm.html | 27 +
.../at/gv/egiz/bku/binding/ExpiryRemoverTest.java | 101 ++--
smcc/src/main/java/at/gv/egiz/smcc/ACOSCard.java | 130 ++---
.../at/gv/egiz/smcc/AbstractSignatureCard.java | 220 ++------
.../src/main/java/at/gv/egiz/smcc/STARCOSCard.java | 234 +++++---
smcc/src/main/java/at/gv/egiz/smcc/SWCard.java | 49 +-
.../main/java/at/gv/egiz/smcc/SignatureCard.java | 15 +-
smcc/src/main/java/at/gv/egiz/smcc/ccid/CCID.java | 77 +++
.../java/at/gv/egiz/smcc/ccid/DefaultReader.java | 264 +++++++++
.../at/gv/egiz/smcc/ccid/GemplusGemPCPinpad.java | 65 +++
.../java/at/gv/egiz/smcc/ccid/ReaderFactory.java | 35 ++
.../test/java/at/gv/egiz/smcc/ACOSCardTest.java | 135 +++++
.../test/java/at/gv/egiz/smcc/STARCOSCardTest.java | 267 +++++++++
.../gv/egiz/bku/smccstal/AbstractPINProvider.java | 2 +-
.../gv/egiz/bku/smccstal/PINProviderFactory.java | 3 +-
.../bku/smccstal/PinpadPINProviderFactory.java | 131 +++--
.../java/at/gv/egiz/bku/smccstal/SecureViewer.java | 11 +-
.../gv/egiz/bku/smccstal/SignRequestHandler.java | 14 +-
.../bku/smccstal/SoftwarePINProviderFactory.java | 25 +-
.../java/at/gv/egiz/smcc/AbstractSMCCSTALTest.java | 7 +-
45 files changed, 2364 insertions(+), 1177 deletions(-)
delete mode 100644 BKUCommonGUI/src/main/java/at/gv/egiz/bku/gui/HashDataViewer.java
create mode 100644 BKUCommonGUI/src/main/java/at/gv/egiz/bku/gui/SecureViewerDialog.java
create mode 100644 BKUCommonGUI/src/main/resources/images/ChipperlingLogo.png
create mode 100644 BKULocal/src/main/java/at/gv/egiz/bku/local/stal/LocalSecureViewer.java
create mode 100644 smcc/src/main/java/at/gv/egiz/smcc/ccid/CCID.java
create mode 100644 smcc/src/main/java/at/gv/egiz/smcc/ccid/DefaultReader.java
create mode 100644 smcc/src/main/java/at/gv/egiz/smcc/ccid/GemplusGemPCPinpad.java
create mode 100644 smcc/src/main/java/at/gv/egiz/smcc/ccid/ReaderFactory.java
create mode 100644 smcc/src/test/java/at/gv/egiz/smcc/ACOSCardTest.java
create mode 100644 smcc/src/test/java/at/gv/egiz/smcc/STARCOSCardTest.java
(limited to 'smcc/src/test/java')
diff --git a/BKUApplet/src/main/java/at/gv/egiz/bku/online/applet/AppletBKUWorker.java b/BKUApplet/src/main/java/at/gv/egiz/bku/online/applet/AppletBKUWorker.java
index 9b9735f6..e8d8976d 100644
--- a/BKUApplet/src/main/java/at/gv/egiz/bku/online/applet/AppletBKUWorker.java
+++ b/BKUApplet/src/main/java/at/gv/egiz/bku/online/applet/AppletBKUWorker.java
@@ -18,6 +18,7 @@ package at.gv.egiz.bku.online.applet;
import at.gv.egiz.bku.smccstal.AbstractBKUWorker;
import at.gv.egiz.bku.gui.BKUGUIFacade;
+import at.gv.egiz.bku.smccstal.SignRequestHandler;
import at.gv.egiz.stal.STALRequest;
import at.gv.egiz.stal.STALResponse;
import at.gv.egiz.stal.SignRequest;
@@ -67,8 +68,10 @@ public class AppletBKUWorker extends AbstractBKUWorker implements Runnable {
STALPortType stalPort = applet.getSTALPort();
STALTranslator stalTranslator = applet.getSTALTranslator();
+ AppletSecureViewer secureViewer =
+ new AppletSecureViewer(gui, stalPort, sessionId);
addRequestHandler(SignRequest.class,
- new AppletSecureViewer(stalPort, sessionId));
+ new SignRequestHandler(secureViewer));
GetNextRequestResponseType nextRequestResp = stalPort.connect(sessionId);
diff --git a/BKUApplet/src/main/java/at/gv/egiz/bku/online/applet/AppletSecureViewer.java b/BKUApplet/src/main/java/at/gv/egiz/bku/online/applet/AppletSecureViewer.java
index e2551e2d..929cecb1 100644
--- a/BKUApplet/src/main/java/at/gv/egiz/bku/online/applet/AppletSecureViewer.java
+++ b/BKUApplet/src/main/java/at/gv/egiz/bku/online/applet/AppletSecureViewer.java
@@ -16,17 +16,8 @@
*/
package at.gv.egiz.bku.online.applet;
+import at.gv.egiz.bku.gui.BKUGUIFacade;
import at.gv.egiz.bku.smccstal.SecureViewer;
-import java.security.DigestException;
-import java.security.MessageDigest;
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.List;
-
-import org.apache.commons.logging.Log;
-import org.apache.commons.logging.LogFactory;
-
-import at.gv.egiz.bku.smccstal.SignRequestHandler;
import at.gv.egiz.stal.HashDataInput;
import at.gv.egiz.stal.impl.ByteArrayHashDataInput;
import at.gv.egiz.stal.service.GetHashDataInputFault;
@@ -34,49 +25,73 @@ import at.gv.egiz.stal.service.STALPortType;
import at.gv.egiz.stal.service.types.GetHashDataInputResponseType;
import at.gv.egiz.stal.service.types.GetHashDataInputType;
import at.gv.egiz.stal.signedinfo.ReferenceType;
+import at.gv.egiz.stal.signedinfo.SignedInfoType;
+import java.awt.event.ActionListener;
+import java.security.DigestException;
+import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.List;
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
/**
- * A SignRequesthandler that obtains hashdata inputs from a STAL webservice and
- * displays these either within the applet or in a separate frame.
- * The internal viewer displays plaintext data only, other mimetypes can be saved to disk.
- * The standalone (frame) viewer displays all mimetypes.
- *
- * (This class depends on STALService and therefore is not part of BKUCommonGUI.)
- *
+ *
* @author Clemens Orthacker
*/
-public class AppletSecureViewer extends SignRequestHandler {
+public class AppletSecureViewer implements SecureViewer {
private static final Log log = LogFactory.getLog(AppletSecureViewer.class);
+
+ protected BKUGUIFacade gui;
protected STALPortType stalPort;
protected String sessId;
+ protected List verifiedDataToBeSigned;
- public AppletSecureViewer(STALPortType stalPort, String sessId) {
- if (stalPort == null || sessId == null) {
+ public AppletSecureViewer(BKUGUIFacade gui, STALPortType stalPort,
+ String sessId) {
+ if (gui == null) {
+ throw new NullPointerException("GUI must not be null");
+ }
+ if (stalPort == null) {
throw new NullPointerException("STAL port must not be null");
}
- this.sessId = sessId;
+ if (sessId == null) {
+ throw new NullPointerException("session id must not be null");
+ }
+ this.gui = gui;
this.stalPort = stalPort;
+ this.sessId = sessId;
}
/**
- * TODO don't throw exceptions
+ * retrieves the data to be signed for
* @param signedReferences
+ * @param okListener
+ * @param okCommand
+ * @param cancelListener
+ * @param cancelCommand
* @throws java.security.DigestException
* @throws java.lang.Exception
*/
@Override
- public void displayDataToBeSigned(List signedReferences)
+ public void displayDataToBeSigned(SignedInfoType signedInfo,
+ ActionListener okListener, String okCommand)
throws DigestException, Exception {
-
- List hdi = getHashDataInput(signedReferences);
- List verifiedHashDataInputs = verifyHashDataInput(signedReferences, hdi);
-
- if (verifiedHashDataInputs.size() > 0) {
- gui.showSecureViewer(verifiedHashDataInputs, this, "hashDataDone");
+
+ if (verifiedDataToBeSigned == null) {
+ log.info("retrieve data to be signed for dsig:SignedInfo " +
+ signedInfo.getId());
+ List hdi =
+ getHashDataInput(signedInfo.getReference());
+ verifiedDataToBeSigned = verifyHashDataInput(signedInfo.getReference(),
+ hdi);
+ }
+ if (verifiedDataToBeSigned.size() > 0) {
+ gui.showSecureViewer(verifiedDataToBeSigned, okListener, okCommand);
} else {
- throw new Exception("No signature data (apart from any QualifyingProperties or a Manifest)");
+ throw new Exception("No data to be signed (apart from any QualifyingProperties or a Manifest)");
}
}
@@ -110,7 +125,7 @@ public class AppletSecureViewer extends SignRequestHandler {
}
}
}
-
+
if (request.getReference().size() < 1) {
log.error("No signature data (apart from any QualifyingProperties or a Manifest) for session " + sessId);
throw new Exception("No signature data (apart from any QualifyingProperties or a Manifest)");
@@ -187,7 +202,7 @@ public class AppletSecureViewer extends SignRequestHandler {
verifiedHashDataInputs.add(new ByteArrayHashDataInput(hdi, signedRefId, mimeType, encoding));
}
}
-
+
return verifiedHashDataInputs;
}
diff --git a/BKUApplet/src/main/java/at/gv/egiz/bku/online/applet/BKUApplet.java b/BKUApplet/src/main/java/at/gv/egiz/bku/online/applet/BKUApplet.java
index a4337bbd..0ddb6dc6 100644
--- a/BKUApplet/src/main/java/at/gv/egiz/bku/online/applet/BKUApplet.java
+++ b/BKUApplet/src/main/java/at/gv/egiz/bku/online/applet/BKUApplet.java
@@ -34,6 +34,7 @@ import at.gv.egiz.bku.gui.BKUGUIFacade;
import at.gv.egiz.bku.gui.BKUGUIImpl;
import at.gv.egiz.stal.service.STALPortType;
import at.gv.egiz.stal.service.STALService;
+import java.applet.AppletContext;
import java.awt.Container;
import javax.xml.namespace.QName;
@@ -207,14 +208,19 @@ public class BKUApplet extends JApplet {
*/
protected void sendRedirect(String sessionId) {
try {
+ AppletContext ctx = getAppletContext();
+ if (ctx == null) {
+ log.error("no applet context (applet might already have been destroyed)");
+ return;
+ }
URL redirectURL = getURLParameter(REDIRECT_URL, sessionId);
String redirectTarget = getParameter(REDIRECT_TARGET);
if (redirectTarget == null) {
log.info("Done. Redirecting to " + redirectURL + " ...");
- getAppletContext().showDocument(redirectURL);
+ ctx.showDocument(redirectURL);
} else {
log.info("Done. Redirecting to " + redirectURL + " (target=" + redirectTarget + ") ...");
- getAppletContext().showDocument(redirectURL, redirectTarget);
+ ctx.showDocument(redirectURL, redirectTarget);
}
} catch (MalformedURLException ex) {
log.warn("Failed to redirect: " + ex.getMessage(), ex);
diff --git a/BKUAppletExt/src/main/java/at/gv/egiz/bku/gui/PINManagementGUI.java b/BKUAppletExt/src/main/java/at/gv/egiz/bku/gui/PINManagementGUI.java
index 159dd29d..d1ca6c00 100644
--- a/BKUAppletExt/src/main/java/at/gv/egiz/bku/gui/PINManagementGUI.java
+++ b/BKUAppletExt/src/main/java/at/gv/egiz/bku/gui/PINManagementGUI.java
@@ -118,18 +118,18 @@ public class PINManagementGUI extends CardMgmtGUI implements PINManagementGUIFac
pinStatusTable.setDefaultRenderer(PINSpec.class, new PINSpecRenderer());
pinStatusTable.setDefaultRenderer(STATUS.class, new PINStatusRenderer(cardmgmtMessages));
pinStatusTable.setTableHeader(null);
-
- pinStatusTable.addMouseMotionListener(new MouseMotionAdapter() {
-
- @Override
- public void mouseMoved(MouseEvent e) {
- if (pinStatusTable.columnAtPoint(e.getPoint()) == 0) {
- pinStatusTable.setCursor(Cursor.getPredefinedCursor(Cursor.HAND_CURSOR));
- } else {
- pinStatusTable.setCursor(Cursor.getDefaultCursor());
- }
- }
- });
+ pinStatusTable.setCursor(Cursor.getPredefinedCursor(Cursor.HAND_CURSOR));
+// pinStatusTable.addMouseMotionListener(new MouseMotionAdapter() {
+//
+// @Override
+// public void mouseMoved(MouseEvent e) {
+// if (pinStatusTable.columnAtPoint(e.getPoint()) == 0) {
+// pinStatusTable.setCursor(Cursor.getPredefinedCursor(Cursor.HAND_CURSOR));
+// } else {
+// pinStatusTable.setCursor(Cursor.getDefaultCursor());
+// }
+// }
+// });
final JButton activateButton = new JButton();
activateButton.setFont(activateButton.getFont().deriveFont(activateButton.getFont().getStyle() & ~java.awt.Font.BOLD));
@@ -392,7 +392,7 @@ public class PINManagementGUI extends CardMgmtGUI implements PINManagementGUIFac
if (pinpad) {
JLabel pinpadLabel = new JLabel();
pinpadLabel.setFont(mgmtLabel.getFont().deriveFont(mgmtLabel.getFont().getStyle() & ~Font.BOLD));
- String pinpadPattern = getMessage(MESSAGE_PINPAD);
+ String pinpadPattern = getMessage(MESSAGE_VERIFYPIN_PINPAD);
pinpadLabel.setText(MessageFormat.format(pinpadPattern,
new Object[] { pinSpec.getLocalizedName(), pinSize }));
diff --git a/BKUAppletExt/src/main/java/at/gv/egiz/bku/gui/PINManagementGUIFacade.java b/BKUAppletExt/src/main/java/at/gv/egiz/bku/gui/PINManagementGUIFacade.java
index 45313f42..f0cc0a27 100644
--- a/BKUAppletExt/src/main/java/at/gv/egiz/bku/gui/PINManagementGUIFacade.java
+++ b/BKUAppletExt/src/main/java/at/gv/egiz/bku/gui/PINManagementGUIFacade.java
@@ -40,13 +40,16 @@ public interface PINManagementGUIFacade extends BKUGUIFacade {
public static final String MESSAGE_ACTIVATE_SUCCESS = "activate.success";
public static final String MESSAGE_CHANGE_SUCCESS = "change.success";
public static final String MESSAGE_PINMGMT = "pin.mgmt";
- public static final String MESSAGE_PINPAD = "pinpad";
- public static final String MESSAGE_CHANGEPIN_PINPAD = "pinpad.change";
+// public static final String MESSAGE_PINPAD = "pinpad";
public static final String MESSAGE_ACTIVATE_PIN = "activate.pin";
public static final String MESSAGE_CHANGE_PIN = "change.pin";
public static final String MESSAGE_VERIFY_PIN = "verify.pin";
public static final String MESSAGE_UNBLOCK_PIN = "unblock.pin";
-
+ public static final String MESSAGE_ACTIVATEPIN_PINPAD = "activate.pinpad";
+ public static final String MESSAGE_CHANGEPIN_PINPAD = "change.pinpad";
+ public static final String MESSAGE_VERIFYPIN_PINPAD = "verify.pinpad";
+ public static final String MESSAGE_UNBLOCKPIN_PINPAD = "unblock.pinpad";
+
public static final String LABEL_OLD_PIN = "label.old.pin";
public static final String LABEL_NEW_PIN = "label.new.pin";
public static final String LABEL_REPEAT_PIN = "label.repeat.pin";
diff --git a/BKUAppletExt/src/main/java/at/gv/egiz/bku/gui/PINStatusRenderer.java b/BKUAppletExt/src/main/java/at/gv/egiz/bku/gui/PINStatusRenderer.java
index 4cb84b77..83ff74f2 100644
--- a/BKUAppletExt/src/main/java/at/gv/egiz/bku/gui/PINStatusRenderer.java
+++ b/BKUAppletExt/src/main/java/at/gv/egiz/bku/gui/PINStatusRenderer.java
@@ -22,8 +22,6 @@ import java.awt.Color;
import java.awt.Font;
import java.util.ResourceBundle;
import javax.swing.table.DefaultTableCellRenderer;
-import org.apache.commons.logging.Log;
-import org.apache.commons.logging.LogFactory;
/**
*
diff --git a/BKUAppletExt/src/main/java/at/gv/egiz/bku/smccstal/ext/ManagementPINProviderFactory.java b/BKUAppletExt/src/main/java/at/gv/egiz/bku/smccstal/ext/ManagementPINProviderFactory.java
index b0dd8766..d635b8df 100644
--- a/BKUAppletExt/src/main/java/at/gv/egiz/bku/smccstal/ext/ManagementPINProviderFactory.java
+++ b/BKUAppletExt/src/main/java/at/gv/egiz/bku/smccstal/ext/ManagementPINProviderFactory.java
@@ -19,6 +19,7 @@ package at.gv.egiz.bku.smccstal.ext;
import at.gv.egiz.smcc.ChangePINProvider;
import at.gv.egiz.bku.gui.PINManagementGUIFacade;
+import at.gv.egiz.smcc.ccid.CCID;
import at.gv.egiz.smcc.PINProvider;
import at.gv.egiz.smcc.SignatureCard;
@@ -33,13 +34,13 @@ public abstract class ManagementPINProviderFactory {
public static ManagementPINProviderFactory getInstance(SignatureCard forCard,
PINManagementGUIFacade gui) {
-// if (forCard.ifdSupportsFeature(SignatureCard.FEATURE_VERIFY_PIN_DIRECT)) {
-//// forCard.ifdSupportsFeature(SignatureCard.FEATURE_MODIFY_PIN_DIRECT)
-// return new PinpadPINProviderFactory(gui);
-//
-// } else {
+ if (forCard.getReader().hasFeature(CCID.FEATURE_VERIFY_PIN_DIRECT)) {
+// forCard.ifdSupportsFeature(SignatureCard.FEATURE_MODIFY_PIN_DIRECT)
+ return new PinpadPINProviderFactory(gui);
+
+ } else {
return new SoftwarePINProviderFactory(gui);
-// }
+ }
}
public abstract PINProvider getVerifyPINProvider();
diff --git a/BKUAppletExt/src/main/java/at/gv/egiz/bku/smccstal/ext/PinpadPINProviderFactory.java b/BKUAppletExt/src/main/java/at/gv/egiz/bku/smccstal/ext/PinpadPINProviderFactory.java
index 4176e0a9..a9ad5ef8 100644
--- a/BKUAppletExt/src/main/java/at/gv/egiz/bku/smccstal/ext/PinpadPINProviderFactory.java
+++ b/BKUAppletExt/src/main/java/at/gv/egiz/bku/smccstal/ext/PinpadPINProviderFactory.java
@@ -73,23 +73,6 @@ public class PinpadPINProviderFactory extends ManagementPINProviderFactory {
showPinpadPINDialog(retries, spec);
retry = true;
return null;
-
-// gui.showPINDialog(type, spec, (retry) ? retries : -1,
-// this, "exec",
-// this, "back");
-//
-// waitForAction();
-//
-// if ("exec".equals(action)) {
-// gui.showWaitDialog(null);
-// retry = true;
-// return gui.getPin();
-// } else if ("back".equals(action)) {
-// throw new CancelledException();
-// } else {
-// log.error("unsupported command " + action);
-// throw new CancelledException();
-// }
}
/**
@@ -111,14 +94,38 @@ public class PinpadPINProviderFactory extends ManagementPINProviderFactory {
title = BKUGUIFacade.TITLE_RETRY;
message = BKUGUIFacade.MESSAGE_RETRIES;
params = new Object[]{String.valueOf(retries)};
- } else {
- title = BKUGUIFacade.TITLE_SIGN;
+ } else if (type == DIALOG.VERIFY) {
+ title = PINManagementGUIFacade.TITLE_VERIFY_PIN;
message = BKUGUIFacade.MESSAGE_ENTERPIN_PINPAD;
String pinSize = String.valueOf(pinSpec.getMinLength());
if (pinSpec.getMinLength() != pinSpec.getMaxLength()) {
pinSize += "-" + pinSpec.getMaxLength();
}
params = new Object[]{pinSpec.getLocalizedName(), pinSize};
+ } else if (type == DIALOG.ACTIVATE) {
+ title = PINManagementGUIFacade.TITLE_ACTIVATE_PIN;
+ message = PINManagementGUIFacade.MESSAGE_ACTIVATEPIN_PINPAD;
+ String pinSize = String.valueOf(pinSpec.getMinLength());
+ if (pinSpec.getMinLength() != pinSpec.getMaxLength()) {
+ pinSize += "-" + pinSpec.getMaxLength();
+ }
+ params = new Object[]{pinSpec.getLocalizedName(), pinSize};
+ } else if (type == DIALOG.CHANGE) {
+ title = PINManagementGUIFacade.TITLE_CHANGE_PIN;
+ message = PINManagementGUIFacade.MESSAGE_CHANGEPIN_PINPAD;
+ String pinSize = String.valueOf(pinSpec.getMinLength());
+ if (pinSpec.getMinLength() != pinSpec.getMaxLength()) {
+ pinSize += "-" + pinSpec.getMaxLength();
+ }
+ params = new Object[]{pinSpec.getLocalizedName(), pinSize};
+ } else { //if (type == DIALOG.UNBLOCK) {
+ title = PINManagementGUIFacade.TITLE_UNBLOCK_PIN;
+ message = PINManagementGUIFacade.MESSAGE_UNBLOCKPIN_PINPAD;
+ String pinSize = String.valueOf(pinSpec.getMinLength());
+ if (pinSpec.getMinLength() != pinSpec.getMaxLength()) {
+ pinSize += "-" + pinSpec.getMaxLength();
+ }
+ params = new Object[]{pinSpec.getLocalizedName(), pinSize};
}
gui.showMessageDialog(title, message, params);
}
diff --git a/BKUAppletExt/src/main/resources/at/gv/egiz/bku/gui/ActivationMessages.properties b/BKUAppletExt/src/main/resources/at/gv/egiz/bku/gui/ActivationMessages.properties
index 4ceacb21..c6d219d4 100644
--- a/BKUAppletExt/src/main/resources/at/gv/egiz/bku/gui/ActivationMessages.properties
+++ b/BKUAppletExt/src/main/resources/at/gv/egiz/bku/gui/ActivationMessages.properties
@@ -24,12 +24,14 @@ title.change.success=Erfolg
# removed message.* prefix to reuse keys as help keys
pin.mgmt=Die Karte verf\u00FCgt \u00FCber {0} PINs
-pinpad={0} ({1} stellig) am Kartenleser eingeben und best\u00E4tigen.
-pinpad.change={0} ({1} stellig) am Kartenleser eingeben und best\u00E4tigen.
activate.pin={0} eingeben und best\u00E4tigen
change.pin={0} eingeben und best\u00E4tigen
unblock.pin=PUK zu {0} eingeben
verify.pin={0} eingeben (TODO: Warning not activated)
+verify.pinpad={0} ({1} stellig) am Kartenleser eingeben (und best\u00E4tigen).
+activate.pinpad={0} ({1} stellig) am Kartenleser eingeben und wiederholen (jeweils best\u00E4tigen).
+change.pinpad=Alte {0} ({1} stellig) am Kartenleser eingeben, danach neue {0} eingeben und wiederholen (jeweils best\u00E4tigen).
+unblock.pinpad={0} ({1} stellig) am Kartenleser eingeben (und best\u00E4tigen).
activate.success={0} wurde erfolgreich aktiviert.
change.success={0} wurde erfolgreich ge\u00E4ndert.
diff --git a/BKUAppletExt/src/main/resources/at/gv/egiz/bku/gui/ActivationMessages_en.properties b/BKUAppletExt/src/main/resources/at/gv/egiz/bku/gui/ActivationMessages_en.properties
index 9178d65c..b4bededf 100644
--- a/BKUAppletExt/src/main/resources/at/gv/egiz/bku/gui/ActivationMessages_en.properties
+++ b/BKUAppletExt/src/main/resources/at/gv/egiz/bku/gui/ActivationMessages_en.properties
@@ -23,11 +23,13 @@ title.change.success=Success
# removed message.* prefix to reuse keys as help keys
pin.mgmt=The smartcard has {0} PINs
-pinpad=Enter {0} ({1} digits) on pinpad and confirm.
-pinpad.change=Enter {0} ({1} digits) on pinpad and confirm.
activate.pin=Enter and confirm {0}
change.pin=Enter and confirm {0}
unblock.pin=Enter PUK for {0}
+verify.pinpad=Enter {0} ({1} digits) on cardreader (and confirm).
+activate.pinpad=Enter {0} ({1} digits) on cardreader and repeat (confirm in each case).
+change.pinpad=Enter old {0} ({1} digits) on cardreader, then enter new {0} and repeat (confirm in each case).
+unblock.pinpad=Enter {0} ({1} digits) on cardreader (and confirm).
activate.success={0} successfully activated
change.success={0} successfully changed
diff --git a/BKUCommonGUI/src/main/java/at/gv/egiz/bku/gui/BKUGUIFacade.java b/BKUCommonGUI/src/main/java/at/gv/egiz/bku/gui/BKUGUIFacade.java
index 1043b6a1..4b079428 100644
--- a/BKUCommonGUI/src/main/java/at/gv/egiz/bku/gui/BKUGUIFacade.java
+++ b/BKUCommonGUI/src/main/java/at/gv/egiz/bku/gui/BKUGUIFacade.java
@@ -43,6 +43,7 @@ public interface BKUGUIFacade {
public static final String MESSAGES_BUNDLE = "at/gv/egiz/bku/gui/Messages";
public static final String DEFAULT_BACKGROUND = "/images/BackgroundChipperling.png";
+ public static final String DEFAULT_ICON = "/images/ChipperlingLogo.png";
public static final String HELP_IMG = "/images/help.png";
public static final String HASHDATA_FONT = "Monospaced";
public static final Color ERROR_COLOR = Color.RED;
@@ -58,6 +59,7 @@ public interface BKUGUIFacade {
public static final String TITLE_WAIT = "title.wait";
public static final String TITLE_HASHDATA = "title.hashdata";
public static final String WINDOWTITLE_SAVE = "windowtitle.save";
+ public static final String WINDOWTITLE_ERROR = "windowtitle.error";
public static final String WINDOWTITLE_SAVEDIR = "windowtitle.savedir";
public static final String WINDOWTITLE_OVERWRITE = "windowtitle.overwrite";
public static final String WINDOWTITLE_VIEWER = "windowtitle.viewer";
@@ -102,42 +104,36 @@ public interface BKUGUIFacade {
public enum Style { tiny, simple, advanced };
-// public void init(Container contentPane, Locale locale, Style guiStyle, URL background, ActionListener helpListener);
-
/**
* BKUWorker needs to init signature card with locale
* @return
*/
public Locale getLocale();
-// public void showWelcomeDialog();
-
- /**
- *
- * @param waitMessage if null, a simple 'please wait' text is displayed
- */
-// public void showWaitDialog(String waitMessage);
-
-// public void showInsertCardDialog(ActionListener cancelListener, String actionCommand);
-
-// public void showCardNotSupportedDialog(ActionListener cancelListener, String actionCommand);
-
public void showCardPINDialog(PINSpec pinSpec, int numRetries,
ActionListener okListener, String okCommand,
ActionListener cancelListener, String cancelCommand);
-// public void showCardPINRetryDialog(PINSpec pinSpec, int numRetries, ActionListener okListener, String okCommand, ActionListener cancelListener, String cancelCommand);
-
- public void showSignaturePINDialog(PINSpec pinSpec, int numRetries, ActionListener signListener, String signCommand, ActionListener cancelListener, String cancelCommand, ActionListener hashdataListener, String hashdataCommand);
-
-// public void showSignaturePINRetryDialog(PINSpec pinSpec, int numRetries, ActionListener okListener, String okCommand, ActionListener cancelListener, String cancelCommand, ActionListener hashdataListener, String hashdataCommand);
+ public void showSignaturePINDialog(PINSpec pinSpec, int numRetries,
+ ActionListener signListener, String signCommand,
+ ActionListener cancelListener, String cancelCommand,
+ ActionListener viewerListener, String viewerCommand);
-// public void showPinpadSignaturePINDialog(PINSpec pinSpec, int retries);
+ public void showPinpadSignaturePINDialog(PINSpec pinSpec, int numRetries,
+ ActionListener viewerListener, String viewerCommand);
public char[] getPin();
- public void showSecureViewer(List signedReferences,
- ActionListener okListener, String okCommand);
+ /**
+ *
+ * @param dataToBeSigned
+ * @param backListener if list of references hides pin dialog, backListener
+ * receives an action when user hits 'back' button (i.e. whenever the pin-dialog
+ * needs to be re-paint)
+ * @param backCommand
+ */
+ public void showSecureViewer(List dataToBeSigned,
+ ActionListener backListener, String backCommand);
public void showErrorDialog(String errorMsgKey, Object[] errorMsgParams,
ActionListener okListener, String okCommand);
diff --git a/BKUCommonGUI/src/main/java/at/gv/egiz/bku/gui/BKUGUIImpl.java b/BKUCommonGUI/src/main/java/at/gv/egiz/bku/gui/BKUGUIImpl.java
index 928be249..a7eebbfd 100644
--- a/BKUCommonGUI/src/main/java/at/gv/egiz/bku/gui/BKUGUIImpl.java
+++ b/BKUCommonGUI/src/main/java/at/gv/egiz/bku/gui/BKUGUIImpl.java
@@ -71,6 +71,7 @@ public class BKUGUIImpl implements BKUGUIFacade {
}
protected HelpMouseListener helpListener;
+ protected SecureViewerDialog secureViewer;
protected Container contentPane;
protected ResourceBundle messages;
@@ -145,13 +146,16 @@ public class BKUGUIImpl implements BKUGUIFacade {
@Override
public void run() {
- log.debug("initializing gui");
+ log.debug("initializing gui [" + Thread.currentThread().getName() + "]");
if (renderIconPanel) {
initIconPanel(background);
initContentPanel(null);
} else {
- initContentPanel(background);
+ initContentPanel((background == null) ?
+ getClass().getResource(DEFAULT_BACKGROUND) :
+ background
+ );
}
GroupLayout layout = new GroupLayout(contentPane);
@@ -159,15 +163,27 @@ public class BKUGUIImpl implements BKUGUIFacade {
if (renderIconPanel) {
layout.setHorizontalGroup(layout.createSequentialGroup()
- .addComponent(iconPanel, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE)
- .addPreferredGap(LayoutStyle.ComponentPlacement.UNRELATED)
- .addComponent(contentPanel, GroupLayout.DEFAULT_SIZE, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE));
- layout.setVerticalGroup(layout.createParallelGroup(GroupLayout.Alignment.LEADING)
- .addComponent(iconPanel, GroupLayout.Alignment.TRAILING, GroupLayout.DEFAULT_SIZE, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
- .addComponent(contentPanel, GroupLayout.DEFAULT_SIZE, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE));
+ .addContainerGap()
+ .addComponent(iconPanel, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE)
+ .addPreferredGap(LayoutStyle.ComponentPlacement.UNRELATED)
+ .addComponent(contentPanel, GroupLayout.DEFAULT_SIZE, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
+ .addContainerGap());
+ layout.setVerticalGroup(layout.createSequentialGroup()
+ .addContainerGap()
+ .addGroup(layout.createParallelGroup(GroupLayout.Alignment.LEADING)
+ .addComponent(iconPanel, GroupLayout.Alignment.TRAILING, GroupLayout.DEFAULT_SIZE, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
+ .addComponent(contentPanel, GroupLayout.DEFAULT_SIZE, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE))
+ .addContainerGap());
} else {
- layout.setHorizontalGroup(layout.createSequentialGroup().addComponent(contentPanel));
- layout.setVerticalGroup(layout.createSequentialGroup().addComponent(contentPanel));
+ layout.setHorizontalGroup(layout.createSequentialGroup()
+ // left border
+ .addContainerGap()
+ .addComponent(contentPanel)
+ .addContainerGap());
+ layout.setVerticalGroup(layout.createSequentialGroup()
+ .addContainerGap()
+ .addComponent(contentPanel)
+ .addContainerGap());
}
}
});
@@ -178,11 +194,12 @@ public class BKUGUIImpl implements BKUGUIFacade {
protected void initIconPanel(URL background) {
if (background == null) {
- background = getClass().getResource(DEFAULT_BACKGROUND);
+ background = getClass().getResource(DEFAULT_ICON);
}
if ("file".equals(background.getProtocol())) {
- log.warn("file:// background images not permitted: " + background);
- background = getClass().getResource(DEFAULT_BACKGROUND);
+ log.warn("file:// background images not permitted: " + background +
+ ", loading default background");
+ background = getClass().getResource(DEFAULT_ICON);
}
log.debug("loading icon panel background " + background);
@@ -194,26 +211,24 @@ public class BKUGUIImpl implements BKUGUIFacade {
iconPanel.setLayout(iconPanelLayout);
iconPanelLayout.setHorizontalGroup(
iconPanelLayout.createSequentialGroup()
- .addContainerGap()
.addComponent(iconLabel, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE));
- // no gap here (contentPanel has containerGap)
iconPanelLayout.setVerticalGroup(
iconPanelLayout.createSequentialGroup()
- .addContainerGap()
- .addComponent(iconLabel, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE)
- .addContainerGap(GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE));
+ .addComponent(iconLabel, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE));
}
protected void initContentPanel(URL background) {
+// if (background == null) {
+// background = getClass().getResource(DEFAULT_BACKGROUND);
+// }
if (background == null) {
- background = getClass().getResource(DEFAULT_BACKGROUND);
- }
- if (background == null) {
+ log.debug("no background image set");
contentPanel = new JPanel();
} else {
if ("file".equals(background.getProtocol())) {
- log.warn("file:// background images not permitted: " + background);
+ log.warn("file:// background images not permitted: " + background +
+ ", loading default background");
background = getClass().getResource(DEFAULT_BACKGROUND);
}
log.debug("loading background " + background);
@@ -257,34 +272,29 @@ public class BKUGUIImpl implements BKUGUIFacade {
GroupLayout contentPanelLayout = new GroupLayout(contentPanel);
contentPanel.setLayout(contentPanelLayout);
- GroupLayout.ParallelGroup horizontalContentInner = contentPanelLayout.createParallelGroup(GroupLayout.Alignment.LEADING);
+ // align header, main and button to the right
+ GroupLayout.ParallelGroup horizontalContent =
+ contentPanelLayout.createParallelGroup(GroupLayout.Alignment.TRAILING); //LEADING);
+ GroupLayout.SequentialGroup verticalContent =
+ contentPanelLayout.createSequentialGroup();
+
if (renderHeaderPanel) {
- horizontalContentInner
+ horizontalContent
.addComponent(headerPanel, 0, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE);
+ verticalContent
+ .addComponent(headerPanel, 0, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE)
+ .addPreferredGap(LayoutStyle.ComponentPlacement.RELATED);
+
}
- horizontalContentInner
+ horizontalContent
.addComponent(mainPanel, 0, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
- .addComponent(buttonPanel, 0, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE);
- GroupLayout.SequentialGroup horizontalContentOuter = contentPanelLayout.createSequentialGroup();
- if (!renderIconPanel) {
- horizontalContentOuter
- .addContainerGap();
- }
- horizontalContentOuter
- .addGroup(horizontalContentInner)
- .addContainerGap();
- contentPanelLayout.setHorizontalGroup(horizontalContentOuter);
-
- GroupLayout.SequentialGroup verticalContent = contentPanelLayout.createSequentialGroup();
- verticalContent.addContainerGap();
- if (renderHeaderPanel) {
- verticalContent.addComponent(headerPanel, 0, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE)
- .addPreferredGap(LayoutStyle.ComponentPlacement.RELATED);
- }
- verticalContent.addComponent(mainPanel, 0, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
- .addPreferredGap(LayoutStyle.ComponentPlacement.UNRELATED)
- .addComponent(buttonPanel, 0, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE)
- .addContainerGap();
+ .addComponent(buttonPanel, 0, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE); //Short.MAX_VALUE);
+ verticalContent
+ .addComponent(mainPanel, 0, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
+ .addPreferredGap(LayoutStyle.ComponentPlacement.UNRELATED)
+ .addComponent(buttonPanel, 0, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE);
+
+ contentPanelLayout.setHorizontalGroup(horizontalContent); //Outer);
contentPanelLayout.setVerticalGroup(verticalContent);
}
@@ -521,7 +531,7 @@ public class BKUGUIImpl implements BKUGUIFacade {
@Override
public void run() {
- log.debug("show card-pin dialog");
+ log.debug("show card-pin dialog [" + Thread.currentThread().getName() + "]");
mainPanel.removeAll();
buttonPanel.removeAll();
@@ -653,7 +663,6 @@ public class BKUGUIImpl implements BKUGUIFacade {
buttonPanel.setLayout(buttonPanelLayout);
GroupLayout.SequentialGroup buttonHorizontal = buttonPanelLayout.createSequentialGroup()
- .addContainerGap(GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
.addComponent(okButton, GroupLayout.PREFERRED_SIZE, buttonSize, GroupLayout.PREFERRED_SIZE);
GroupLayout.Group buttonVertical;
@@ -700,6 +709,128 @@ public class BKUGUIImpl implements BKUGUIFacade {
// showSignaturePINDialog(pinSpec, -1, signListener, signCommand, cancelListener, cancelCommand, hashdataListener, hashdataCommand);
// }
+ @Override
+ public void showPinpadSignaturePINDialog(final PINSpec pinSpec, final int numRetries,
+// final ActionListener cancelListener, final String cancelCommand,
+ final ActionListener hashdataListener, final String hashdataCommand) {
+
+ log.debug("scheduling pinpad signature-pin dialog");
+
+ SwingUtilities.invokeLater(new Runnable() {
+
+ @Override
+ public void run() {
+
+ log.debug("show pinpad signature-pin dialog [" + Thread.currentThread().getName() + "]");
+
+ mainPanel.removeAll();
+ buttonPanel.removeAll();
+
+ if (renderHeaderPanel) {
+ if (numRetries < 0) {
+ titleLabel.setText(getMessage(TITLE_SIGN));
+ } else {
+ titleLabel.setText(getMessage(TITLE_RETRY));
+ }
+ }
+
+ JLabel infoLabel = new JLabel();
+ if (numRetries < 0) {
+ infoLabel.setFont(infoLabel.getFont().deriveFont(infoLabel.getFont().getStyle() & ~java.awt.Font.BOLD));
+ if (shortText) {
+ infoLabel.setText(getMessage(MESSAGE_HASHDATALINK_TINY));
+ } else {
+ infoLabel.setText(getMessage(MESSAGE_HASHDATALINK));
+ }
+ infoLabel.setCursor(Cursor.getPredefinedCursor(Cursor.HAND_CURSOR));
+ infoLabel.setForeground(HYPERLINK_COLOR);
+ infoLabel.addMouseListener(new MouseAdapter() {
+
+ @Override
+ public void mouseClicked(MouseEvent me) {
+ ActionEvent e = new ActionEvent(this, ActionEvent.ACTION_PERFORMED, hashdataCommand);
+ hashdataListener.actionPerformed(e);
+ }
+ });
+ helpListener.setHelpTopic(HELP_SIGNPIN);
+ } else {
+ String retryPattern;
+ if (numRetries < 2) {
+ retryPattern = getMessage(MESSAGE_LAST_RETRY);
+ } else {
+ retryPattern = getMessage(MESSAGE_RETRIES);
+ }
+ infoLabel.setText(MessageFormat.format(retryPattern, new Object[]{String.valueOf(numRetries)}));
+ infoLabel.setFont(infoLabel.getFont().deriveFont(infoLabel.getFont().getStyle() | java.awt.Font.BOLD));
+ infoLabel.setForeground(ERROR_COLOR);
+ helpListener.setHelpTopic(HELP_RETRY);
+ }
+
+ String pinSize = String.valueOf(pinSpec.getMinLength());
+ if (pinSpec.getMinLength() != pinSpec.getMaxLength()) {
+ pinSize += "-" + pinSpec.getMaxLength();
+ }
+
+ String msgPattern = getMessage(MESSAGE_ENTERPIN_PINPAD);
+ String msg = MessageFormat.format(msgPattern, new Object[] {
+ pinSpec.getLocalizedName(), pinSize });
+
+ JLabel msgLabel = new JLabel();
+ msgLabel.setFont(msgLabel.getFont().deriveFont(msgLabel.getFont().getStyle() & ~Font.BOLD));
+ msgLabel.setText(msg);
+
+ GroupLayout mainPanelLayout = new GroupLayout(mainPanel);
+ mainPanel.setLayout(mainPanelLayout);
+
+ GroupLayout.SequentialGroup infoHorizontal = mainPanelLayout.createSequentialGroup()
+ .addComponent(infoLabel);
+ GroupLayout.ParallelGroup infoVertical = mainPanelLayout.createParallelGroup(GroupLayout.Alignment.LEADING)
+ .addComponent(infoLabel);
+
+ if (!renderHeaderPanel) {
+ infoHorizontal
+ .addPreferredGap(LayoutStyle.ComponentPlacement.UNRELATED, 0, Short.MAX_VALUE)
+ .addComponent(helpLabel);
+ infoVertical
+ .addComponent(helpLabel);
+ }
+
+ mainPanelLayout.setHorizontalGroup(
+ mainPanelLayout.createParallelGroup(GroupLayout.Alignment.LEADING)
+ .addGroup(infoHorizontal)
+ .addComponent(msgLabel));
+
+ mainPanelLayout.setVerticalGroup(
+ mainPanelLayout.createSequentialGroup()
+ .addGroup(infoVertical)
+ .addPreferredGap(LayoutStyle.ComponentPlacement.RELATED)
+ .addComponent(msgLabel));
+
+ //no cancel button (cancel via pinpad)
+// if (renderCancelButton) {
+// JButton cancelButton = new JButton();
+// cancelButton.setFont(cancelButton.getFont().deriveFont(cancelButton.getFont().getStyle() & ~java.awt.Font.BOLD));
+// cancelButton.setText(getMessage(BUTTON_CANCEL));
+// cancelButton.setActionCommand(cancelCommand);
+// cancelButton.addActionListener(cancelListener);
+//
+// GroupLayout buttonPanelLayout = new GroupLayout(buttonPanel);
+// buttonPanel.setLayout(buttonPanelLayout);
+//
+// GroupLayout.SequentialGroup buttonHorizontal = buttonPanelLayout.createSequentialGroup()
+// .addComponent(cancelButton, GroupLayout.PREFERRED_SIZE, buttonSize, GroupLayout.PREFERRED_SIZE);
+// GroupLayout.SequentialGroup buttonVertical = buttonPanelLayout.createSequentialGroup()
+// .addComponent(cancelButton);
+//
+// buttonPanelLayout.setHorizontalGroup(buttonHorizontal);
+// buttonPanelLayout.setVerticalGroup(buttonVertical);
+// }
+
+ contentPanel.validate();
+ }
+ });
+ }
+
@Override
public void showSignaturePINDialog(final PINSpec pinSpec, final int numRetries,
final ActionListener signListener, final String signCommand,
@@ -717,7 +848,7 @@ public class BKUGUIImpl implements BKUGUIFacade {
@Override
public void run() {
- log.debug("show signature-pin dialog");
+ log.debug("show signature-pin dialog [" + Thread.currentThread().getName() + "]");
mainPanel.removeAll();
buttonPanel.removeAll();
@@ -730,6 +861,38 @@ public class BKUGUIImpl implements BKUGUIFacade {
}
}
+ JLabel infoLabel = new JLabel();
+ if (numRetries < 0) {
+ infoLabel.setFont(infoLabel.getFont().deriveFont(infoLabel.getFont().getStyle() & ~java.awt.Font.BOLD));
+ if (shortText) {
+ infoLabel.setText(getMessage(MESSAGE_HASHDATALINK_TINY));
+ } else {
+ infoLabel.setText(getMessage(MESSAGE_HASHDATALINK));
+ }
+ infoLabel.setCursor(Cursor.getPredefinedCursor(Cursor.HAND_CURSOR));
+ infoLabel.setForeground(HYPERLINK_COLOR);
+ infoLabel.addMouseListener(new MouseAdapter() {
+
+ @Override
+ public void mouseClicked(MouseEvent me) {
+ ActionEvent e = new ActionEvent(this, ActionEvent.ACTION_PERFORMED, hashdataCommand);
+ hashdataListener.actionPerformed(e);
+ }
+ });
+ helpListener.setHelpTopic(HELP_SIGNPIN);
+ } else {
+ String retryPattern;
+ if (numRetries < 2) {
+ retryPattern = getMessage(MESSAGE_LAST_RETRY);
+ } else {
+ retryPattern = getMessage(MESSAGE_RETRIES);
+ }
+ infoLabel.setText(MessageFormat.format(retryPattern, new Object[]{String.valueOf(numRetries)}));
+ infoLabel.setFont(infoLabel.getFont().deriveFont(infoLabel.getFont().getStyle() | java.awt.Font.BOLD));
+ infoLabel.setForeground(ERROR_COLOR);
+ helpListener.setHelpTopic(HELP_RETRY);
+ }
+
JButton signButton = new JButton();
signButton.setFont(signButton.getFont().deriveFont(signButton.getFont().getStyle() & ~java.awt.Font.BOLD));
signButton.setText(getMessage(BUTTON_SIGN));
@@ -765,46 +928,14 @@ public class BKUGUIImpl implements BKUGUIFacade {
}
pinsizeLabel.setText(MessageFormat.format(pinsizePattern, new Object[]{pinSize}));
- JLabel infoLabel = new JLabel();
- if (numRetries < 0) {
- infoLabel.setFont(infoLabel.getFont().deriveFont(infoLabel.getFont().getStyle() & ~java.awt.Font.BOLD));
- if (shortText) {
- infoLabel.setText(getMessage(MESSAGE_HASHDATALINK_TINY));
- } else {
- infoLabel.setText(getMessage(MESSAGE_HASHDATALINK));
- }
- infoLabel.setCursor(Cursor.getPredefinedCursor(Cursor.HAND_CURSOR));
- infoLabel.setForeground(HYPERLINK_COLOR);
- infoLabel.addMouseListener(new MouseAdapter() {
-
- @Override
- public void mouseClicked(MouseEvent me) {
- ActionEvent e = new ActionEvent(this, ActionEvent.ACTION_PERFORMED, hashdataCommand);
- hashdataListener.actionPerformed(e);
- }
- });
- helpListener.setHelpTopic(HELP_SIGNPIN);
- } else {
- String retryPattern;
- if (numRetries < 2) {
- retryPattern = getMessage(MESSAGE_LAST_RETRY);
- } else {
- retryPattern = getMessage(MESSAGE_RETRIES);
- }
- infoLabel.setText(MessageFormat.format(retryPattern, new Object[]{String.valueOf(numRetries)}));
- infoLabel.setFont(infoLabel.getFont().deriveFont(infoLabel.getFont().getStyle() | java.awt.Font.BOLD));
- infoLabel.setForeground(ERROR_COLOR);
- helpListener.setHelpTopic(HELP_RETRY);
- }
-
GroupLayout mainPanelLayout = new GroupLayout(mainPanel);
mainPanel.setLayout(mainPanelLayout);
-
+
GroupLayout.SequentialGroup infoHorizontal = mainPanelLayout.createSequentialGroup()
.addComponent(infoLabel);
GroupLayout.ParallelGroup infoVertical = mainPanelLayout.createParallelGroup(GroupLayout.Alignment.LEADING)
.addComponent(infoLabel);
-
+
if (!renderHeaderPanel) {
infoHorizontal
.addPreferredGap(LayoutStyle.ComponentPlacement.UNRELATED, 0, Short.MAX_VALUE)
@@ -814,8 +945,8 @@ public class BKUGUIImpl implements BKUGUIFacade {
}
// align pinfield and pinsize to the right
- GroupLayout.ParallelGroup pinHorizontal = mainPanelLayout.createParallelGroup(GroupLayout.Alignment.TRAILING);
- GroupLayout.Group pinVertical;
+ GroupLayout.Group pinHorizontal = mainPanelLayout.createParallelGroup(GroupLayout.Alignment.TRAILING);
+ GroupLayout.SequentialGroup pinVertical = mainPanelLayout.createSequentialGroup();
if (pinLabelPos == PinLabelPosition.ABOVE) {
pinHorizontal
@@ -823,20 +954,25 @@ public class BKUGUIImpl implements BKUGUIFacade {
.addComponent(signPinLabel, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE)
.addComponent(pinField, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE))
.addComponent(pinsizeLabel, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE);
- pinVertical = mainPanelLayout.createSequentialGroup()
+ pinVertical
.addComponent(signPinLabel)
.addPreferredGap(LayoutStyle.ComponentPlacement.RELATED)
- .addComponent(pinField, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE);
- } else {
+ .addComponent(pinField, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE)
+ .addPreferredGap(LayoutStyle.ComponentPlacement.RELATED)
+ .addComponent(pinsizeLabel);
+ } else { // PinLabelPosition.LEFT
pinHorizontal
.addGroup(mainPanelLayout.createSequentialGroup()
.addComponent(signPinLabel, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE)
.addPreferredGap(LayoutStyle.ComponentPlacement.RELATED)
.addComponent(pinField, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE))
.addComponent(pinsizeLabel, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE);
- pinVertical = mainPanelLayout.createParallelGroup(GroupLayout.Alignment.BASELINE)
- .addComponent(signPinLabel)
- .addComponent(pinField);
+ pinVertical
+ .addGroup(mainPanelLayout.createParallelGroup(GroupLayout.Alignment.BASELINE)
+ .addComponent(signPinLabel)
+ .addComponent(pinField))
+ .addPreferredGap(LayoutStyle.ComponentPlacement.RELATED)
+ .addComponent(pinsizeLabel);
}
mainPanelLayout.setHorizontalGroup(
@@ -848,18 +984,14 @@ public class BKUGUIImpl implements BKUGUIFacade {
mainPanelLayout.createSequentialGroup()
.addGroup(infoVertical)
.addPreferredGap(LayoutStyle.ComponentPlacement.RELATED)
- .addGroup(pinVertical)
- .addPreferredGap(LayoutStyle.ComponentPlacement.RELATED)
- .addComponent(pinsizeLabel));
+ .addGroup(pinVertical));
GroupLayout buttonPanelLayout = new GroupLayout(buttonPanel);
buttonPanel.setLayout(buttonPanelLayout);
- GroupLayout.SequentialGroup buttonHorizontal = buttonPanelLayout.createSequentialGroup()
- .addContainerGap(GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
- .addComponent(signButton, GroupLayout.PREFERRED_SIZE, buttonSize, GroupLayout.PREFERRED_SIZE);
+ GroupLayout.SequentialGroup buttonHorizontal = buttonPanelLayout.createSequentialGroup();
GroupLayout.Group buttonVertical;
-
+
if (renderCancelButton) {
JButton cancelButton = new JButton();
cancelButton.setFont(cancelButton.getFont().deriveFont(cancelButton.getFont().getStyle() & ~java.awt.Font.BOLD));
@@ -868,17 +1000,19 @@ public class BKUGUIImpl implements BKUGUIFacade {
cancelButton.addActionListener(cancelListener);
buttonHorizontal
+ .addComponent(signButton, GroupLayout.PREFERRED_SIZE, buttonSize, GroupLayout.PREFERRED_SIZE)
.addPreferredGap(LayoutStyle.ComponentPlacement.RELATED)
.addComponent(cancelButton, GroupLayout.PREFERRED_SIZE, buttonSize, GroupLayout.PREFERRED_SIZE);
-
buttonVertical = buttonPanelLayout.createParallelGroup(GroupLayout.Alignment.BASELINE)
.addComponent(signButton)
- .addComponent(cancelButton);
+ .addComponent(cancelButton);
} else {
+ buttonHorizontal
+ .addComponent(signButton, GroupLayout.PREFERRED_SIZE, buttonSize, GroupLayout.PREFERRED_SIZE);
buttonVertical = buttonPanelLayout.createSequentialGroup()
.addComponent(signButton);
}
-
+
buttonPanelLayout.setHorizontalGroup(buttonHorizontal);
buttonPanelLayout.setVerticalGroup(buttonVertical);
@@ -951,7 +1085,7 @@ public class BKUGUIImpl implements BKUGUIFacade {
@Override
public void run() {
- log.debug("show message dialog");
+ log.debug("show message dialog [" + Thread.currentThread().getName() + "]");
mainPanel.removeAll();
buttonPanel.removeAll();
@@ -1011,7 +1145,6 @@ public class BKUGUIImpl implements BKUGUIFacade {
buttonPanelLayout.setHorizontalGroup(
buttonPanelLayout.createSequentialGroup()
- .addContainerGap(GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
.addComponent(okButton, GroupLayout.PREFERRED_SIZE, buttonSize, GroupLayout.PREFERRED_SIZE));
buttonPanelLayout.setVerticalGroup(
buttonPanelLayout.createSequentialGroup()
@@ -1084,68 +1217,69 @@ public class BKUGUIImpl implements BKUGUIFacade {
}
return null;
}
+
+
+ ////////////////////////////////////////////////////////////////////////////
+ // SECURE VIEWER
+ ////////////////////////////////////////////////////////////////////////////
+
/**
- * TODO handle multiple references in HashDataViewer
* @param signedReferences
- * @param okListener
+ * @param backListener gets notified if pin-dialog has to be redrawn
+ * (signedRefencesList returns via BACK button)
* @param okCommand
*/
@Override
- public void showSecureViewer(final List signedReferences,
- final ActionListener okListener,
- final String okCommand) {
-
- if (signedReferences == null) {
- showErrorDialog(getMessage(ERR_NO_HASHDATA), new Object[] {"No SignedReferences provided"}, okListener, okCommand);
- return;
- }
+ public void showSecureViewer(final List dataToBeSigned,
+ final ActionListener backListener, final String backCommand) {
- if (signedReferences.size() == 1) {
+ if (dataToBeSigned == null) {
+ showErrorDialog(getMessage(ERR_NO_HASHDATA),
+ new Object[] {"no signature data provided"},
+ backListener, backCommand);
+ } else if (dataToBeSigned.size() == 1) {
try {
- log.debug("scheduling hashdata viewer");
+ log.debug("scheduling secure viewer");
- SwingUtilities.invokeAndWait(new Runnable() {
+ SwingUtilities.invokeLater(new Runnable() {
@Override
public void run() {
- ActionListener saveHashDataListener = new ActionListener() {
-
- @Override
- public void actionPerformed(ActionEvent e) {
- HashDataInput hdi = signedReferences.get(0);
- showSaveHashDataInputDialog(Collections.singletonList(hdi), okListener, okCommand);
- }
- };
- showHashDataViewer(signedReferences.get(0), saveHashDataListener, "save");
+ showSecureViewer(dataToBeSigned.get(0));
}
});
- } catch (InterruptedException ex) {
- log.error("Failed to display HashDataViewer: " + ex.getMessage());
- } catch (InvocationTargetException ex) {
- log.error("Failed to display HashDataViewer: " + ex.getMessage());
+ } catch (Exception ex) { //InterruptedException InvocationTargetException
+ log.error("Failed to display secure viewer: " + ex.getMessage());
+ log.trace(ex);
+ showErrorDialog(ERR_UNKNOWN, null, backListener, backCommand);
}
} else {
- showSignedReferencesListDialog(signedReferences, okListener, okCommand);
+ showSignedReferencesListDialog(dataToBeSigned, backListener, backCommand);
}
}
/**
* has to be called from event dispatcher thread
+ * This method blocks until the dialog's close button is pressed.
* @param hashDataText
* @param saveListener
* @param saveCommand
*/
- private void showHashDataViewer(final HashDataInput hashDataInput, final ActionListener saveListener, final String saveCommand) {
+ private void showSecureViewer(HashDataInput dataToBeSigned) {
- log.debug("show hashdata viewer");
-
- ActionListener l = helpListener.getActionListener();
- HashDataViewer.showHashDataInput(contentPane, hashDataInput, messages, saveListener, saveCommand, l);
+ log.debug("show secure viewer [" + Thread.currentThread().getName() + "]");
+ if (secureViewer == null) {
+ secureViewer = new SecureViewerDialog(null, messages,
+ helpListener.getActionListener());
+ }
+ secureViewer.setContent(dataToBeSigned);
+ log.trace("show secure viewer returned");
}
- private void showSignedReferencesListDialog(final List signedReferences, final ActionListener backListener, final String backCommand) {
+ private void showSignedReferencesListDialog(final List signedReferences,
+ final ActionListener backListener, final String backCommand) {
log.debug("scheduling signed references list dialog");
@@ -1154,7 +1288,7 @@ public class BKUGUIImpl implements BKUGUIFacade {
@Override
public void run() {
- log.debug("show signed references list dialog");
+ log.debug("show signed references list dialog [" + Thread.currentThread().getName() + "]");
mainPanel.removeAll();
buttonPanel.removeAll();
@@ -1202,13 +1336,7 @@ public class BKUGUIImpl implements BKUGUIFacade {
int selectionIdx = lsm.getMinSelectionIndex();
if (selectionIdx >= 0) {
final HashDataInput selection = signedReferences.get(selectionIdx);
- showHashDataViewer(selection, new ActionListener() {
-
- @Override
- public void actionPerformed(ActionEvent e) {
- showSaveHashDataInputDialog(Collections.singletonList(selection), null, null);
- }
- }, "save");
+ showSecureViewer(selection);
}
}
});
@@ -1255,9 +1383,8 @@ public class BKUGUIImpl implements BKUGUIFacade {
buttonPanel.setLayout(buttonPanelLayout);
buttonPanelLayout.setHorizontalGroup(buttonPanelLayout.createSequentialGroup()
- .addContainerGap(GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
.addComponent(backButton, GroupLayout.PREFERRED_SIZE, buttonSize, GroupLayout.PREFERRED_SIZE));
- buttonPanelLayout.setVerticalGroup(buttonPanelLayout.createParallelGroup(GroupLayout.Alignment.BASELINE)
+ buttonPanelLayout.setVerticalGroup(buttonPanelLayout.createSequentialGroup()
.addComponent(backButton));
contentPanel.validate();
@@ -1266,96 +1393,101 @@ public class BKUGUIImpl implements BKUGUIFacade {
}
/**
- *
- * @param signedRefs
* @param okListener may be null
- * @param okCommand
*/
- private void showSaveHashDataInputDialog(final List signedRefs, final ActionListener okListener, final String okCommand) {
-
- log.debug("scheduling save hashdatainput dialog");
-
- SwingUtilities.invokeLater(new Runnable() {
+// private void showSaveDialog(final List signedRefs,
+// final ActionListener okListener, final String okCommand) {
+//
+// log.debug("scheduling save dialog");
+//
+// SwingUtilities.invokeLater(new Runnable() {
+//
+// @Override
+// public void run() {
+//
+// log.debug("show save dialog");
+//
+// String userHome = System.getProperty("user.home");
+//
+// JFileChooser fileDialog = new JFileChooser(userHome);
+// fileDialog.setMultiSelectionEnabled(false);
+// fileDialog.setDialogType(JFileChooser.SAVE_DIALOG);
+// fileDialog.setFileHidingEnabled(true);
+// if (signedRefs.size() == 1) {
+// fileDialog.setDialogTitle(getMessage(WINDOWTITLE_SAVE));
+// fileDialog.setFileSelectionMode(JFileChooser.FILES_ONLY);
+// String mimeType = signedRefs.get(0).getMimeType();
+// MimeFilter mimeFilter = new MimeFilter(mimeType, messages);
+// fileDialog.setFileFilter(mimeFilter);
+// String filename = getMessage(SAVE_HASHDATAINPUT_PREFIX) + MimeFilter.getExtension(mimeType);
+// fileDialog.setSelectedFile(new File(userHome, filename));
+// } else {
+// fileDialog.setDialogTitle(getMessage(WINDOWTITLE_SAVEDIR));
+// fileDialog.setFileSelectionMode(JFileChooser.DIRECTORIES_ONLY);
+// }
+//
+// //parent contentPane -> placed over applet
+// switch (fileDialog.showSaveDialog(fileDialog)) {
+// case JFileChooser.APPROVE_OPTION:
+// File f = fileDialog.getSelectedFile();
+// for (HashDataInput hashDataInput : signedRefs) {
+// String mimeType = hashDataInput.getMimeType();
+// String id = hashDataInput.getReferenceId();
+// File file;
+// if (f.isDirectory()) {
+// String filename = getMessage(SAVE_HASHDATAINPUT_PREFIX) + '_' + id + MimeFilter.getExtension(mimeType);
+// file = new File(f, filename);
+// } else {
+// file = f;
+// }
+// if (file.exists()) {
+// String ovrwrt = getMessage(MESSAGE_OVERWRITE);
+// int overwrite = JOptionPane.showConfirmDialog(fileDialog, MessageFormat.format(ovrwrt, file), getMessage(WINDOWTITLE_OVERWRITE), JOptionPane.OK_CANCEL_OPTION);
+// if (overwrite != JOptionPane.OK_OPTION) {
+// continue;
+// }
+// }
+// if (log.isDebugEnabled()) {
+// log.debug("writing hashdata input " + id + " (" + mimeType + ") to file " + file);
+// }
+// FileOutputStream fos = null;
+// try {
+// fos = new FileOutputStream(file);
+// BufferedOutputStream bos = new BufferedOutputStream(fos);
+// InputStream hdi = hashDataInput.getHashDataInput();
+// int b;
+// while ((b = hdi.read()) != -1) {
+// bos.write(b);
+// }
+// bos.flush();
+// bos.close();
+// } catch (IOException ex) {
+// log.error("Failed to write " + file + ": " + ex.getMessage());
+// showErrorDialog(ERR_WRITE_HASHDATA, new Object[] {ex.getMessage()}, null, null);
+// ex.printStackTrace();
+// } finally {
+// try {
+// fos.close();
+// } catch (IOException ex) {
+// }
+// }
+// }
+// break;
+// case JFileChooser.CANCEL_OPTION :
+// log.debug("cancelled save dialog");
+// break;
+// }
+// if (okListener != null) {
+// okListener.actionPerformed(new ActionEvent(fileDialog, ActionEvent.ACTION_PERFORMED, okCommand));
+// }
+// }
+// });
+// }
+
+ ////////////////////////////////////////////////////////////////////////////
+ // UTILITY METHODS
+ ////////////////////////////////////////////////////////////////////////////
- @Override
- public void run() {
-
- log.debug("show save hashdatainput dialog");
-
- String userHome = System.getProperty("user.home");
-
- JFileChooser fileDialog = new JFileChooser(userHome);
- fileDialog.setMultiSelectionEnabled(false);
- fileDialog.setDialogType(JFileChooser.SAVE_DIALOG);
- fileDialog.setFileHidingEnabled(true);
- if (signedRefs.size() == 1) {
- fileDialog.setDialogTitle(getMessage(WINDOWTITLE_SAVE));
- fileDialog.setFileSelectionMode(JFileChooser.FILES_ONLY);
- String mimeType = signedRefs.get(0).getMimeType();
- MimeFilter mimeFilter = new MimeFilter(mimeType, messages);
- fileDialog.setFileFilter(mimeFilter);
- String filename = getMessage(SAVE_HASHDATAINPUT_PREFIX) + MimeFilter.getExtension(mimeType);
- fileDialog.setSelectedFile(new File(userHome, filename));
- } else {
- fileDialog.setDialogTitle(getMessage(WINDOWTITLE_SAVEDIR));
- fileDialog.setFileSelectionMode(JFileChooser.DIRECTORIES_ONLY);
- }
-
- //parent contentPane -> placed over applet
- switch (fileDialog.showSaveDialog(fileDialog)) {
- case JFileChooser.APPROVE_OPTION:
- File f = fileDialog.getSelectedFile();
- for (HashDataInput hashDataInput : signedRefs) {
- String mimeType = hashDataInput.getMimeType();
- String id = hashDataInput.getReferenceId();
- File file;
- if (f.isDirectory()) {
- String filename = getMessage(SAVE_HASHDATAINPUT_PREFIX) + '_' + id + MimeFilter.getExtension(mimeType);
- file = new File(f, filename);
- } else {
- file = f;
- }
- if (file.exists()) {
- String ovrwrt = getMessage(MESSAGE_OVERWRITE);
- int overwrite = JOptionPane.showConfirmDialog(fileDialog, MessageFormat.format(ovrwrt, file), getMessage(WINDOWTITLE_OVERWRITE), JOptionPane.OK_CANCEL_OPTION);
- if (overwrite != JOptionPane.OK_OPTION) {
- continue;
- }
- }
- if (log.isDebugEnabled()) {
- log.debug("Writing HashDataInput " + id + " (" + mimeType + ") to file " + file);
- }
- FileOutputStream fos = null;
- try {
- fos = new FileOutputStream(file);
- BufferedOutputStream bos = new BufferedOutputStream(fos);
- InputStream hdi = hashDataInput.getHashDataInput();
- int b;
- while ((b = hdi.read()) != -1) {
- bos.write(b);
- }
- bos.flush();
- bos.close();
- } catch (IOException ex) {
- log.error("Failed to write HashDataInput to file " + file + ": " + ex.getMessage());
- showErrorDialog(ERR_WRITE_HASHDATA, new Object[] {ex.getMessage()}, null, null);
- ex.printStackTrace();
- } finally {
- try {
- fos.close();
- } catch (IOException ex) {
- }
- }
- }
- }
- log.debug("done saving hashdatainput");
- if (okListener != null) {
- okListener.actionPerformed(new ActionEvent(fileDialog, ActionEvent.ACTION_PERFORMED, okCommand));
- }
- }
- });
- }
-
private void registerHelpListener(ActionListener helpListener) {
if (helpListener != null) {
this.helpListener = new HelpMouseListener(helpListener);
@@ -1371,6 +1503,11 @@ public class BKUGUIImpl implements BKUGUIFacade {
}
}
+
+ ////////////////////////////////////////////////////////////////////////////
+ // INITIALIZERS (MAY BE OVERRIDDEN BY SUBCLASSES)
+ ////////////////////////////////////////////////////////////////////////////
+
/**
* Called from constructor.
* Subclasses may override this method to ensure the message bundle is loaded
diff --git a/BKUCommonGUI/src/main/java/at/gv/egiz/bku/gui/HashDataViewer.java b/BKUCommonGUI/src/main/java/at/gv/egiz/bku/gui/HashDataViewer.java
deleted file mode 100644
index 6c097b2a..00000000
--- a/BKUCommonGUI/src/main/java/at/gv/egiz/bku/gui/HashDataViewer.java
+++ /dev/null
@@ -1,293 +0,0 @@
-/*
- * Copyright 2008 Federal Chancellery Austria and
- * Graz University of Technology
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package at.gv.egiz.bku.gui;
-
-import at.gv.egiz.bku.gui.html.RestrictedHTMLEditorKit;
-import at.gv.egiz.stal.HashDataInput;
-import java.awt.Component;
-import java.awt.Container;
-import java.awt.Cursor;
-import java.awt.Dimension;
-import java.awt.Font;
-import java.awt.Frame;
-import java.awt.event.ActionEvent;
-import java.awt.event.ActionListener;
-import java.awt.event.MouseAdapter;
-import java.awt.event.MouseEvent;
-import java.io.BufferedReader;
-import java.io.InputStreamReader;
-import java.io.Reader;
-import java.nio.charset.Charset;
-import java.text.MessageFormat;
-import java.util.ResourceBundle;
-import javax.swing.GroupLayout;
-import javax.swing.ImageIcon;
-import javax.swing.JButton;
-import javax.swing.JDialog;
-import javax.swing.JEditorPane;
-import javax.swing.JLabel;
-import javax.swing.JOptionPane;
-import javax.swing.JPanel;
-import javax.swing.JScrollPane;
-import javax.swing.LayoutStyle;
-import javax.swing.text.Document;
-import javax.swing.text.EditorKit;
-import javax.swing.text.StyledEditorKit;
-import org.apache.commons.logging.Log;
-import org.apache.commons.logging.LogFactory;
-
-/**
- *
- * @author Clemens Orthacker
- */
-public class HashDataViewer extends JDialog
- implements ActionListener {
-
- public static final String PLAINTEXT_FONT = "Monospaced";
- protected static final Log log = LogFactory.getLog(HashDataViewer.class);
-
- private static HashDataViewer dialog;
-
- protected ResourceBundle messages;
-
- /**
- *
- * @param signedReferences currently, only one hashdata input (the first in the list) is displayed
- */
- public static void showHashDataInput(HashDataInput hashDataInput,
- ResourceBundle messages,
- ActionListener saveListener,
- String saveCommand,
- ActionListener helpListener) {
- showHashDataInput(null, hashDataInput, messages, saveListener, saveCommand, helpListener);
- }
-
- /**
- *
- * @param frameComp owner
- */
- public static void showHashDataInput(Component frameComp,
- HashDataInput hashDataInput,
- ResourceBundle messages,
- ActionListener saveListener,
- String saveCommand,
- ActionListener helpListener) {
-
- Frame frame = null;
- if (frameComp != null) {
- JOptionPane.getFrameForComponent(frameComp);
- }
- dialog = new HashDataViewer(frame,
- messages,
- hashDataInput,
- saveListener,
- saveCommand,
- helpListener);
- dialog.setVisible(true);
- }
-
- private HashDataViewer(Frame frame,
- ResourceBundle messages,
- HashDataInput hashDataInput,
- ActionListener saveListener,
- String saveCommand,
- ActionListener helpListener) {
- super(frame, messages.getString(BKUGUIFacade.WINDOWTITLE_VIEWER), true);
- this.messages = messages;
-
- Charset cs;
- if (hashDataInput.getEncoding() == null) {
- cs = Charset.forName("UTF-8");
- } else {
- try {
- cs = Charset.forName(hashDataInput.getEncoding());
- } catch (Exception ex) {
- log.debug("charset " + hashDataInput.getEncoding() + " not supported, assuming UTF-8: " + ex.getMessage());
- cs = Charset.forName("UTF-8");
- }
- }
-
-
- InputStreamReader isr = new InputStreamReader(hashDataInput.getHashDataInput(), cs);
- Reader content = new BufferedReader(isr);
-
- JPanel hashDataPanel = createViewerPanel(content,
- hashDataInput.getMimeType(),
- helpListener);
- JPanel buttonPanel = createButtonPanel(saveListener, saveCommand);
- initContentPane(new Dimension(600, 400), hashDataPanel, buttonPanel);
-
- pack();
- if (frame != null) {
- setLocationRelativeTo(frame);
- } else {
- setLocationByPlatform(true);
- }
- }
-
- private void initContentPane(Dimension preferredSize, JPanel viewerPanel, JPanel buttonPanel) {
- Container contentPane = getContentPane();
- contentPane.setPreferredSize(preferredSize);
-
- GroupLayout mainLayout = new GroupLayout(contentPane);
- contentPane.setLayout(mainLayout);
-
- mainLayout.setHorizontalGroup(
- mainLayout.createSequentialGroup().addContainerGap().addGroup(
- mainLayout.createParallelGroup(GroupLayout.Alignment.LEADING).addComponent(viewerPanel, 0, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE).addComponent(buttonPanel, 0, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)).addContainerGap());
- mainLayout.setVerticalGroup(
- mainLayout.createSequentialGroup()
- .addContainerGap()
- .addComponent(viewerPanel, 0, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)
- .addPreferredGap(LayoutStyle.ComponentPlacement.UNRELATED)
- .addComponent(buttonPanel, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE)
- .addContainerGap());
- }
-
- /**
- *
- * @param messages
- * @param content
- * @param mimeType defaults to text/plain if null
- * @param encoding must be null if document contains charset declaration (e.g. HTML page), otherwise the parser crashes
- * @param helpListener may be null
- * @return
- */
- private JPanel createViewerPanel(Reader content,
- String mimeType,
- final ActionListener helpListener) {
-
- if (mimeType == null) {
- mimeType = "text/plain";
- }
- log.debug("viewer dialog: " + mimeType);
-
- JEditorPane viewer = new JEditorPane();
- viewer.setEditable(false);
- viewer.setContentType(mimeType);
-
- if ("text/plain".equals(mimeType)) {
- viewer.setEditorKit(new StyledEditorKit());
- viewer.setFont(new Font(PLAINTEXT_FONT, viewer.getFont().getStyle(), viewer.getFont().getSize()));
-// } else if ("text/html".equals(mimeType)) {
-// viewer.setEditorKit(new RestrictedHTMLEditorKit());
- } else if ("application/xhtml+xml".equals(mimeType)) {
- viewer.setContentType("text/html");
- }
-
- EditorKit editorKit = viewer.getEditorKit();
- Document document = editorKit.createDefaultDocument();
-// document.putProperty("IgnoreCharsetDirective", new Boolean(true));
-
- try {
- viewer.read(content, document);
- content.close();
- } catch (Exception ex) {
- log.error(ex.getMessage(), ex);
- String p = messages.getString(BKUGUIFacade.ERR_VIEWER);
- viewer.setText(MessageFormat.format(p, ex.getMessage()));
- }
-
- JScrollPane scrollPane = new JScrollPane(viewer);
- scrollPane.setPreferredSize(viewer.getPreferredSize());
- scrollPane.setAlignmentX(LEFT_ALIGNMENT);
- viewer.setCaretPosition(0);
-
- JPanel viewerPanel = new JPanel();
- GroupLayout viewerPanelLayout = new GroupLayout(viewerPanel);
- viewerPanel.setLayout(viewerPanelLayout);
-
- GroupLayout.SequentialGroup infoHorizontal = viewerPanelLayout.createSequentialGroup();
- GroupLayout.ParallelGroup infoVertical = viewerPanelLayout.createParallelGroup(GroupLayout.Alignment.LEADING);
-
- if ("application/xhtml+xml".equals(mimeType)) {
- JLabel viewerLabel = new JLabel();
- viewerLabel.setText(messages.getString(BKUGUIFacade.WARNING_XHTML));
- viewerLabel.setFont(viewerLabel.getFont().deriveFont(viewerLabel.getFont().getStyle() | java.awt.Font.BOLD));
- viewerLabel.setLabelFor(viewer);
-
- infoHorizontal.addComponent(viewerLabel);
- infoVertical.addComponent(viewerLabel);
- }
-
- if (helpListener != null) {
- JLabel helpLabel = new JLabel();
- helpLabel.setIcon(new ImageIcon(getClass().getResource(BKUGUIFacade.HELP_IMG)));
- helpLabel.getAccessibleContext().setAccessibleName(messages.getString(BKUGUIFacade.ALT_HELP));
- helpLabel.addMouseListener(new MouseAdapter() {
-
- @Override
- public void mouseClicked(MouseEvent arg0) {
- ActionEvent e = new ActionEvent(this, ActionEvent.ACTION_PERFORMED, BKUGUIFacade.HELP_HASHDATAVIEWER);
- helpListener.actionPerformed(e);
- }
- });
- helpLabel.setCursor(Cursor.getPredefinedCursor(Cursor.HAND_CURSOR));
-
- infoHorizontal
- .addPreferredGap(LayoutStyle.ComponentPlacement.UNRELATED, 0, Short.MAX_VALUE)
- .addComponent(helpLabel);
- infoVertical
- .addComponent(helpLabel);
- }
-
- viewerPanelLayout.setHorizontalGroup(
- viewerPanelLayout.createParallelGroup(GroupLayout.Alignment.LEADING)
- .addGroup(infoHorizontal)
- .addComponent(scrollPane));
- viewerPanelLayout.setVerticalGroup(
- viewerPanelLayout.createSequentialGroup()
- .addGroup(infoVertical)
- .addPreferredGap(LayoutStyle.ComponentPlacement.RELATED)
- .addComponent(scrollPane));
-
-
- return viewerPanel;
- }
-
- private JPanel createButtonPanel(ActionListener saveListener, String saveCommand) {
- JButton closeButton = new JButton();
- closeButton.setText(messages.getString(BKUGUIFacade.BUTTON_CLOSE));
- closeButton.addActionListener(this);
-
- JButton saveButton = new JButton();
- saveButton.setText(messages.getString(BKUGUIFacade.BUTTON_SAVE));
- saveButton.setActionCommand(saveCommand);
- saveButton.addActionListener(saveListener);
-
- int buttonSize = closeButton.getPreferredSize().width;
- if (saveButton.getPreferredSize().width > buttonSize) {
- buttonSize = saveButton.getPreferredSize().width;
- }
-
- JPanel buttonPanel = new JPanel();
- GroupLayout buttonPanelLayout = new GroupLayout(buttonPanel);
- buttonPanel.setLayout(buttonPanelLayout);
-
- buttonPanelLayout.setHorizontalGroup(
- buttonPanelLayout.createSequentialGroup().addContainerGap(GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE).addComponent(saveButton, GroupLayout.PREFERRED_SIZE, buttonSize, GroupLayout.PREFERRED_SIZE).addPreferredGap(LayoutStyle.ComponentPlacement.RELATED).addComponent(closeButton, GroupLayout.PREFERRED_SIZE, buttonSize, GroupLayout.PREFERRED_SIZE));
- buttonPanelLayout.setVerticalGroup(
- buttonPanelLayout.createParallelGroup(GroupLayout.Alignment.BASELINE).addComponent(saveButton).addComponent(closeButton));
-
- return buttonPanel;
- }
-
- @Override
- public void actionPerformed(ActionEvent e) {
- HashDataViewer.dialog.setVisible(false);
- }
-}
diff --git a/BKUCommonGUI/src/main/java/at/gv/egiz/bku/gui/SecureViewerDialog.java b/BKUCommonGUI/src/main/java/at/gv/egiz/bku/gui/SecureViewerDialog.java
new file mode 100644
index 00000000..6a16306b
--- /dev/null
+++ b/BKUCommonGUI/src/main/java/at/gv/egiz/bku/gui/SecureViewerDialog.java
@@ -0,0 +1,371 @@
+/*
+ * Copyright 2008 Federal Chancellery Austria and
+ * Graz University of Technology
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package at.gv.egiz.bku.gui;
+
+import at.gv.egiz.stal.HashDataInput;
+import java.awt.Container;
+import java.awt.Cursor;
+import java.awt.Dimension;
+import java.awt.Font;
+import java.awt.Frame;
+import java.awt.event.ActionEvent;
+import java.awt.event.ActionListener;
+import java.awt.event.MouseAdapter;
+import java.awt.event.MouseEvent;
+import java.io.BufferedOutputStream;
+import java.io.BufferedReader;
+import java.io.File;
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.InputStreamReader;
+import java.io.Reader;
+import java.nio.charset.Charset;
+import java.text.MessageFormat;
+import java.util.ResourceBundle;
+import javax.swing.GroupLayout;
+import javax.swing.ImageIcon;
+import javax.swing.JButton;
+import javax.swing.JDialog;
+import javax.swing.JEditorPane;
+import javax.swing.JFileChooser;
+import javax.swing.JLabel;
+import javax.swing.JOptionPane;
+import javax.swing.JPanel;
+import javax.swing.JScrollPane;
+import javax.swing.LayoutStyle;
+import javax.swing.SwingUtilities;
+import javax.swing.text.Document;
+import javax.swing.text.EditorKit;
+import javax.swing.text.StyledEditorKit;
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+
+/**
+ *
+ * @author Clemens Orthacker
+ */
+public class SecureViewerDialog extends JDialog implements ActionListener {
+
+ public static final String PLAINTEXT_FONT = "Monospaced";
+ public static final Dimension VIEWER_DIMENSION = new Dimension(600, 400);
+ protected static final Log log = LogFactory.getLog(SecureViewerDialog.class);
+
+// private static SecureViewerDialog dialog;
+ protected ResourceBundle messages;
+ protected JEditorPane viewer;
+ protected JLabel viewerLabel;
+ protected JScrollPane scrollPane;
+ protected HashDataInput content; //remember for save dialog
+
+ /**
+ * Create and display a modal SecureViewer dialog.
+ * This method blocks until the dialog's close button is pressed.
+ *
+ * @param owner, dialog is positioned relative to its owner
+ * (if null, at default location of native windowing system)
+ */
+// public static void showDataToBeSigned(HashDataInput dataToBeSigned,
+// ResourceBundle messages,
+// ActionListener saveListener, String saveCommand,
+// ActionListener helpListener) {
+//
+//// Frame ownerFrame = (owner != null) ?
+//// JOptionPane.getFrameForComponent(owner) :
+//// null;
+// dialog = new SecureViewerDialog(null, messages,
+// saveListener, saveCommand, helpListener);
+// dialog.setContent(dataToBeSigned);
+// dialog.setVisible(true);
+// }
+ public SecureViewerDialog(Frame owner, ResourceBundle messages,
+// ActionListener saveListener, String saveCommand,
+ ActionListener helpListener) {
+ super(owner, messages.getString(BKUGUIFacade.WINDOWTITLE_VIEWER), true);
+ this.messages = messages;
+
+ initContentPane(VIEWER_DIMENSION,
+ createViewerPanel(helpListener),
+ createButtonPanel()); //saveListener, saveCommand));
+
+ pack();
+ if (owner != null) {
+ setLocationRelativeTo(owner);
+ } else {
+ setLocationByPlatform(true);
+ }
+ }
+
+ private void initContentPane(Dimension preferredSize,
+ JPanel viewerPanel, JPanel buttonPanel) {
+ Container contentPane = getContentPane();
+ contentPane.setPreferredSize(preferredSize);
+
+ GroupLayout mainLayout = new GroupLayout(contentPane);
+ contentPane.setLayout(mainLayout);
+
+ mainLayout.setHorizontalGroup(
+ mainLayout.createSequentialGroup().addContainerGap().addGroup(
+ mainLayout.createParallelGroup(GroupLayout.Alignment.LEADING).addComponent(viewerPanel, 0, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE).addComponent(buttonPanel, 0, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE)).addContainerGap());
+ mainLayout.setVerticalGroup(
+ mainLayout.createSequentialGroup().addContainerGap().addComponent(viewerPanel, 0, GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE).addPreferredGap(LayoutStyle.ComponentPlacement.UNRELATED).addComponent(buttonPanel, GroupLayout.PREFERRED_SIZE, GroupLayout.DEFAULT_SIZE, GroupLayout.PREFERRED_SIZE).addContainerGap());
+ }
+
+ /**
+ * @param helpListener may be null
+ */
+ private JPanel createViewerPanel(final ActionListener helpListener) {
+ viewer = new JEditorPane();
+ viewer.setEditable(false);
+
+ scrollPane = new JScrollPane();
+
+ JPanel viewerPanel = new JPanel();
+ GroupLayout viewerPanelLayout = new GroupLayout(viewerPanel);
+ viewerPanel.setLayout(viewerPanelLayout);
+
+ GroupLayout.SequentialGroup infoHorizontal = viewerPanelLayout.createSequentialGroup();
+ GroupLayout.ParallelGroup infoVertical = viewerPanelLayout.createParallelGroup(GroupLayout.Alignment.LEADING);
+
+ viewerLabel = new JLabel();
+ viewerLabel.setFont(viewerLabel.getFont().deriveFont(viewerLabel.getFont().getStyle() | java.awt.Font.BOLD));
+// viewerLabel.setLabelFor(viewer);
+
+ infoHorizontal.addComponent(viewerLabel);
+ infoVertical.addComponent(viewerLabel);
+
+ if (helpListener != null) {
+ JLabel helpLabel = new JLabel();
+ helpLabel.setIcon(new ImageIcon(getClass().getResource(BKUGUIFacade.HELP_IMG)));
+ helpLabel.getAccessibleContext().setAccessibleName(messages.getString(BKUGUIFacade.ALT_HELP));
+ helpLabel.addMouseListener(new MouseAdapter() {
+
+ @Override
+ public void mouseClicked(MouseEvent arg0) {
+ ActionEvent e = new ActionEvent(this, ActionEvent.ACTION_PERFORMED, BKUGUIFacade.HELP_HASHDATAVIEWER);
+ helpListener.actionPerformed(e);
+ }
+ });
+ helpLabel.setCursor(Cursor.getPredefinedCursor(Cursor.HAND_CURSOR));
+
+ infoHorizontal.addPreferredGap(LayoutStyle.ComponentPlacement.UNRELATED, 0, Short.MAX_VALUE).addComponent(helpLabel);
+ infoVertical.addComponent(helpLabel);
+ }
+
+ viewerPanelLayout.setHorizontalGroup(
+ viewerPanelLayout.createParallelGroup(GroupLayout.Alignment.LEADING).addGroup(infoHorizontal).addComponent(scrollPane));
+ viewerPanelLayout.setVerticalGroup(
+ viewerPanelLayout.createSequentialGroup().addGroup(infoVertical).addPreferredGap(LayoutStyle.ComponentPlacement.RELATED).addComponent(scrollPane));
+
+ return viewerPanel;
+ }
+
+ /**
+ * Sets the hashdataInput to be displayed and makes the dialog visible.
+ * This method blocks until the dialog's close button is pressed.
+ *
+ * @param mimeType defaults to text/plain if null
+ * @param encoding must be null if document contains charset declaration (e.g. HTML page), otherwise the parser crashes
+
+ * @param hashDataInput
+ */
+ public void setContent(HashDataInput hashDataInput) {
+
+ this.content = null;
+
+ String mimeType = hashDataInput.getMimeType();
+ if (mimeType == null) {
+ mimeType = "text/plain";
+ }
+ log.debug("secure viewer mime type: " + mimeType);
+ // loads editorkit for text/plain if unrecognized
+ viewer.setContentType(mimeType);
+
+ if ("text/plain".equals(mimeType)) {
+ viewer.setEditorKit(new StyledEditorKit());
+ viewer.setFont(new Font(PLAINTEXT_FONT, viewer.getFont().getStyle(), viewer.getFont().getSize()));
+// } else if ("text/html".equals(mimeType)) {
+// viewer.setEditorKit(new RestrictedHTMLEditorKit());
+ } else if ("application/xhtml+xml".equals(mimeType)) {
+ viewer.setContentType("text/html");
+ }
+
+ EditorKit editorKit = viewer.getEditorKit();
+ Document document = editorKit.createDefaultDocument();
+// document.putProperty("IgnoreCharsetDirective", new Boolean(true));
+
+ try {
+ Charset cs = (hashDataInput.getEncoding() == null) ? Charset.forName("UTF-8") : Charset.forName(hashDataInput.getEncoding());
+ log.debug("secure viewer encoding: " + cs.toString());
+
+ InputStreamReader isr = new InputStreamReader(hashDataInput.getHashDataInput(), cs);
+ Reader contentReader = new BufferedReader(isr);
+ viewer.read(contentReader, document);
+ contentReader.close();
+
+ this.content = hashDataInput;
+
+// } catch (IllegalCharsetNameException ex) {
+// } catch (UnsupportedCharsetException ex) {
+ } catch (Exception ex) {
+ log.error(ex.getMessage(), ex);
+ String p = messages.getString(BKUGUIFacade.ERR_VIEWER);
+ viewer.setText(MessageFormat.format(p, ex.getMessage()));
+ }
+ viewer.setCaretPosition(0);
+
+ scrollPane.setViewportView(viewer);
+ scrollPane.setPreferredSize(viewer.getPreferredSize());
+ scrollPane.setAlignmentX(LEFT_ALIGNMENT);
+
+ if ("application/xhtml+xml".equals(mimeType)) {
+ viewerLabel.setText(messages.getString(BKUGUIFacade.WARNING_XHTML));
+ } else {
+ viewerLabel.setText("");
+ }
+
+ setVisible(true);
+ }
+
+ private JPanel createButtonPanel() { //ActionListener saveListener, String saveCommand) {
+ JButton closeButton = new JButton();
+ closeButton.setText(messages.getString(BKUGUIFacade.BUTTON_CLOSE));
+ closeButton.setActionCommand("close");
+ closeButton.addActionListener(this);
+
+ JButton saveButton = new JButton();
+ saveButton.setText(messages.getString(BKUGUIFacade.BUTTON_SAVE));
+ saveButton.setActionCommand("save");
+ saveButton.addActionListener(this);
+
+ int buttonSize = closeButton.getPreferredSize().width;
+ if (saveButton.getPreferredSize().width > buttonSize) {
+ buttonSize = saveButton.getPreferredSize().width;
+ }
+
+ JPanel buttonPanel = new JPanel();
+ GroupLayout buttonPanelLayout = new GroupLayout(buttonPanel);
+ buttonPanel.setLayout(buttonPanelLayout);
+
+ buttonPanelLayout.setHorizontalGroup(
+ buttonPanelLayout.createSequentialGroup().addContainerGap(GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE).addComponent(saveButton, GroupLayout.PREFERRED_SIZE, buttonSize, GroupLayout.PREFERRED_SIZE).addPreferredGap(LayoutStyle.ComponentPlacement.RELATED).addComponent(closeButton, GroupLayout.PREFERRED_SIZE, buttonSize, GroupLayout.PREFERRED_SIZE));
+ buttonPanelLayout.setVerticalGroup(
+ buttonPanelLayout.createParallelGroup(GroupLayout.Alignment.BASELINE).addComponent(saveButton).addComponent(closeButton));
+
+ return buttonPanel;
+ }
+
+ @Override
+ public void actionPerformed(ActionEvent e) {
+ if ("close".equals(e.getActionCommand())) {
+// SecureViewerDialog.dialog.setVisible(false);
+ log.trace("closing secure viewer");
+ setVisible(false);
+ log.trace("secure viewer closed");
+ } else if ("save".equals(e.getActionCommand())) {
+ log.trace("display secure viewer save dialog");
+ showSaveDialog(content, null, null);
+ log.trace("done secure viewer save");
+ } else {
+ log.warn("unknown action command " + e.getActionCommand());
+ }
+ }
+
+ private void showSaveDialog(final HashDataInput hashDataInput,
+ final ActionListener okListener, final String okCommand) {
+
+ log.debug("scheduling save dialog [" + Thread.currentThread().getName() + "]");
+
+ SwingUtilities.invokeLater(new Runnable() {
+
+ @Override
+ public void run() {
+
+ log.debug("show save dialog [" + Thread.currentThread().getName() + "]");
+
+ String userHome = System.getProperty("user.home");
+
+ JFileChooser fileDialog = new JFileChooser(userHome);
+ fileDialog.setMultiSelectionEnabled(false);
+ fileDialog.setDialogType(JFileChooser.SAVE_DIALOG);
+ fileDialog.setFileHidingEnabled(true);
+ fileDialog.setDialogTitle(messages.getString(BKUGUIFacade.WINDOWTITLE_SAVE));
+ fileDialog.setFileSelectionMode(JFileChooser.FILES_ONLY);
+ String mimeType = hashDataInput.getMimeType();
+ MimeFilter mimeFilter = new MimeFilter(mimeType, messages);
+ fileDialog.setFileFilter(mimeFilter);
+ String filename = messages.getString(BKUGUIFacade.SAVE_HASHDATAINPUT_PREFIX) +
+ MimeFilter.getExtension(mimeType);
+ fileDialog.setSelectedFile(new File(userHome, filename));
+
+ //parent contentPane -> placed over applet
+ switch (fileDialog.showSaveDialog(fileDialog)) {
+ case JFileChooser.APPROVE_OPTION:
+ File file = fileDialog.getSelectedFile();
+ String id = hashDataInput.getReferenceId();
+ if (file.exists()) {
+ String msgPattern = messages.getString(BKUGUIFacade.MESSAGE_OVERWRITE);
+ int overwrite = JOptionPane.showConfirmDialog(fileDialog,
+ MessageFormat.format(msgPattern, file),
+ messages.getString(BKUGUIFacade.WINDOWTITLE_OVERWRITE),
+ JOptionPane.OK_CANCEL_OPTION);
+ if (overwrite != JOptionPane.OK_OPTION) {
+ return;
+ }
+ }
+ if (log.isDebugEnabled()) {
+ log.debug("writing hashdata input " + id + " (" + mimeType + ") to file " + file);
+ }
+ FileOutputStream fos = null;
+ try {
+ fos = new FileOutputStream(file);
+ BufferedOutputStream bos = new BufferedOutputStream(fos);
+ InputStream hdi = hashDataInput.getHashDataInput();
+ int b;
+ while ((b = hdi.read()) != -1) {
+ bos.write(b);
+ }
+ bos.flush();
+ bos.close();
+ } catch (IOException ex) {
+ log.error("Failed to write " + file + ": " + ex.getMessage());
+ log.debug(ex);
+ String errPattern = messages.getString(BKUGUIFacade.ERR_WRITE_HASHDATA);
+ JOptionPane.showMessageDialog(fileDialog,
+ MessageFormat.format(errPattern, ex.getMessage()),
+ messages.getString(BKUGUIFacade.WINDOWTITLE_ERROR),
+ JOptionPane.ERROR_MESSAGE);
+ } finally {
+ try {
+ if (fos != null) {
+ fos.close();
+ }
+ } catch (IOException ex) {
+ }
+ }
+ break;
+ case JFileChooser.CANCEL_OPTION:
+ log.debug("cancelled save dialog");
+ break;
+ }
+ if (okListener != null) {
+ okListener.actionPerformed(new ActionEvent(fileDialog, ActionEvent.ACTION_PERFORMED, okCommand));
+ }
+ }
+ });
+ }
+}
diff --git a/BKUCommonGUI/src/main/resources/at/gv/egiz/bku/gui/Messages.properties b/BKUCommonGUI/src/main/resources/at/gv/egiz/bku/gui/Messages.properties
index 6d651b2d..9bfe8fb1 100644
--- a/BKUCommonGUI/src/main/resources/at/gv/egiz/bku/gui/Messages.properties
+++ b/BKUCommonGUI/src/main/resources/at/gv/egiz/bku/gui/Messages.properties
@@ -25,6 +25,7 @@ title.retry=Falsche PIN
title.wait=Bitte warten
title.hashdata=Signaturdaten
windowtitle.save=Signaturdaten speichern
+windowtitle.error=Fehler
windowtitle.savedir=Signaturdaten in Verzeichnis speichern
windowtitle.overwrite=Datei \u00FCberschreiben?
windowtitle.viewer=Signaturdaten
@@ -79,7 +80,7 @@ error.unknown.param=Ein Fehler trat auf: {0}
error.unknown=Ein Fehler trat auf
error.test=Fehler1 {0} - Fehler2 {1}
error.card.locked=B\u00FCrgerkarte ist gesperrt
-error.card.notactivated=B\u00FCrgerkartenfunktion ist nicht aktiviert
+error.card.notactivated=Die B\u00FCrgerkarte ist nicht aktiviert
error.pin.timeout=Zeit\u00FCberschreitung bei Eingabe der PIN
error.viewer=Der Inhalt kann nicht dargestellt werden: {0}
error.external.link=Externer Link {0} wird nicht ge\u00F6ffnet
diff --git a/BKUCommonGUI/src/main/resources/at/gv/egiz/bku/gui/Messages_en.properties b/BKUCommonGUI/src/main/resources/at/gv/egiz/bku/gui/Messages_en.properties
index 2fb66969..a36f9b83 100644
--- a/BKUCommonGUI/src/main/resources/at/gv/egiz/bku/gui/Messages_en.properties
+++ b/BKUCommonGUI/src/main/resources/at/gv/egiz/bku/gui/Messages_en.properties
@@ -25,6 +25,7 @@ title.retry=Wrong PIN
title.wait=Please wait
title.hashdata=Signature data
windowtitle.save=Save signature data
+windowtitle.error=Error
windowtitle.savedir=Save signature data to directory
windowtitle.overwrite=Overwrite file?
windowtitle.viewer=Signature data
diff --git a/BKUCommonGUI/src/main/resources/images/ChipperlingLogo.png b/BKUCommonGUI/src/main/resources/images/ChipperlingLogo.png
new file mode 100644
index 00000000..eee4be4f
Binary files /dev/null and b/BKUCommonGUI/src/main/resources/images/ChipperlingLogo.png differ
diff --git a/BKUCommonGUI/src/test/java/at/gv/egiz/bku/gui/BKUGUITest.java b/BKUCommonGUI/src/test/java/at/gv/egiz/bku/gui/BKUGUITest.java
index c8cff617..b3eaf8c7 100644
--- a/BKUCommonGUI/src/test/java/at/gv/egiz/bku/gui/BKUGUITest.java
+++ b/BKUCommonGUI/src/test/java/at/gv/egiz/bku/gui/BKUGUITest.java
@@ -39,8 +39,9 @@ public class BKUGUITest {
public void testBKUGUI() {
JFrame testFrame = new JFrame("BKUGUITest");
Container contentPane = testFrame.getContentPane();
- contentPane.setPreferredSize(new Dimension(170, 150));
- BKUGUIFacade gui = new BKUGUIImpl(contentPane, null, BKUGUIFacade.Style.tiny, null, null);
+// contentPane.setPreferredSize(new Dimension(170, 150));
+ contentPane.setPreferredSize(new Dimension(290, 190));
+ BKUGUIFacade gui = new BKUGUIImpl(contentPane, null, BKUGUIFacade.Style.advanced, null, null);
BKUGUIWorker worker = new BKUGUIWorker();
worker.init(gui);
testFrame.pack();
diff --git a/BKUCommonGUI/src/test/java/at/gv/egiz/bku/gui/BKUGUIWorker.java b/BKUCommonGUI/src/test/java/at/gv/egiz/bku/gui/BKUGUIWorker.java
index 194e18b0..5475a45b 100644
--- a/BKUCommonGUI/src/test/java/at/gv/egiz/bku/gui/BKUGUIWorker.java
+++ b/BKUCommonGUI/src/test/java/at/gv/egiz/bku/gui/BKUGUIWorker.java
@@ -149,7 +149,9 @@ public class BKUGUIWorker implements Runnable {
//
// Thread.sleep(2000);
//
- gui.showSignaturePINDialog(signPinSpec, -1, signListener, "sign", cancelListener, "cancel", hashdataListener, "hashdata");
+// gui.showSignaturePINDialog(signPinSpec, -1, signListener, "sign", cancelListener, "cancel", hashdataListener, "hashdata");
+
+ gui.showPinpadSignaturePINDialog(signPinSpec, -1, hashdataListener, "hashdata");
//
// Thread.sleep(4000);
//
diff --git a/BKULocal/src/main/java/at/gv/egiz/bku/local/stal/BKUGuiProxy.java b/BKULocal/src/main/java/at/gv/egiz/bku/local/stal/BKUGuiProxy.java
index 5a0ba84a..3f560967 100644
--- a/BKULocal/src/main/java/at/gv/egiz/bku/local/stal/BKUGuiProxy.java
+++ b/BKULocal/src/main/java/at/gv/egiz/bku/local/stal/BKUGuiProxy.java
@@ -144,4 +144,12 @@ public class BKUGuiProxy implements BKUGUIFacade {
showDialog();
delegate.showMessageDialog(titleKey, msgKey);
}
+
+ @Override
+ public void showPinpadSignaturePINDialog(PINSpec pinSpec, int numRetries,
+ ActionListener viewerListener, String viewerCommand) {
+ showDialog();
+ delegate.showPinpadSignaturePINDialog(pinSpec, numRetries,
+ viewerListener, viewerCommand);
+ }
}
diff --git a/BKULocal/src/main/java/at/gv/egiz/bku/local/stal/LocalBKUWorker.java b/BKULocal/src/main/java/at/gv/egiz/bku/local/stal/LocalBKUWorker.java
index 61cc7c4c..a782de1a 100644
--- a/BKULocal/src/main/java/at/gv/egiz/bku/local/stal/LocalBKUWorker.java
+++ b/BKULocal/src/main/java/at/gv/egiz/bku/local/stal/LocalBKUWorker.java
@@ -37,7 +37,8 @@ public class LocalBKUWorker extends AbstractBKUWorker {
public LocalBKUWorker(BKUGUIFacade gui, JDialog container) {
super(gui);
this.container = container;
- addRequestHandler(SignRequest.class, new LocalSignRequestHandler());
+ addRequestHandler(SignRequest.class,
+ new LocalSignRequestHandler(new LocalSecureViewer(gui)));
}
@Override
diff --git a/BKULocal/src/main/java/at/gv/egiz/bku/local/stal/LocalSecureViewer.java b/BKULocal/src/main/java/at/gv/egiz/bku/local/stal/LocalSecureViewer.java
new file mode 100644
index 00000000..cbe5af7a
--- /dev/null
+++ b/BKULocal/src/main/java/at/gv/egiz/bku/local/stal/LocalSecureViewer.java
@@ -0,0 +1,109 @@
+
+package at.gv.egiz.bku.local.stal;
+
+import at.gv.egiz.bku.slcommands.impl.DataObjectHashDataInput;
+import at.gv.egiz.bku.smccstal.SecureViewer;
+import java.io.IOException;
+import java.util.ArrayList;
+
+import at.gv.egiz.bku.gui.BKUGUIFacade;
+import at.gv.egiz.stal.HashDataInput;
+import at.gv.egiz.stal.impl.ByteArrayHashDataInput;
+import at.gv.egiz.stal.signedinfo.ReferenceType;
+import at.gv.egiz.stal.signedinfo.SignedInfoType;
+import java.awt.event.ActionListener;
+import java.io.ByteArrayOutputStream;
+import java.io.InputStream;
+import java.util.Collections;
+import java.util.List;
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+
+public class LocalSecureViewer implements SecureViewer {
+
+ private static final Log log = LogFactory.getLog(LocalSignRequestHandler.class);
+ private List hashDataInputs = Collections.EMPTY_LIST;
+
+ protected BKUGUIFacade gui;
+
+ public LocalSecureViewer(BKUGUIFacade gui) {
+ this.gui = gui;
+ }
+
+ public void setDataToBeSigned(List dataToBeSigned) {
+ this.hashDataInputs = dataToBeSigned;
+ }
+
+ /**
+ *
+ * @param dsigReferences
+ * @throws java.lang.Exception
+ */
+ @Override
+ public void displayDataToBeSigned(SignedInfoType signedInfo,
+ ActionListener okListener, String okCommand)
+ throws Exception {
+ if (signedInfo.getReference().size() == 0) {
+ log.error("No hashdata input selected to be displayed: null");
+ throw new Exception("No HashData Input selected to be displayed");
+ }
+
+ ArrayList selectedHashDataInputs = new ArrayList();
+ for (ReferenceType dsigRef : signedInfo.getReference()) {
+ // don't get Manifest, QualifyingProperties, ...
+ if (dsigRef.getType() == null) {
+ String dsigRefId = dsigRef.getId();
+ if (dsigRefId != null) {
+ boolean hdiAvailable = false;
+ for (HashDataInput hashDataInput : hashDataInputs) {
+ if (dsigRefId.equals(hashDataInput.getReferenceId())) {
+ log.debug("display hashdata input for dsig:SignedReference " +
+ dsigRefId);
+ selectedHashDataInputs.add(
+ ensureCachedHashDataInput(hashDataInput));
+ hdiAvailable = true;
+ break;
+ }
+ }
+ if (!hdiAvailable) {
+ log.error("no hashdata input for dsig:SignedReference " + dsigRefId);
+ throw new Exception(
+ "No HashDataInput available for dsig:SignedReference " + dsigRefId);
+ }
+ } else {
+ throw new Exception(
+ "Cannot get HashDataInput for dsig:Reference without Id attribute");
+ }
+ }
+ }
+
+ if (selectedHashDataInputs.size() < 1) {
+ log.error("dsig:SignedInfo does not contain a data reference");
+ throw new Exception("dsig:SignedInfo does not contain a data reference");
+ }
+ gui.showSecureViewer(selectedHashDataInputs, okListener, okCommand);
+ }
+
+
+ private HashDataInput ensureCachedHashDataInput(HashDataInput hashDataInput)
+ throws IOException {
+ if (!(hashDataInput instanceof DataObjectHashDataInput)) {
+
+ log.warn("expected DataObjectHashDataInput for LocalSignRequestHandler, got " +
+ hashDataInput.getClass().getName());
+
+ InputStream hdIs = hashDataInput.getHashDataInput();
+ ByteArrayOutputStream baos = new ByteArrayOutputStream(hdIs.available());
+ int b;
+ while ((b = hdIs.read()) != -1) {
+ baos.write(b);
+ }
+ hashDataInput = new ByteArrayHashDataInput(baos.toByteArray(),
+ hashDataInput.getReferenceId(),
+ hashDataInput.getMimeType(),
+ hashDataInput.getEncoding());
+ }
+ return hashDataInput;
+ }
+
+}
diff --git a/BKULocal/src/main/java/at/gv/egiz/bku/local/stal/LocalSignRequestHandler.java b/BKULocal/src/main/java/at/gv/egiz/bku/local/stal/LocalSignRequestHandler.java
index 531e6591..492b8a05 100644
--- a/BKULocal/src/main/java/at/gv/egiz/bku/local/stal/LocalSignRequestHandler.java
+++ b/BKULocal/src/main/java/at/gv/egiz/bku/local/stal/LocalSignRequestHandler.java
@@ -16,9 +16,7 @@
*/
package at.gv.egiz.bku.local.stal;
-import at.gv.egiz.bku.slcommands.impl.DataObjectHashDataInput;
-import java.io.IOException;
-import java.util.ArrayList;
+import at.gv.egiz.bku.smccstal.SecureViewer;
import java.util.Collections;
import java.util.List;
@@ -40,9 +38,16 @@ import java.io.InputStream;
* @author clemens
*/
public class LocalSignRequestHandler extends SignRequestHandler {
+// implements SecureViewer {
private static final Log log = LogFactory.getLog(LocalSignRequestHandler.class);
- private List hashDataInputs = Collections.EMPTY_LIST;
+
+ protected LocalSecureViewer secureViewer;
+
+ public LocalSignRequestHandler(LocalSecureViewer secureViewer) {
+ super(secureViewer);
+ }
+
/**
* If the request is a SIGN request, it contains a list of DataObjectHashDataInput
@@ -53,75 +58,13 @@ public class LocalSignRequestHandler extends SignRequestHandler {
*/
@SuppressWarnings("unchecked")
@Override
- public STALResponse handleRequest(STALRequest request) throws InterruptedException {
+ public STALResponse handleRequest(STALRequest request)
+ throws InterruptedException {
+
if (request instanceof SignRequest) {
SignRequest signReq = (SignRequest) request;
- hashDataInputs = signReq.getHashDataInput();
+ secureViewer.setDataToBeSigned(signReq.getHashDataInput());
}
return super.handleRequest(request);
}
-
- /**
- *
- * @param dsigReferences
- * @throws java.lang.Exception
- */
- @Override
- public void displayDataToBeSigned(List dsigReferences) throws Exception {
- if (dsigReferences == null || dsigReferences.size() < 1) {
- log.error("No hashdata input selected to be displayed: null");
- throw new Exception("No HashData Input selected to be displayed");
- }
-
- ArrayList selectedHashDataInputs = new ArrayList();
- for (ReferenceType dsigRef : dsigReferences) {
- // don't get Manifest, QualifyingProperties, ...
- if (dsigRef.getType() == null) {
- String dsigRefId = dsigRef.getId();
- if (dsigRefId != null) {
- boolean hdiAvailable = false;
- for (HashDataInput hashDataInput : hashDataInputs) {
- if (dsigRefId.equals(hashDataInput.getReferenceId())) {
- log.debug("display hashdata input for dsig:SignedReference " + dsigRefId);
- if (!(hashDataInput instanceof DataObjectHashDataInput)) {
- log.warn(
- "expected DataObjectHashDataInput for LocalSignRequestHandler, got " + hashDataInput.getClass().getName());
- hashDataInput = getByteArrayHashDataInput(hashDataInput);
- }
- selectedHashDataInputs.add(hashDataInput);
- hdiAvailable = true;
- break;
- }
- }
- if (!hdiAvailable) {
- log.error("no hashdata input for dsig:SignedReference " + dsigRefId);
- throw new Exception(
- "No HashDataInput available for dsig:SignedReference " + dsigRefId);
- }
- } else {
- throw new Exception(
- "Cannot get HashDataInput for dsig:Reference without Id attribute");
- }
- }
- }
-
- if (selectedHashDataInputs.size() < 1) {
- log.error("dsig:SignedInfo does not contain a data reference");
- throw new Exception("dsig:SignedInfo does not contain a data reference");
- }
- gui.showSecureViewer(selectedHashDataInputs, this, "hashDataDone");
- }
-
- private ByteArrayHashDataInput getByteArrayHashDataInput(HashDataInput hashDataInput) throws IOException {
-
- InputStream hdIs = hashDataInput.getHashDataInput();
- ByteArrayOutputStream baos = new ByteArrayOutputStream(hdIs.available());
- int b;
- while ((b = hdIs.read()) != -1) {
- baos.write(b);
- }
- ByteArrayHashDataInput hdi = new ByteArrayHashDataInput(baos.toByteArray(), hashDataInput.getReferenceId(), hashDataInput.getMimeType(), hashDataInput.getEncoding());
-
- return hdi;
- }
}
diff --git a/BKUOnline/src/main/resources/at/gv/egiz/bku/online/conf/defaultConf.properties b/BKUOnline/src/main/resources/at/gv/egiz/bku/online/conf/defaultConf.properties
index e2f07481..04c9c7bf 100644
--- a/BKUOnline/src/main/resources/at/gv/egiz/bku/online/conf/defaultConf.properties
+++ b/BKUOnline/src/main/resources/at/gv/egiz/bku/online/conf/defaultConf.properties
@@ -40,9 +40,12 @@ SSL.sslProtocol=TLS
# warning do not set the following property to true
# its intended for debugging and testing only
SSL.disableAllChecks=false
+#SSL.disableHostnameVerification=true
# ------------ END SSL Config --------------------
+#UserAgent=citizen-card-environment/1.2 MOCCA/1.0
+
ValidateHashDataInputs=true
AppletTimeout=300000
diff --git a/BKUOnline/src/main/resources/log4j.properties b/BKUOnline/src/main/resources/log4j.properties
index f608c83d..25ea9faa 100644
--- a/BKUOnline/src/main/resources/log4j.properties
+++ b/BKUOnline/src/main/resources/log4j.properties
@@ -30,7 +30,7 @@ log4j.appender.STDOUT.layout.ConversionPattern=%-5p | %t | %c %x - %m%n
log4j.appender.file=org.apache.log4j.RollingFileAppender
log4j.appender.file.maxFileSize=500KB
log4j.appender.file.maxBackupIndex=9
-log4j.appender.file.File=${catalina.home}/logs/bkuonline.log
+log4j.appender.file.File=${catalina.base}/logs/bkuonline.log
log4j.appender.file.threshold=trace
log4j.appender.file.layout=org.apache.log4j.PatternLayout
log4j.appender.file.layout.ConversionPattern=%d{ABSOLUTE} %5p | %t | %c{1}:%L - %m%n
\ No newline at end of file
diff --git a/BKUOnline/src/main/webapp/SLRequestForm.html b/BKUOnline/src/main/webapp/SLRequestForm.html
index 9ff7b68a..4714e82f 100644
--- a/BKUOnline/src/main/webapp/SLRequestForm.html
+++ b/BKUOnline/src/main/webapp/SLRequestForm.html
@@ -103,6 +103,33 @@
-->
+
-
+
diff --git a/smcc/src/main/java/at/gv/egiz/smcc/ACOSCard.java b/smcc/src/main/java/at/gv/egiz/smcc/ACOSCard.java
index 1ed5a177..b8cdb208 100644
--- a/smcc/src/main/java/at/gv/egiz/smcc/ACOSCard.java
+++ b/smcc/src/main/java/at/gv/egiz/smcc/ACOSCard.java
@@ -16,6 +16,8 @@
*/
package at.gv.egiz.smcc;
+import at.gv.egiz.smcc.pin.gui.ModifyPINGUI;
+import at.gv.egiz.smcc.pin.gui.PINGUI;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
@@ -79,10 +81,16 @@ public class ACOSCard extends AbstractSignatureCard implements PINMgmtSignatureC
public static final byte KID_PIN_SIG = (byte) 0x81;
+ public static final byte KID_PUK_SIG = (byte) 0x83;
+
public static final byte KID_PIN_DEC = (byte) 0x81;
+ public static final byte KID_PUK_DEC = (byte) 0x82;
+
public static final byte KID_PIN_INF = (byte) 0x83;
+ public static final byte KID_PUK_INF = (byte) 0x84;
+
public static final byte[] DST_SIG = new byte[] { (byte) 0x84, (byte) 0x01, // tag
// ,
// length
@@ -217,7 +225,7 @@ public class ACOSCard extends AbstractSignatureCard implements PINMgmtSignatureC
@Override
@Exclusive
- public byte[] getInfobox(String infobox, PINProvider provider, String domainId)
+ public byte[] getInfobox(String infobox, PINGUI provider, String domainId)
throws SignatureCardException, InterruptedException {
if ("IdentityLink".equals(infobox)) {
@@ -233,7 +241,7 @@ public class ACOSCard extends AbstractSignatureCard implements PINMgmtSignatureC
}
- protected byte[] getIdentityLinkV1(PINProvider provider, String domainId)
+ protected byte[] getIdentityLinkV1(PINGUI provider, String domainId)
throws SignatureCardException, InterruptedException {
try {
@@ -262,7 +270,7 @@ public class ACOSCard extends AbstractSignatureCard implements PINMgmtSignatureC
}
- protected byte[] getIdentityLinkV2(PINProvider provider, String domainId)
+ protected byte[] getIdentityLinkV2(PINGUI provider, String domainId)
throws SignatureCardException, InterruptedException {
try {
@@ -388,7 +396,7 @@ public class ACOSCard extends AbstractSignatureCard implements PINMgmtSignatureC
@Override
@Exclusive
public byte[] createSignature(InputStream input, KeyboxName keyboxName,
- PINProvider provider, String alg) throws SignatureCardException, InterruptedException, IOException {
+ PINGUI provider, String alg) throws SignatureCardException, InterruptedException, IOException {
ByteArrayOutputStream dst = new ByteArrayOutputStream();
// key ID
@@ -487,7 +495,7 @@ public class ACOSCard extends AbstractSignatureCard implements PINMgmtSignatureC
* @see at.gv.egiz.smcc.AbstractSignatureCard#verifyPIN(at.gv.egiz.smcc.PINSpec, at.gv.egiz.smcc.PINProvider)
*/
@Override
- public void verifyPIN(PINSpec pinSpec, PINProvider pinProvider)
+ public void verifyPIN(PINSpec pinSpec, PINGUI pinProvider)
throws LockedException, NotActivatedException, CancelledException,
TimeoutException, SignatureCardException, InterruptedException {
@@ -509,7 +517,7 @@ public class ACOSCard extends AbstractSignatureCard implements PINMgmtSignatureC
* @see at.gv.egiz.smcc.AbstractSignatureCard#changePIN(at.gv.egiz.smcc.PINSpec, at.gv.egiz.smcc.ChangePINProvider)
*/
@Override
- public void changePIN(PINSpec pinSpec, ChangePINProvider pinProvider)
+ public void changePIN(PINSpec pinSpec, ModifyPINGUI pinProvider)
throws LockedException, NotActivatedException, CancelledException,
TimeoutException, SignatureCardException, InterruptedException {
@@ -528,7 +536,7 @@ public class ACOSCard extends AbstractSignatureCard implements PINMgmtSignatureC
}
@Override
- public void activatePIN(PINSpec pinSpec, PINProvider pinProvider)
+ public void activatePIN(PINSpec pinSpec, ModifyPINGUI pinGUI)
throws CancelledException, SignatureCardException, CancelledException,
TimeoutException, InterruptedException {
log.error("ACTIVATE PIN not supported by ACOS");
@@ -536,7 +544,7 @@ public class ACOSCard extends AbstractSignatureCard implements PINMgmtSignatureC
}
@Override
- public void unblockPIN(PINSpec pinSpec, PINProvider pinProvider)
+ public void unblockPIN(PINSpec pinSpec, ModifyPINGUI pinGUI)
throws CancelledException, SignatureCardException, InterruptedException {
throw new SignatureCardException("Unblock PIN not supported.");
}
@@ -570,10 +578,8 @@ public class ACOSCard extends AbstractSignatureCard implements PINMgmtSignatureC
// PROTECTED METHODS (assume exclusive card access)
////////////////////////////////////////////////////////////////////////
- protected void verifyPINLoop(CardChannel channel, PINSpec spec, PINProvider provider)
- throws InterruptedException, LockedException, NotActivatedException,
- TimeoutException, PINFormatException, PINOperationAbortedException,
- SignatureCardException, CardException {
+ protected void verifyPINLoop(CardChannel channel, PINSpec spec, PINGUI provider)
+ throws InterruptedException, CardException, SignatureCardException {
int retries = -1;
do {
@@ -581,10 +587,8 @@ public class ACOSCard extends AbstractSignatureCard implements PINMgmtSignatureC
} while (retries > 0);
}
- protected void changePINLoop(CardChannel channel, PINSpec spec, ChangePINProvider provider)
- throws InterruptedException, LockedException, NotActivatedException,
- TimeoutException, PINFormatException, PINOperationAbortedException,
- SignatureCardException, CardException {
+ protected void changePINLoop(CardChannel channel, PINSpec spec, ModifyPINGUI provider)
+ throws InterruptedException, CardException, SignatureCardException {
int retries = -1;
do {
@@ -593,7 +597,7 @@ public class ACOSCard extends AbstractSignatureCard implements PINMgmtSignatureC
}
protected int verifyPIN(CardChannel channel, PINSpec pinSpec,
- PINProvider provider, int retries) throws InterruptedException, CardException, SignatureCardException {
+ PINGUI provider, int retries) throws InterruptedException, CardException, SignatureCardException {
VerifyAPDUSpec apduSpec = new VerifyAPDUSpec(
new byte[] {
@@ -602,7 +606,7 @@ public class ACOSCard extends AbstractSignatureCard implements PINMgmtSignatureC
(byte) 0x00, (byte) 0x00, (byte) 0x00, (byte) 0x00 },
0, VerifyAPDUSpec.PIN_FORMAT_ASCII, 8);
- ResponseAPDU resp = reader.verify(channel, apduSpec, pinSpec, provider, retries);
+ ResponseAPDU resp = reader.verify(channel, apduSpec, provider, pinSpec, retries);
if (resp.getSW() == 0x9000) {
return -1;
@@ -625,7 +629,7 @@ public class ACOSCard extends AbstractSignatureCard implements PINMgmtSignatureC
}
protected int changePIN(CardChannel channel, PINSpec pinSpec,
- ChangePINProvider pinProvider, int retries) throws CancelledException, InterruptedException, CardException, SignatureCardException {
+ ModifyPINGUI pinProvider, int retries) throws CancelledException, InterruptedException, CardException, SignatureCardException {
ChangeReferenceDataAPDUSpec apduSpec = new ChangeReferenceDataAPDUSpec(
new byte[] {
@@ -639,7 +643,7 @@ public class ACOSCard extends AbstractSignatureCard implements PINMgmtSignatureC
- ResponseAPDU resp = reader.modify(channel, apduSpec, pinSpec, pinProvider, retries);
+ ResponseAPDU resp = reader.modify(channel, apduSpec, pinProvider, pinSpec, retries);
if (resp.getSW() == 0x9000) {
return -1;
diff --git a/smcc/src/main/java/at/gv/egiz/smcc/AbstractSignatureCard.java b/smcc/src/main/java/at/gv/egiz/smcc/AbstractSignatureCard.java
index 54b4c7fe..fcb94fc6 100644
--- a/smcc/src/main/java/at/gv/egiz/smcc/AbstractSignatureCard.java
+++ b/smcc/src/main/java/at/gv/egiz/smcc/AbstractSignatureCard.java
@@ -16,6 +16,8 @@
*/
package at.gv.egiz.smcc;
+import at.gv.egiz.smcc.reader.CardReader;
+import at.gv.egiz.smcc.reader.ReaderFactory;
import java.util.ArrayList;
import java.util.List;
import java.util.Locale;
@@ -29,9 +31,6 @@ import javax.smartcardio.CardTerminal;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
-import at.gv.egiz.smcc.ccid.CCID;
-import at.gv.egiz.smcc.ccid.ReaderFactory;
-
public abstract class AbstractSignatureCard implements SignatureCard {
private static Log log = LogFactory.getLog(AbstractSignatureCard.class);
@@ -45,7 +44,7 @@ public abstract class AbstractSignatureCard implements SignatureCard {
private Card card_;
- protected CCID reader;
+ protected CardReader reader;
protected AbstractSignatureCard(String resourceBundleName) {
this.resourceBundleName = resourceBundleName;
@@ -68,7 +67,7 @@ public abstract class AbstractSignatureCard implements SignatureCard {
@Override
public void init(Card card, CardTerminal cardTerminal) {
this.card_ = card;
- this.reader = ReaderFactory.getInstance().getReader(card, cardTerminal);
+ this.reader = ReaderFactory.getReader(card, cardTerminal);
}
@Override
@@ -80,11 +79,6 @@ public abstract class AbstractSignatureCard implements SignatureCard {
return new LogCardChannel(card_.getBasicChannel());
}
- @Override
- public CCID getReader() {
- return reader;
- }
-
@Override
public void setLocale(Locale locale) {
if (locale == null) {
diff --git a/smcc/src/main/java/at/gv/egiz/smcc/BELPICCard.java b/smcc/src/main/java/at/gv/egiz/smcc/BELPICCard.java
index e02a55d4..41358bb5 100644
--- a/smcc/src/main/java/at/gv/egiz/smcc/BELPICCard.java
+++ b/smcc/src/main/java/at/gv/egiz/smcc/BELPICCard.java
@@ -18,6 +18,7 @@
package at.gv.egiz.smcc;
+import at.gv.egiz.smcc.pin.gui.PINGUI;
import java.io.IOException;
import java.io.InputStream;
import java.security.MessageDigest;
@@ -110,7 +111,7 @@ public class BELPICCard extends AbstractSignatureCard implements SignatureCard {
@Override
@Exclusive
- public byte[] getInfobox(String infobox, PINProvider provider, String domainId)
+ public byte[] getInfobox(String infobox, PINGUI provider, String domainId)
throws SignatureCardException, InterruptedException {
throw new IllegalArgumentException("Infobox '" + infobox
@@ -120,7 +121,7 @@ public class BELPICCard extends AbstractSignatureCard implements SignatureCard {
@Override
@Exclusive
public byte[] createSignature(InputStream input, KeyboxName keyboxName,
- PINProvider provider, String alg) throws SignatureCardException, InterruptedException, IOException {
+ PINGUI provider, String alg) throws SignatureCardException, InterruptedException, IOException {
if (KeyboxName.SECURE_SIGNATURE_KEYPAIR != keyboxName) {
throw new SignatureCardException("Card does not support key " + keyboxName + ".");
@@ -176,7 +177,7 @@ public class BELPICCard extends AbstractSignatureCard implements SignatureCard {
}
protected void verifyPINLoop(CardChannel channel, PINSpec spec,
- PINProvider provider) throws LockedException, NotActivatedException,
+ PINGUI provider) throws LockedException, NotActivatedException,
SignatureCardException, InterruptedException, CardException {
int retries = -1; //verifyPIN(channel, spec, null, -1);
@@ -186,7 +187,7 @@ public class BELPICCard extends AbstractSignatureCard implements SignatureCard {
}
protected int verifyPIN(CardChannel channel, PINSpec pinSpec,
- PINProvider provider, int retries) throws SignatureCardException,
+ PINGUI provider, int retries) throws SignatureCardException,
LockedException, NotActivatedException, InterruptedException,
CardException {
@@ -197,7 +198,7 @@ public class BELPICCard extends AbstractSignatureCard implements SignatureCard {
(byte) 0xff, (byte) 0xff, (byte) 0xff },
1, VerifyAPDUSpec.PIN_FORMAT_BCD, 7, 4, 4);
- ResponseAPDU resp = reader.verify(channel, apduSpec, pinSpec, provider, retries);
+ ResponseAPDU resp = reader.verify(channel, apduSpec, provider, pinSpec, retries);
if (resp.getSW() == 0x9000) {
return -1;
diff --git a/smcc/src/main/java/at/gv/egiz/smcc/ChangePINProvider.java b/smcc/src/main/java/at/gv/egiz/smcc/ChangePINProvider.java
deleted file mode 100644
index 41010551..00000000
--- a/smcc/src/main/java/at/gv/egiz/smcc/ChangePINProvider.java
+++ /dev/null
@@ -1,36 +0,0 @@
-/*
-* Copyright 2008 Federal Chancellery Austria and
-* Graz University of Technology
-*
-* Licensed under the Apache License, Version 2.0 (the "License");
-* you may not use this file except in compliance with the License.
-* You may obtain a copy of the License at
-*
-* http://www.apache.org/licenses/LICENSE-2.0
-*
-* Unless required by applicable law or agreed to in writing, software
-* distributed under the License is distributed on an "AS IS" BASIS,
-* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-* See the License for the specific language governing permissions and
-* limitations under the License.
-*/
-package at.gv.egiz.smcc;
-
-/**
- *
- * @author Clemens Orthacker
- */
-public interface ChangePINProvider extends PINProvider {
-
- /**
- *
- * @param spec
- * @param retries
- * @return null if no old value for this pin
- * @throws at.gv.egiz.smcc.CancelledException if cancelled by user
- * @throws java.lang.InterruptedException
- */
- public char[] provideOldPIN(PINSpec spec, int retries)
- throws CancelledException, InterruptedException;
-
-}
diff --git a/smcc/src/main/java/at/gv/egiz/smcc/ITCard.java b/smcc/src/main/java/at/gv/egiz/smcc/ITCard.java
index 831a1f9b..64389190 100644
--- a/smcc/src/main/java/at/gv/egiz/smcc/ITCard.java
+++ b/smcc/src/main/java/at/gv/egiz/smcc/ITCard.java
@@ -17,6 +17,7 @@
package at.gv.egiz.smcc;
+import at.gv.egiz.smcc.pin.gui.PINGUI;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
@@ -96,7 +97,7 @@ public class ITCard extends AbstractSignatureCard {
@Override
@Exclusive
- public byte[] getInfobox(String infobox, PINProvider provider, String domainId)
+ public byte[] getInfobox(String infobox, PINGUI provider, String domainId)
throws SignatureCardException, InterruptedException {
throw new IllegalArgumentException("Infobox '" + infobox
@@ -106,7 +107,7 @@ public class ITCard extends AbstractSignatureCard {
@Override
@Exclusive
public byte[] createSignature(InputStream input, KeyboxName keyboxName,
- PINProvider provider, String alg) throws SignatureCardException,
+ PINGUI provider, String alg) throws SignatureCardException,
InterruptedException, IOException {
if (KeyboxName.SECURE_SIGNATURE_KEYPAIR != keyboxName) {
@@ -159,7 +160,7 @@ public class ITCard extends AbstractSignatureCard {
}
protected void verifyPINLoop(CardChannel channel, PINSpec spec,
- PINProvider provider) throws LockedException, NotActivatedException,
+ PINGUI provider) throws LockedException, NotActivatedException,
SignatureCardException, InterruptedException, CardException {
int retries = -1;
@@ -169,7 +170,7 @@ public class ITCard extends AbstractSignatureCard {
}
protected int verifyPIN(CardChannel channel, PINSpec pinSpec,
- PINProvider provider, int retries) throws SignatureCardException,
+ PINGUI provider, int retries) throws SignatureCardException,
LockedException, NotActivatedException, InterruptedException,
CardException {
@@ -180,7 +181,7 @@ public class ITCard extends AbstractSignatureCard {
(byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff },
0, VerifyAPDUSpec.PIN_FORMAT_ASCII, 8);
- ResponseAPDU resp = reader.verify(channel, apduSpec, pinSpec, provider, retries);
+ ResponseAPDU resp = reader.verify(channel, apduSpec, provider, pinSpec, retries);
if (resp.getSW() == 0x9000) {
return -2;
diff --git a/smcc/src/main/java/at/gv/egiz/smcc/PINConfirmationException.java b/smcc/src/main/java/at/gv/egiz/smcc/PINConfirmationException.java
index eaf38435..24dfa53c 100644
--- a/smcc/src/main/java/at/gv/egiz/smcc/PINConfirmationException.java
+++ b/smcc/src/main/java/at/gv/egiz/smcc/PINConfirmationException.java
@@ -23,23 +23,4 @@ package at.gv.egiz.smcc;
* @author Clemens Orthacker
*/
public class PINConfirmationException extends SignatureCardException {
-
- private static final long serialVersionUID = 1L;
-
- public PINConfirmationException() {
- super();
- }
-
- public PINConfirmationException(String message, Throwable cause) {
- super(message, cause);
- }
-
- public PINConfirmationException(String message) {
- super(message);
- }
-
- public PINConfirmationException(Throwable cause) {
- super(cause);
- }
-
}
diff --git a/smcc/src/main/java/at/gv/egiz/smcc/PINFormatException.java b/smcc/src/main/java/at/gv/egiz/smcc/PINFormatException.java
index 774fcdf5..721c63e2 100644
--- a/smcc/src/main/java/at/gv/egiz/smcc/PINFormatException.java
+++ b/smcc/src/main/java/at/gv/egiz/smcc/PINFormatException.java
@@ -23,23 +23,4 @@ package at.gv.egiz.smcc;
* @author Clemens Orthacker
*/
public class PINFormatException extends SignatureCardException {
-
- private static final long serialVersionUID = 1L;
-
- public PINFormatException() {
- super();
- }
-
- public PINFormatException(String message, Throwable cause) {
- super(message, cause);
- }
-
- public PINFormatException(String message) {
- super(message);
- }
-
- public PINFormatException(Throwable cause) {
- super(cause);
- }
-
}
diff --git a/smcc/src/main/java/at/gv/egiz/smcc/PINMgmtSignatureCard.java b/smcc/src/main/java/at/gv/egiz/smcc/PINMgmtSignatureCard.java
index 53738612..5091c10f 100644
--- a/smcc/src/main/java/at/gv/egiz/smcc/PINMgmtSignatureCard.java
+++ b/smcc/src/main/java/at/gv/egiz/smcc/PINMgmtSignatureCard.java
@@ -16,6 +16,9 @@
*/
package at.gv.egiz.smcc;
+import at.gv.egiz.smcc.pin.gui.ModifyPINGUI;
+
+import at.gv.egiz.smcc.pin.gui.PINGUI;
import java.util.List;
public interface PINMgmtSignatureCard extends SignatureCard {
@@ -26,16 +29,16 @@ public interface PINMgmtSignatureCard extends SignatureCard {
public PIN_STATE getPINState(PINSpec pinSpec) throws SignatureCardException;
- public void verifyPIN(PINSpec pinSpec, PINProvider pinProvider)
+ public void verifyPIN(PINSpec pinSpec, PINGUI pinGUI)
throws LockedException, NotActivatedException, CancelledException, SignatureCardException, InterruptedException;
- public void changePIN(PINSpec pinSpec, ChangePINProvider pinProvider)
+ public void changePIN(PINSpec pinSpec, ModifyPINGUI changePINGUI)
throws LockedException, NotActivatedException, CancelledException, PINFormatException, SignatureCardException, InterruptedException;
- public void activatePIN(PINSpec pinSpec, PINProvider pinProvider)
+ public void activatePIN(PINSpec pinSpec, ModifyPINGUI activatePINGUI)
throws CancelledException, SignatureCardException, InterruptedException;
- public void unblockPIN(PINSpec pinSpec, PINProvider pukProvider)
+ public void unblockPIN(PINSpec pinSpec, ModifyPINGUI pukGUI)
throws CancelledException, SignatureCardException, InterruptedException;
}
diff --git a/smcc/src/main/java/at/gv/egiz/smcc/PINProvider.java b/smcc/src/main/java/at/gv/egiz/smcc/PINProvider.java
deleted file mode 100644
index 5c294b5b..00000000
--- a/smcc/src/main/java/at/gv/egiz/smcc/PINProvider.java
+++ /dev/null
@@ -1,45 +0,0 @@
-/*
-* Copyright 2008 Federal Chancellery Austria and
-* Graz University of Technology
-*
-* Licensed under the Apache License, Version 2.0 (the "License");
-* you may not use this file except in compliance with the License.
-* You may obtain a copy of the License at
-*
-* http://www.apache.org/licenses/LICENSE-2.0
-*
-* Unless required by applicable law or agreed to in writing, software
-* distributed under the License is distributed on an "AS IS" BASIS,
-* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-* See the License for the specific language governing permissions and
-* limitations under the License.
-*/
-package at.gv.egiz.smcc;
-
-/**
- * The number of retries is not fixed and there is no way (?) to obtain this value.
- * A PINProvider should therefore maintain an internal retry counter or flag
- * to decide whether or not to warn the user (num retries passed in providePIN).
- *
- * Therefore PINProvider objects should not be reused.
- *
- * (ACOS: reload counter: between 0 and 15, where 15 meens deactivated)
- *
- * @author Clemens Orthacker
- */
-public interface PINProvider {
-
- /**
- *
- * @param spec
- * @param retries num of remaining retries or -1 if unknown
- * (a positive value does not necessarily signify that there was
- * already an unsuccessful PIN verification)
- * @return pin != null
- * @throws at.gv.egiz.smcc.CancelledException
- * @throws java.lang.InterruptedException
- */
- public char[] providePIN(PINSpec spec, int retries)
- throws CancelledException, InterruptedException;
-
-}
diff --git a/smcc/src/main/java/at/gv/egiz/smcc/ResetRetryCounterAPDUSpec.java b/smcc/src/main/java/at/gv/egiz/smcc/ResetRetryCounterAPDUSpec.java
new file mode 100644
index 00000000..7e71eb7e
--- /dev/null
+++ b/smcc/src/main/java/at/gv/egiz/smcc/ResetRetryCounterAPDUSpec.java
@@ -0,0 +1,38 @@
+/*
+* Copyright 2008 Federal Chancellery Austria and
+* Graz University of Technology
+*
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+package at.gv.egiz.smcc;
+
+public class ResetRetryCounterAPDUSpec extends ChangeReferenceDataAPDUSpec {
+
+ /**
+ * @param apdu
+ * @param pukPosition
+ * @param pukFormat
+ * @param pukLength
+ * @param pukLengthSize
+ * @param pukLengthPos
+ * @param pinInsertionOffsetNew
+ */
+ public ResetRetryCounterAPDUSpec(byte[] apdu, int pukPosition,
+ int pukFormat, int pukLength, int pukLengthSize, int pukLengthPos,
+ int pinInsertionOffsetNew) {
+ super(apdu, pukPosition, pukFormat, pukLength, pukLengthSize, pukLengthPos);
+ this.pinInsertionOffsetNew = pinInsertionOffsetNew;
+ }
+
+
+}
diff --git a/smcc/src/main/java/at/gv/egiz/smcc/STARCOSCard.java b/smcc/src/main/java/at/gv/egiz/smcc/STARCOSCard.java
index 79a4cc69..ad05352f 100644
--- a/smcc/src/main/java/at/gv/egiz/smcc/STARCOSCard.java
+++ b/smcc/src/main/java/at/gv/egiz/smcc/STARCOSCard.java
@@ -17,6 +17,8 @@
package at.gv.egiz.smcc;
+import at.gv.egiz.smcc.pin.gui.ModifyPINGUI;
+import at.gv.egiz.smcc.pin.gui.PINGUI;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.InputStream;
@@ -225,7 +227,7 @@ public class STARCOSCard extends AbstractSignatureCard implements PINMgmtSignatu
@Override
@Exclusive
- public byte[] getInfobox(String infobox, PINProvider provider, String domainId)
+ public byte[] getInfobox(String infobox, PINGUI pinGUI, String domainId)
throws SignatureCardException, InterruptedException {
try {
@@ -243,7 +245,7 @@ public class STARCOSCard extends AbstractSignatureCard implements PINMgmtSignatu
try {
return ISO7816Utils.readTransparentFileTLV(channel, -1, (byte) 0x30);
} catch (SecurityStatusNotSatisfiedException e) {
- verifyPINLoop(channel, spec, provider);
+ verifyPINLoop(channel, spec, pinGUI);
}
}
@@ -301,7 +303,7 @@ public class STARCOSCard extends AbstractSignatureCard implements PINMgmtSignatu
@Override
@Exclusive
public byte[] createSignature(InputStream input, KeyboxName keyboxName,
- PINProvider provider, String alg) throws SignatureCardException, InterruptedException, IOException {
+ PINGUI provider, String alg) throws SignatureCardException, InterruptedException, IOException {
ByteArrayOutputStream dst = new ByteArrayOutputStream();
byte[] ht = null;
@@ -431,7 +433,7 @@ public class STARCOSCard extends AbstractSignatureCard implements PINMgmtSignatu
*/
@Override
@Exclusive
- public void verifyPIN(PINSpec pinSpec, PINProvider pinProvider)
+ public void verifyPIN(PINSpec pinSpec, PINGUI pinProvider)
throws LockedException, NotActivatedException, CancelledException,
TimeoutException, SignatureCardException, InterruptedException {
@@ -442,12 +444,7 @@ public class STARCOSCard extends AbstractSignatureCard implements PINMgmtSignatu
// SELECT application
execSELECT_AID(channel, pinSpec.getContextAID());
}
- log.debug("*** verifyPIN loop");
verifyPINLoop(channel, pinSpec, pinProvider);
-// log.debug("*** verifyPIN 0");
-// int retries = verifyPIN(channel, pinSpec, null, 0);
-// log.debug("*** verifyPIN " + retries + " tries");
-// verifyPIN(channel, pinSpec, pinProvider, retries);
} catch (CardException e) {
log.info("Failed to verify PIN.", e);
throw new SignatureCardException("Failed to verify PIN.", e);
@@ -460,7 +457,7 @@ public class STARCOSCard extends AbstractSignatureCard implements PINMgmtSignatu
*/
@Override
@Exclusive
- public void changePIN(PINSpec pinSpec, ChangePINProvider pinProvider)
+ public void changePIN(PINSpec pinSpec, ModifyPINGUI pinGUI)
throws LockedException, NotActivatedException, CancelledException,
TimeoutException, SignatureCardException, InterruptedException {
@@ -471,9 +468,7 @@ public class STARCOSCard extends AbstractSignatureCard implements PINMgmtSignatu
// SELECT application
execSELECT_AID(channel, pinSpec.getContextAID());
}
- changePINLoop(channel, pinSpec, pinProvider);
-// int retries = verifyPIN(channel, pinSpec, null, 0);
-// changePIN(channel, pinSpec, pinProvider, retries);
+ changePINLoop(channel, pinSpec, pinGUI);
} catch (CardException e) {
log.info("Failed to change PIN.", e);
throw new SignatureCardException("Failed to change PIN.", e);
@@ -486,7 +481,7 @@ public class STARCOSCard extends AbstractSignatureCard implements PINMgmtSignatu
*/
@Override
@Exclusive
- public void activatePIN(PINSpec pinSpec, PINProvider pinProvider)
+ public void activatePIN(PINSpec pinSpec, ModifyPINGUI activatePINGUI)
throws CancelledException, SignatureCardException, CancelledException,
TimeoutException, InterruptedException {
@@ -497,7 +492,7 @@ public class STARCOSCard extends AbstractSignatureCard implements PINMgmtSignatu
// SELECT application
execSELECT_AID(channel, pinSpec.getContextAID());
}
- activatePIN(channel, pinSpec, pinProvider);
+ activatePIN(channel, pinSpec, activatePINGUI);
} catch (CardException e) {
log.info("Failed to activate PIN.", e);
throw new SignatureCardException("Failed to activate PIN.", e);
@@ -509,9 +504,16 @@ public class STARCOSCard extends AbstractSignatureCard implements PINMgmtSignatu
* @see at.gv.egiz.smcc.PINMgmtSignatureCard#unblockPIN(at.gv.egiz.smcc.PINSpec, at.gv.egiz.smcc.PINProvider)
*/
@Override
- public void unblockPIN(PINSpec pinSpec, PINProvider pukProvider)
+ public void unblockPIN(PINSpec pinSpec, ModifyPINGUI pukProvider)
throws CancelledException, SignatureCardException, InterruptedException {
- throw new SignatureCardException("Unblock PIN is not supported.");
+ CardChannel channel = getCardChannel();
+
+ try {
+ unblockPINLoop(channel, pinSpec, pukProvider);
+ } catch (CardException e) {
+ log.info("Failed to activate PIN.", e);
+ throw new SignatureCardException("Failed to activate PIN.", e);
+ }
}
@Override
@@ -574,7 +576,7 @@ public class STARCOSCard extends AbstractSignatureCard implements PINMgmtSignatu
// PROTECTED METHODS (assume exclusive card access)
////////////////////////////////////////////////////////////////////////
- protected void verifyPINLoop(CardChannel channel, PINSpec spec, PINProvider provider)
+ protected void verifyPINLoop(CardChannel channel, PINSpec spec, PINGUI provider)
throws LockedException, NotActivatedException, SignatureCardException,
InterruptedException, CardException {
@@ -584,7 +586,7 @@ public class STARCOSCard extends AbstractSignatureCard implements PINMgmtSignatu
} while (retries > 0);
}
- protected void changePINLoop(CardChannel channel, PINSpec spec, ChangePINProvider provider)
+ protected void changePINLoop(CardChannel channel, PINSpec spec, ModifyPINGUI provider)
throws LockedException, NotActivatedException, SignatureCardException,
InterruptedException, CardException {
@@ -594,8 +596,19 @@ public class STARCOSCard extends AbstractSignatureCard implements PINMgmtSignatu
} while (retries > 0);
}
+ protected void unblockPINLoop(CardChannel channel, PINSpec spec, ModifyPINGUI provider)
+ throws LockedException, NotActivatedException, SignatureCardException,
+ InterruptedException, CardException {
+
+ //TODO get PUK retry counter from EF FID 0036 in MF
+ int retries = -1;
+ do {
+ retries = unblockPIN(channel, spec, provider, retries);
+ } while (retries > 0);
+ }
+
protected int verifyPIN(CardChannel channel, PINSpec pinSpec,
- PINProvider provider, int retries) throws SignatureCardException,
+ PINGUI provider, int retries) throws SignatureCardException,
LockedException, NotActivatedException, InterruptedException,
CardException {
@@ -608,108 +621,135 @@ public class STARCOSCard extends AbstractSignatureCard implements PINMgmtSignatu
ResponseAPDU resp;
if (provider != null) {
- resp = reader.verify(channel, apduSpec, pinSpec, provider, retries);
+ resp = reader.verify(channel, apduSpec, provider, pinSpec, retries);
} else {
resp = channel.transmit(new CommandAPDU(0x00, 0x20, 0x00, pinSpec.getKID()));
}
-
+
+
if (resp.getSW() == 0x9000) {
return -1;
- }
- if (resp.getSW() == 0x63c0) {
- // returned by the 'short' VERIFY
+ } else if (resp.getSW() == 0x6983 || resp.getSW() == 0x63c0) {
+ // authentication method blocked (0x63c0 returned by 'short' VERIFY)
throw new LockedException();
- }
- if (resp.getSW() >> 4 == 0x63c) {
- return 0x0f & resp.getSW();
- }
-
- switch (resp.getSW()) {
- case 0x6983:
- // authentication method blocked
- // returned by the 'long' VERIFY
- throw new LockedException();
- case 0x6984:
- // reference data not usable
+ } else if (resp.getSW() == 0x6984 || resp.getSW() == 0x6985) {
+ // reference data not usable; conditions of use not satisfied
throw new NotActivatedException();
- case 0x6985:
- // conditions of use not satisfied
+ } else if (resp.getSW() >> 4 == 0x63c) {
+ return 0x0f & resp.getSW();
+ } else if (version > 1.2 && resp.getSW() == 0x6400) {
+ log.warn("cannot query pin status prior to card activation");
throw new NotActivatedException();
-
- default:
+ } else {
String msg = "VERIFY failed. SW=" + Integer.toHexString(resp.getSW());
log.info(msg);
throw new SignatureCardException(msg);
}
-
}
protected int changePIN(CardChannel channel, PINSpec pinSpec,
- ChangePINProvider pinProvider, int retries) throws CancelledException,
+ ModifyPINGUI pinProvider, int retries) throws CancelledException,
InterruptedException, CardException, SignatureCardException {
-
- ChangeReferenceDataAPDUSpec apduSpec = new ChangeReferenceDataAPDUSpec(
- new byte[] {
- (byte) 0x00, (byte) 0x24, (byte) 0x00, pinSpec.getKID(), (byte) 0x10,
- (byte) 0x20, (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff,
- (byte) 0xff, (byte) 0xff, (byte) 0xff,
- (byte) 0x20, (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff,
- (byte) 0xff, (byte) 0xff, (byte) 0xff },
+
+ ChangeReferenceDataAPDUSpec apduSpec = new ChangeReferenceDataAPDUSpec(
+ new byte[] {
+ (byte) 0x00, (byte) 0x24, (byte) 0x00, pinSpec.getKID(), (byte) 0x10,
+ (byte) 0x20, (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff,
+ (byte) 0xff, (byte) 0xff, (byte) 0xff,
+ (byte) 0x20, (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff,
+ (byte) 0xff, (byte) 0xff, (byte) 0xff },
1, VerifyAPDUSpec.PIN_FORMAT_BCD, 7, 4, 4, 8);
-
- ResponseAPDU resp = reader.modify(channel, apduSpec, pinSpec, pinProvider, retries);
-
+
+ ResponseAPDU resp = reader.modify(channel, apduSpec, pinProvider, pinSpec, retries);
+
if (resp.getSW() == 0x9000) {
return -1;
- }
- if (resp.getSW() >> 4 == 0x63c) {
- return 0x0f & resp.getSW();
- }
-
- switch (resp.getSW()) {
- case 0x6983:
+ } else if (resp.getSW() == 0x6983) {
// authentication method blocked
throw new LockedException();
-
- default:
+ } else if (resp.getSW() == 0x6984) {
+ throw new NotActivatedException();
+ } else if (resp.getSW() >> 4 == 0x63c) {
+ return 0x0f & resp.getSW();
+ } else {
String msg = "CHANGE REFERENCE DATA failed. SW=" + Integer.toHexString(resp.getSW());
log.info(msg);
throw new SignatureCardException(msg);
}
-
-
}
protected int activatePIN(CardChannel channel, PINSpec pinSpec,
- PINProvider provider) throws SignatureCardException,
+ ModifyPINGUI provider) throws SignatureCardException,
InterruptedException, CardException {
- NewReferenceDataAPDUSpec apduSpec = new NewReferenceDataAPDUSpec(
+ ResponseAPDU resp;
+ if (version < 1.2) {
+ NewReferenceDataAPDUSpec apduSpec = new NewReferenceDataAPDUSpec(
+ new byte[] {
+ (byte) 0x00, (byte) 0x24, (byte) 0x01, pinSpec.getKID(), (byte) 0x08,
+ (byte) 0x20, (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff,
+ (byte) 0xff, (byte) 0xff, (byte) 0xff },
+ 1, VerifyAPDUSpec.PIN_FORMAT_BCD, 7, 4, 4);
+
+ resp = reader.modify(channel, apduSpec, provider, pinSpec);
+ } else {
+ NewReferenceDataAPDUSpec apduSpec = new NewReferenceDataAPDUSpec(
+ new byte[] {
+ (byte) 0x00, (byte) 0x24, (byte) 0x00, pinSpec.getKID(), (byte) 0x10,
+ (byte) 0x26, (byte) 0x12, (byte) 0x34, (byte) 0x56, (byte) 0xff,
+ (byte) 0xff, (byte) 0xff, (byte) 0xff,
+ (byte) 0x20, (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff,
+ (byte) 0xff, (byte) 0xff, (byte) 0xff },
+ 1, VerifyAPDUSpec.PIN_FORMAT_BCD, 7, 4, 4);
+ apduSpec.setPinInsertionOffsetNew(8);
+ resp = reader.modify(channel, apduSpec, provider, pinSpec);
+ }
+
+ if (resp.getSW() == 0x9000) {
+ return -1;
+ } else {
+ String msg = "CHANGE REFERENCE DATA failed. SW=" + Integer.toHexString(resp.getSW());
+ log.info(msg);
+ throw new SignatureCardException(msg);
+ }
+ }
+
+ protected int unblockPIN(CardChannel channel, PINSpec pinSpec,
+ ModifyPINGUI provider, int retries) throws SignatureCardException,
+ InterruptedException, CardException {
+
+ if (version < 1.2) {
+ // would return 0x6982 (Security status not satisfied)
+ throw new SignatureCardException("RESET RETRY COUNTER is not supported by this card.");
+ }
+
+ ResetRetryCounterAPDUSpec apduSpec = new ResetRetryCounterAPDUSpec(
new byte[] {
- (byte) 0x00, (byte) 0x24, (byte) 0x01, pinSpec.getKID(), (byte) 0x08,
+ (byte) 0x00, (byte) 0x2c, (byte) 0x00, pinSpec.getKID(), (byte) 0x10,
(byte) 0x20, (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff,
- (byte) 0xff, (byte) 0xff, (byte) 0xff },
- 1, VerifyAPDUSpec.PIN_FORMAT_BCD, 7, 4, 4);
-
- ResponseAPDU resp = reader.activate(channel, apduSpec, pinSpec, provider);
-
- switch (resp.getSW()) {
-
- case 0x9000:
- return -1;
+ (byte) 0xff, (byte) 0xff, (byte) 0xff,
+ (byte) 0x20, (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff,
+ (byte) 0xff, (byte) 0xff, (byte) 0xff },
+ 1, VerifyAPDUSpec.PIN_FORMAT_BCD, 7, 4, 4, 8);
- case 0x6983:
- // authentication method blocked
- throw new LockedException();
+ ResponseAPDU resp = reader.modify(channel, apduSpec, provider, pinSpec, retries);
- default:
- String msg = "CHANGE REFERENCE DATA failed. SW=" + Integer.toHexString(resp.getSW());
+ if (resp.getSW() == 0x9000) {
+ return -1;
+ } else if (resp.getSW() == 0x6983) {
+ // PUK blocked
+ throw new LockedException();
+ } else if (resp.getSW() == 0x6984) {
+ throw new NotActivatedException();
+ } else if (resp.getSW() >> 4 == 0x63c) {
+ return 0x0f & resp.getSW();
+ } else {
+ String msg = "RESET RETRY COUNTER failed. SW=" + Integer.toHexString(resp.getSW());
log.info(msg);
throw new SignatureCardException(msg);
}
-
}
-
+
protected void execSELECT_MF(CardChannel channel) throws CardException, SignatureCardException {
ResponseAPDU resp = channel.transmit(
new CommandAPDU(0x00, 0xA4, 0x00, 0x0C));
diff --git a/smcc/src/main/java/at/gv/egiz/smcc/SWCard.java b/smcc/src/main/java/at/gv/egiz/smcc/SWCard.java
index 670704d5..73c7faa8 100644
--- a/smcc/src/main/java/at/gv/egiz/smcc/SWCard.java
+++ b/smcc/src/main/java/at/gv/egiz/smcc/SWCard.java
@@ -40,15 +40,12 @@ import java.util.Enumeration;
import java.util.Locale;
import javax.smartcardio.Card;
-import javax.smartcardio.CardChannel;
-import javax.smartcardio.CardException;
import javax.smartcardio.CardTerminal;
-import javax.smartcardio.ResponseAPDU;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
-import at.gv.egiz.smcc.ccid.CCID;
+import at.gv.egiz.smcc.pin.gui.PINGUI;
/**
*
@@ -280,7 +277,7 @@ public class SWCard implements SignatureCard {
}
- public byte[] getInfobox(String infobox, PINProvider provider, String domainId) throws SignatureCardException {
+ public byte[] getInfobox(String infobox, PINGUI provider, String domainId) throws SignatureCardException {
String fileName = getFileName(infobox + ".ibx");
FileInputStream file;
@@ -309,7 +306,7 @@ public class SWCard implements SignatureCard {
}
@Override
- public byte[] createSignature(InputStream input, KeyboxName keyboxName, PINProvider provider, String alg) throws SignatureCardException, InterruptedException, IOException {
+ public byte[] createSignature(InputStream input, KeyboxName keyboxName, PINGUI provider, String alg) throws SignatureCardException, InterruptedException, IOException {
// KeyStore password
char[] password = getPassword(keyboxName);
@@ -396,101 +393,4 @@ public class SWCard implements SignatureCard {
@Override
public void reset() throws SignatureCardException {
}
-
- @Override
- public CCID getReader() {
- return new CCID() {
-
- @Override
- public boolean hasFeature(Byte feature) {
- return false;
- }
-
- @Override
- public byte getbTimeOut() {
- return 0;
- }
-
- @Override
- public byte getbTimeOut2() {
- return 0;
- }
-
- @Override
- public byte getwPINMaxExtraDigitL() {
- return 0x12;
- }
-
- @Override
- public byte getwPINMaxExtraDigitH() {
- return 0x00;
- }
-
- @Override
- public byte getbEntryValidationCondition() {
- return 0x02;
- }
-
- @Override
- public Card connect() {
- return null;
- }
-
- @Override
- public String getName() {
- return "Software CardReader";
- }
-
- @Override
- public byte[] verifyPin(byte[] PIN_VERIFY) throws CardException {
- throw new UnsupportedOperationException("Not supported yet.");
- }
-
- @Override
- public byte[] verifyPinDirect(byte[] PIN_VERIFY) throws CardException {
- throw new UnsupportedOperationException("Not supported yet.");
- }
-
- @Override
- public byte[] modifyPin(byte[] PIN_MODIFY) throws CardException {
- throw new UnsupportedOperationException("Not supported yet.");
- }
-
- @Override
- public byte[] modifyPinDirect(byte[] PIN_MODIFY) throws CardException {
- throw new UnsupportedOperationException("Not supported yet.");
- }
-
- @Override
- public void setDisablePinpad(boolean disable) {
- throw new UnsupportedOperationException("Not supported yet.");
- }
-
- @Override
- public ResponseAPDU verify(CardChannel channel, VerifyAPDUSpec apduSpec,
- PINSpec pinSpec, PINProvider provider, int retries)
- throws CancelledException, InterruptedException, CardException,
- SignatureCardException {
- throw new UnsupportedOperationException("Not supported yet.");
- }
-
- @Override
- public ResponseAPDU activate(CardChannel channel,
- NewReferenceDataAPDUSpec apduSpec, PINSpec pinSpec,
- PINProvider provider) throws CancelledException,
- InterruptedException, CardException, SignatureCardException {
- // TODO Auto-generated method stub
- return null;
- }
-
- @Override
- public ResponseAPDU modify(CardChannel channel,
- ChangeReferenceDataAPDUSpec apduSpec, PINSpec pinSpec,
- ChangePINProvider provider, int retries) throws CancelledException,
- InterruptedException, CardException, SignatureCardException {
- // TODO Auto-generated method stub
- return null;
- }
- };
- }
}
diff --git a/smcc/src/main/java/at/gv/egiz/smcc/SignatureCard.java b/smcc/src/main/java/at/gv/egiz/smcc/SignatureCard.java
index 3d56f97b..fa589b84 100644
--- a/smcc/src/main/java/at/gv/egiz/smcc/SignatureCard.java
+++ b/smcc/src/main/java/at/gv/egiz/smcc/SignatureCard.java
@@ -17,8 +17,7 @@
package at.gv.egiz.smcc;
-import at.gv.egiz.smcc.ccid.CCID;
-
+import at.gv.egiz.smcc.pin.gui.PINGUI;
import java.io.IOException;
import java.io.InputStream;
import java.util.Locale;
@@ -99,7 +98,7 @@ public interface SignatureCard {
* @throws SignatureCardException
* @throws InterruptedException if applet is destroyed while in pin dialog
*/
- public byte[] getInfobox(String infobox, PINProvider provider, String domainId)
+ public byte[] getInfobox(String infobox, PINGUI pinGUI, String domainId)
throws SignatureCardException, InterruptedException;
/**
@@ -114,9 +113,7 @@ public interface SignatureCard {
* @throws IOException
*/
public byte[] createSignature(InputStream input, KeyboxName keyboxName,
- PINProvider provider, String alg) throws SignatureCardException, InterruptedException, IOException;
-
- public CCID getReader();
+ PINGUI pinGUI, String alg) throws SignatureCardException, InterruptedException, IOException;
/**
* Sets the local for evtl. required callbacks (e.g. PINSpec)
diff --git a/smcc/src/main/java/at/gv/egiz/smcc/pin/gui/ModifyPINGUI.java b/smcc/src/main/java/at/gv/egiz/smcc/pin/gui/ModifyPINGUI.java
new file mode 100644
index 00000000..00dc2d0e
--- /dev/null
+++ b/smcc/src/main/java/at/gv/egiz/smcc/pin/gui/ModifyPINGUI.java
@@ -0,0 +1,36 @@
+/*
+* Copyright 2008 Federal Chancellery Austria and
+* Graz University of Technology
+*
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+package at.gv.egiz.smcc.pin.gui;
+
+import at.gv.egiz.smcc.CancelledException;
+import at.gv.egiz.smcc.PINSpec;
+
+
+public interface ModifyPINGUI extends ModifyPINProvider {
+
+ void modifyPINDirect(PINSpec spec, int retries) throws CancelledException, InterruptedException;
+ void finishDirect();
+
+ void enterCurrentPIN(PINSpec spec, int retries);
+ void enterNewPIN(PINSpec spec);
+ void confirmNewPIN(PINSpec spec);
+ void validKeyPressed();
+ void correctionButtonPressed();
+ void allKeysCleared();
+ /** called prior to MODIFY_PIN_FINISH control command transmission (clear display or display wait message) */
+ void finish();
+}
diff --git a/smcc/src/main/java/at/gv/egiz/smcc/pin/gui/ModifyPINProvider.java b/smcc/src/main/java/at/gv/egiz/smcc/pin/gui/ModifyPINProvider.java
new file mode 100644
index 00000000..36f0097d
--- /dev/null
+++ b/smcc/src/main/java/at/gv/egiz/smcc/pin/gui/ModifyPINProvider.java
@@ -0,0 +1,48 @@
+/*
+* Copyright 2008 Federal Chancellery Austria and
+* Graz University of Technology
+*
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+package at.gv.egiz.smcc.pin.gui;
+
+import at.gv.egiz.smcc.CancelledException;
+import at.gv.egiz.smcc.PINSpec;
+
+
+/**
+ * user interface for "software pin-entry" of
+ *
+ * - current pin and new pin (change pin)
+ *
- new pin (pin activation, no current pin)
+ *
- puk and new pin (probably verify only?)
+ *
+ * @author Clemens Orthacker
+ */
+public interface ModifyPINProvider {
+
+ /**
+ *
+ * @param spec
+ * @param retries
+ * @return null if no old value for this pin
+ * @throws at.gv.egiz.smcc.CancelledException if cancelled by user
+ * @throws java.lang.InterruptedException
+ */
+ public char[] provideCurrentPIN(PINSpec spec, int retries)
+ throws CancelledException, InterruptedException;
+
+ public char[] provideNewPIN(PINSpec spec)
+ throws CancelledException, InterruptedException;
+
+}
diff --git a/smcc/src/main/java/at/gv/egiz/smcc/pin/gui/PINGUI.java b/smcc/src/main/java/at/gv/egiz/smcc/pin/gui/PINGUI.java
new file mode 100644
index 00000000..5199977b
--- /dev/null
+++ b/smcc/src/main/java/at/gv/egiz/smcc/pin/gui/PINGUI.java
@@ -0,0 +1,42 @@
+/*
+* Copyright 2008 Federal Chancellery Austria and
+* Graz University of Technology
+*
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+package at.gv.egiz.smcc.pin.gui;
+
+import at.gv.egiz.smcc.CancelledException;
+import at.gv.egiz.smcc.PINSpec;
+
+
+/**
+ * Display messages for pinpad pin-entry.
+ * Provides an interface for two types of pinpad pin-entry: pinpad-direct and pinpad-start/finish
+ * @author clemens.orthacker@iaik.tugraz.at
+ */
+public interface PINGUI extends PINProvider {
+
+ void enterPINDirect(PINSpec spec, int retries)
+ throws CancelledException, InterruptedException;
+
+ /**
+ * @throws CancelledException, InterruptedException if signature-data dialog is interrupted or cancelled
+ */
+ void enterPIN(PINSpec spec, int retries)
+ throws CancelledException, InterruptedException;
+ void validKeyPressed();
+ void correctionButtonPressed();
+ void allKeysCleared();
+
+}
diff --git a/smcc/src/main/java/at/gv/egiz/smcc/pin/gui/PINProvider.java b/smcc/src/main/java/at/gv/egiz/smcc/pin/gui/PINProvider.java
new file mode 100644
index 00000000..3bf49888
--- /dev/null
+++ b/smcc/src/main/java/at/gv/egiz/smcc/pin/gui/PINProvider.java
@@ -0,0 +1,49 @@
+/*
+* Copyright 2008 Federal Chancellery Austria and
+* Graz University of Technology
+*
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+package at.gv.egiz.smcc.pin.gui;
+
+import at.gv.egiz.smcc.CancelledException;
+import at.gv.egiz.smcc.PINSpec;
+
+
+/**
+ * The number of retries is not fixed and there is no way (?) to obtain this value.
+ * A PINProvider should therefore maintain an internal retry counter or flag
+ * to decide whether or not to warn the user (num retries passed in providePIN).
+ *
+ * Therefore PINProvider objects should not be reused.
+ *
+ * (ACOS: reload counter: between 0 and 15, where 15 meens deactivated)
+ *
+ * @author Clemens Orthacker
+ */
+public interface PINProvider {
+
+ /**
+ *
+ * @param spec
+ * @param retries num of remaining retries or -1 if unknown
+ * (a positive value does not necessarily signify that there was
+ * already an unsuccessful PIN verification)
+ * @return pin != null
+ * @throws at.gv.egiz.smcc.CancelledException
+ * @throws java.lang.InterruptedException
+ */
+ char[] providePIN(PINSpec pinSpec, int retries)
+ throws CancelledException, InterruptedException;
+
+}
diff --git a/smcc/src/main/java/at/gv/egiz/smcc/reader/CardReader.java b/smcc/src/main/java/at/gv/egiz/smcc/reader/CardReader.java
new file mode 100644
index 00000000..a1246dd6
--- /dev/null
+++ b/smcc/src/main/java/at/gv/egiz/smcc/reader/CardReader.java
@@ -0,0 +1,92 @@
+/*
+ * Copyright 2008 Federal Chancellery Austria and
+ * Graz University of Technology
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package at.gv.egiz.smcc.reader;
+
+import javax.smartcardio.CardChannel;
+import javax.smartcardio.CardException;
+import javax.smartcardio.ResponseAPDU;
+
+import at.gv.egiz.smcc.CancelledException;
+import at.gv.egiz.smcc.ChangeReferenceDataAPDUSpec;
+import at.gv.egiz.smcc.NewReferenceDataAPDUSpec;
+import at.gv.egiz.smcc.PINSpec;
+import at.gv.egiz.smcc.ResetRetryCounterAPDUSpec;
+import at.gv.egiz.smcc.SignatureCardException;
+import at.gv.egiz.smcc.VerifyAPDUSpec;
+import at.gv.egiz.smcc.pin.gui.ModifyPINGUI;
+import at.gv.egiz.smcc.pin.gui.PINGUI;
+import javax.smartcardio.Card;
+
+/**
+ *
+ * @author Clemens Orthacker
+ */
+public interface CardReader {
+
+
+ String[] FEATURES = new String[]{"NO_FEATURE",
+ "FEATURE_VERIFY_PIN_START",
+ "FEATURE_VERIFY_PIN_FINISH",
+ "FEATURE_MODIFY_PIN_START",
+ "FEATURE_MODIFY_PIN_FINISH",
+ "FEATURE_GET_KEY_PRESSED",
+ "FEATURE_VERIFY_PIN_DIRECT",
+ "FEATURE_MODIFY_PIN_DIRECT",
+ "FEATURE_MCT_READER_DIRECT",
+ "FEATURE_MCT_UNIVERSAL",
+ "FEATURE_IFD_PIN_PROPERTIES",
+ "FEATURE_ABORT",
+ "FEATURE_SET_SPE_MESSAGE",
+ "FEATURE_VERIFY_PIN_DIRECT_APP_ID",
+ "FEATURE_MODIFY_PIN_DIRECT_APP_ID",
+ "FEATURE_WRITE_DISPLAY",
+ "FEATURE_GET_KEY",
+ "FEATURE_IFD_DISPLAY_PROPERTIES"};
+
+ Byte FEATURE_VERIFY_PIN_START = new Byte((byte) 0x01);
+ Byte FEATURE_VERIFY_PIN_FINISH = new Byte((byte) 0x02);
+ Byte FEATURE_MODIFY_PIN_START = new Byte((byte) 0x03);
+ Byte FEATURE_MODIFY_PIN_FINISH = new Byte((byte) 0x04);
+ Byte FEATURE_GET_KEY_PRESSED = new Byte((byte) 0x05);
+ Byte FEATURE_VERIFY_PIN_DIRECT = new Byte((byte) 0x06);
+ Byte FEATURE_MODIFY_PIN_DIRECT = new Byte((byte) 0x07);
+ Byte FEATURE_MCT_READER_DIRECT = new Byte((byte) 0x08);
+ Byte FEATURE_MCT_UNIVERSAL = new Byte((byte) 0x09);
+ Byte FEATURE_IFD_PIN_PROPERTIES = new Byte((byte) 0x0a);
+ //TODO continue list
+
+
+ Card connect() throws CardException;
+
+ boolean hasFeature(Byte feature);
+
+ ResponseAPDU verify(CardChannel channel, VerifyAPDUSpec apduSpec,
+ PINGUI pinGUI, PINSpec pinSpec, int retries)
+ throws CancelledException, InterruptedException, CardException, SignatureCardException;
+
+ ResponseAPDU modify(CardChannel channel, ChangeReferenceDataAPDUSpec apduSpec,
+ ModifyPINGUI pinGUI, PINSpec pinSpec, int retries)
+ throws CancelledException, InterruptedException, CardException, SignatureCardException;
+
+ ResponseAPDU modify(CardChannel channel, NewReferenceDataAPDUSpec apduSpec,
+ ModifyPINGUI pinGUI, PINSpec pinSpec)
+ throws CancelledException, InterruptedException, CardException, SignatureCardException;
+
+ ResponseAPDU modify(CardChannel channel, ResetRetryCounterAPDUSpec apduSpec,
+ ModifyPINGUI pinGUI, PINSpec pinSpec, int retries)
+ throws CancelledException, InterruptedException, CardException, SignatureCardException;
+}
diff --git a/smcc/src/main/java/at/gv/egiz/smcc/reader/DefaultCardReader.java b/smcc/src/main/java/at/gv/egiz/smcc/reader/DefaultCardReader.java
new file mode 100644
index 00000000..45ea7a5a
--- /dev/null
+++ b/smcc/src/main/java/at/gv/egiz/smcc/reader/DefaultCardReader.java
@@ -0,0 +1,106 @@
+/*
+ * Copyright 2008 Federal Chancellery Austria and
+ * Graz University of Technology
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package at.gv.egiz.smcc.reader;
+
+
+import javax.smartcardio.Card;
+import javax.smartcardio.CardChannel;
+import javax.smartcardio.CardException;
+import javax.smartcardio.CardTerminal;
+import javax.smartcardio.ResponseAPDU;
+
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+
+import at.gv.egiz.smcc.ChangeReferenceDataAPDUSpec;
+import at.gv.egiz.smcc.NewReferenceDataAPDUSpec;
+import at.gv.egiz.smcc.PINSpec;
+import at.gv.egiz.smcc.ResetRetryCounterAPDUSpec;
+import at.gv.egiz.smcc.SignatureCardException;
+import at.gv.egiz.smcc.VerifyAPDUSpec;
+import at.gv.egiz.smcc.pin.gui.ModifyPINGUI;
+import at.gv.egiz.smcc.pin.gui.PINGUI;
+import at.gv.egiz.smcc.util.ISO7816Utils;
+
+/**
+ *
+ * @author Clemens Orthacker
+ */
+public class DefaultCardReader implements CardReader {
+
+ protected final static Log log = LogFactory.getLog(DefaultCardReader.class);
+
+ protected CardTerminal ct;
+ protected String name;
+
+ public DefaultCardReader(CardTerminal ct) {
+ if (ct == null) {
+ throw new NullPointerException("no card or card terminal provided");
+ }
+ this.ct = ct;
+ this.name = ct.getName();
+ }
+
+ @Override
+ public ResponseAPDU verify(CardChannel channel, VerifyAPDUSpec apduSpec,
+ PINGUI pinGUI, PINSpec pinSpec, int retries)
+ throws SignatureCardException, CardException, InterruptedException {
+
+ log.debug("VERIFY");
+ return channel.transmit(ISO7816Utils.createVerifyAPDU(apduSpec, pinGUI.providePIN(pinSpec, retries)));
+ }
+
+ @Override
+ public ResponseAPDU modify(CardChannel channel, ChangeReferenceDataAPDUSpec apduSpec,
+ ModifyPINGUI pinGUI, PINSpec pinSpec, int retries)
+ throws SignatureCardException, CardException, InterruptedException {
+ log.debug("MODIFY (CHANGE_REFERENCE_DATA)");
+ char[] oldPin = pinGUI.provideCurrentPIN(pinSpec, retries);
+ char[] newPin = pinGUI.provideNewPIN(pinSpec);
+ return channel.transmit(ISO7816Utils.createChangeReferenceDataAPDU(apduSpec, oldPin, newPin));
+ }
+
+ @Override
+ public ResponseAPDU modify(CardChannel channel, NewReferenceDataAPDUSpec apduSpec,
+ ModifyPINGUI pinGUI, PINSpec pinSpec)
+ throws SignatureCardException, CardException, InterruptedException {
+ log.debug("MODIFY (NEW_REFERENCE_DATA)");
+ char[] newPIN = pinGUI.provideNewPIN(pinSpec);
+ return channel.transmit(ISO7816Utils.createNewReferenceDataAPDU(apduSpec, newPIN));
+ }
+
+ @Override
+ public ResponseAPDU modify(CardChannel channel, ResetRetryCounterAPDUSpec apduSpec,
+ ModifyPINGUI pinGUI, PINSpec pinSpec, int retries)
+ throws InterruptedException, CardException, SignatureCardException {
+ log.debug("MODIFY (RESET_RETRY_COUNTER)");
+ //TODO
+ return modify(channel, (ChangeReferenceDataAPDUSpec) apduSpec, pinGUI, pinSpec, retries);
+ }
+
+ @Override
+ public Card connect() throws CardException {
+ log.debug("connect icc");
+ return ct.connect("*");
+ }
+
+ @Override
+ public boolean hasFeature(Byte feature) {
+ return false;
+ }
+
+}
diff --git a/smcc/src/main/java/at/gv/egiz/smcc/reader/PinpadCardReader.java b/smcc/src/main/java/at/gv/egiz/smcc/reader/PinpadCardReader.java
new file mode 100644
index 00000000..c2537af8
--- /dev/null
+++ b/smcc/src/main/java/at/gv/egiz/smcc/reader/PinpadCardReader.java
@@ -0,0 +1,703 @@
+/*
+ * Copyright 2008 Federal Chancellery Austria and
+ * Graz University of Technology
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package at.gv.egiz.smcc.reader;
+
+import java.io.ByteArrayOutputStream;
+import java.io.IOException;
+import java.util.Map;
+
+import javax.smartcardio.Card;
+import javax.smartcardio.CardChannel;
+import javax.smartcardio.CardException;
+import javax.smartcardio.CardTerminal;
+import javax.smartcardio.ResponseAPDU;
+
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+
+import at.gv.egiz.smcc.CancelledException;
+import at.gv.egiz.smcc.ChangeReferenceDataAPDUSpec;
+import at.gv.egiz.smcc.NewReferenceDataAPDUSpec;
+import at.gv.egiz.smcc.PINConfirmationException;
+import at.gv.egiz.smcc.PINFormatException;
+import at.gv.egiz.smcc.PINOperationAbortedException;
+import at.gv.egiz.smcc.PINSpec;
+import at.gv.egiz.smcc.ResetRetryCounterAPDUSpec;
+import at.gv.egiz.smcc.SignatureCardException;
+import at.gv.egiz.smcc.TimeoutException;
+import at.gv.egiz.smcc.VerifyAPDUSpec;
+import at.gv.egiz.smcc.pin.gui.ModifyPINGUI;
+import at.gv.egiz.smcc.pin.gui.PINGUI;
+import at.gv.egiz.smcc.util.SMCCHelper;
+
+/**
+ *
+ * @author Clemens Orthacker
+ */
+public class PinpadCardReader extends DefaultCardReader {
+
+ public static final int PIN_ENTRY_POLLING_INTERVAL = 10;
+
+ protected final static Log log = LogFactory.getLog(PinpadCardReader.class);
+
+ protected byte bEntryValidationCondition = 0x02; // validation key pressed
+ protected byte bTimeOut = 0x3c; // 60sec (= max on ReinerSCT)
+ protected byte bTimeOut2 = 0x00; // default (attention with SCM)
+ protected byte wPINMaxExtraDigitH = 0x00; // min pin length zero digits
+ protected byte wPINMaxExtraDigitL = 0x0c; // max pin length 12 digits
+
+ /**
+ * supported features and respective control codes
+ */
+ protected Map features;
+ protected boolean VERIFY, MODIFY, VERIFY_DIRECT, MODIFY_DIRECT;
+
+ public PinpadCardReader(CardTerminal ct, Map features) {
+ super(ct);
+ if (features == null) {
+ throw new NullPointerException("Pinpad card reader does not support any features");
+ }
+ this.features = features;
+
+ if (features.containsKey(FEATURE_VERIFY_PIN_START) &&
+ features.containsKey(FEATURE_GET_KEY_PRESSED) &&
+ features.containsKey(FEATURE_VERIFY_PIN_FINISH)) {
+ VERIFY = true;
+ }
+ if (features.containsKey(FEATURE_MODIFY_PIN_START) &&
+ features.containsKey(FEATURE_GET_KEY_PRESSED) &&
+ features.containsKey(FEATURE_MODIFY_PIN_FINISH)) {
+ MODIFY = true;
+ }
+ if (features.containsKey(FEATURE_VERIFY_PIN_DIRECT)) {
+ VERIFY_DIRECT = true;
+ }
+ if (features.containsKey(FEATURE_MODIFY_PIN_DIRECT)) {
+ MODIFY_DIRECT = true;
+ }
+
+ if (name != null) {
+ name = name.toLowerCase();
+ //ReinerSCT: http://support.reiner-sct.de/downloads/LINUX
+ // http://www.linux-club.de/viewtopic.php?f=61&t=101287&start=0
+ //old: REINER SCT CyberJack 00 00
+ //new (CCID): 0C4B/0300 Reiner-SCT cyberJack pinpad(a) 00 00
+ //Snow Leopard: Reiner-SCT cyberJack pinpad(a) 00 00
+ //display: REINER SCT CyberJack 00 00
+ if(name.startsWith("gemplus gempc pinpad") || name.startsWith("gemalto gempc pinpad")) {
+ log.debug("setting custom wPINMaxExtraDigitH (0x04) for " + name);
+ wPINMaxExtraDigitH = 0x04;
+ log.debug("setting custom wPINMaxExtraDigitL (0x08) for " + name);
+ wPINMaxExtraDigitL = 0x08;
+ } else if (name.startsWith("omnikey cardman 3621")) {
+ log.debug("setting custom wPINMaxExtraDigitH (0x01) for " + name);
+ wPINMaxExtraDigitH = 0x01;
+ } else if (name.startsWith("scm spr 532") || name.startsWith("scm microsystems inc. sprx32 usb smart card reader")) {
+ log.debug("setting custom bTimeOut (0x3c) for " + name);
+ bTimeOut = 0x3c;
+ log.debug("setting custom bTimeOut2 (0x0f) for " + name);
+ bTimeOut2 = 0x0f;
+ } else if (name.startsWith("cherry smartboard xx44")) {
+ log.debug("setting custom wPINMaxExtraDigitH (0x01) for " + name);
+ wPINMaxExtraDigitH = 0x01;
+ }
+ }
+
+ }
+
+ @Override
+ public boolean hasFeature(Byte feature) {
+ return features.containsKey(feature);
+ }
+
+ private void VERIFY_PIN_START(Card icc, byte[] PIN_VERIFY) throws CardException {
+ int ioctl = features.get(FEATURE_VERIFY_PIN_START);
+ if (log.isTraceEnabled()) {
+ log.trace("VERIFY_PIN_START (" + Integer.toHexString(ioctl) +
+ ") " + SMCCHelper.toString(PIN_VERIFY));
+ }
+ byte[] resp = icc.transmitControlCommand(ioctl, PIN_VERIFY);
+ if (resp != null && resp.length > 0) {
+ if (resp[0] == (byte) 0x57) {
+ log.error("Invalid parameter in PIN_VERIFY structure");
+ throw new CardException("ERROR_INVALID_PARAMETER");
+ } else {
+ log.error("unexpected response to VERIFY_PIN_START: " +
+ SMCCHelper.toString(resp));
+ throw new CardException("unexpected response to VERIFY_PIN_START: " +
+ SMCCHelper.toString(resp));
+ }
+ }
+ }
+
+ private byte GET_KEY_PRESSED(Card icc) throws CardException {
+ int ioctl = features.get(FEATURE_GET_KEY_PRESSED);
+ byte[] resp = icc.transmitControlCommand(ioctl, new byte[0]);
+ if (resp != null && resp.length == 1) {
+// if (log.isTraceEnabled()) {
+// log.trace("response " + SMCCHelper.toString(resp));
+// }
+ return resp[0];
+ }
+ log.error("unexpected response to GET_KEY_PRESSED: " +
+ SMCCHelper.toString(resp));
+ throw new CardException("unexpected response to GET_KEY_PRESSED: " +
+ SMCCHelper.toString(resp));
+ }
+
+ private byte[] VERIFY_PIN_FINISH(Card icc) throws CardException {
+ int ioctl = features.get(FEATURE_VERIFY_PIN_FINISH);
+ if (log.isTraceEnabled()) {
+ log.trace("VERIFY_PIN_FINISH (" + Integer.toHexString(ioctl) + ")");
+ }
+ byte[] resp = icc.transmitControlCommand(ioctl, new byte[0]);
+ if (resp != null && resp.length == 2) {
+ if (log.isTraceEnabled()) {
+ log.trace("response " + SMCCHelper.toString(resp));
+ }
+ return resp;
+ }
+ log.error("unexpected response to VERIFY_PIN_FINISH: " +
+ SMCCHelper.toString(resp));
+ throw new CardException("unexpected response to VERIFY_PIN_FINISH: " +
+ SMCCHelper.toString(resp));
+ }
+
+ private void MODIFY_PIN_START(Card icc, byte[] PIN_MODIFY) throws CardException {
+ int ioctl = features.get(FEATURE_MODIFY_PIN_START);
+ if (log.isTraceEnabled()) {
+ log.trace("MODFIY_PIN_START (" + Integer.toHexString(ioctl) +
+ ") " + SMCCHelper.toString(PIN_MODIFY));
+ }
+ byte[] resp = icc.transmitControlCommand(ioctl, PIN_MODIFY);
+ if (resp != null && resp.length > 0) {
+ if (resp[0] == (byte) 0x57) {
+ log.error("Invalid parameter in PIN_MODIFY structure");
+ throw new CardException("ERROR_INVALID_PARAMETER");
+ } else {
+ log.error("unexpected response to MODIFY_PIN_START: " +
+ SMCCHelper.toString(resp));
+ throw new CardException("unexpected response to MODIFY_PIN_START: " +
+ SMCCHelper.toString(resp));
+ }
+ }
+ }
+
+ private byte[] MODIFY_PIN_FINISH(Card icc) throws CardException {
+ int ioctl = features.get(FEATURE_MODIFY_PIN_FINISH);
+ if (log.isTraceEnabled()) {
+ log.trace("MODIFY_PIN_FINISH (" + Integer.toHexString(ioctl) + ")");
+ }
+ byte[] resp = icc.transmitControlCommand(ioctl, new byte[0]);
+ if (resp != null && resp.length == 2) {
+ if (log.isTraceEnabled()) {
+ log.trace("response " + SMCCHelper.toString(resp));
+ }
+ return resp;
+ }
+ log.error("unexpected response to MODIFY_PIN_FINISH: " +
+ SMCCHelper.toString(resp));
+ throw new CardException("unexpected response to MODIFY_PIN_FINISH: " +
+ SMCCHelper.toString(resp));
+ }
+
+ private byte[] VERIFY_PIN_DIRECT(Card icc, byte[] PIN_VERIFY) throws CardException {
+ int ioctl = features.get(FEATURE_VERIFY_PIN_DIRECT);
+ if (log.isTraceEnabled()) {
+ log.trace("VERIFY_PIN_DIRECT (" + Integer.toHexString(ioctl) +
+ ") " + SMCCHelper.toString(PIN_VERIFY));
+ }
+ byte[] resp = icc.transmitControlCommand(ioctl, PIN_VERIFY);
+ if (log.isTraceEnabled()) {
+ log.trace("response " + SMCCHelper.toString(resp));
+ }
+ return resp;
+ }
+
+ private byte[] verifyPin(Card icc, byte[] PIN_VERIFY, PINGUI pinGUI)
+ throws SignatureCardException, CardException, InterruptedException {
+
+// pinGUI.enterPIN(pinSpec, retries);
+
+ log.debug("VERIFY_PIN_START [" + FEATURES[FEATURE_VERIFY_PIN_START] + "]");
+ VERIFY_PIN_START(icc, PIN_VERIFY);
+
+ byte resp;
+ do {
+ resp = GET_KEY_PRESSED(icc);
+ if (resp == (byte) 0x00) {
+ synchronized(this) {
+ try {
+ wait(PIN_ENTRY_POLLING_INTERVAL);
+ } catch (InterruptedException ex) {
+ log.error("interrupted in VERIFY_PIN");
+ }
+ }
+ } else if (resp == (byte) 0x0d) {
+ log.debug("GET_KEY_PRESSED: 0x0d (user confirmed)");
+ break;
+ } else if (resp == (byte) 0x2b) {
+ log.trace("GET_KEY_PRESSED: 0x2b (user entered valid key 0-9)");
+ pinGUI.validKeyPressed();
+ } else if (resp == (byte) 0x1b) {
+ log.debug("GET_KEY_PRESSED: 0x1b (user cancelled VERIFY_PIN via cancel button)");
+ break; // returns 0x6401
+ } else if (resp == (byte) 0x08) {
+ log.debug("GET_KEY_PRESSED: 0x08 (user pressed correction/backspace button)");
+ pinGUI.correctionButtonPressed();
+ } else if (resp == (byte) 0x0e) {
+ log.debug("GET_KEY_PRESSED: 0x0e (timeout occured)");
+ break; // return 0x6400
+ } else if (resp == (byte) 0x40) {
+ log.debug("GET_KEY_PRESSED: 0x40 (PIN_Operation_Aborted)");
+ throw new PINOperationAbortedException("PIN_Operation_Aborted (0x40)");
+ } else if (resp == (byte) 0x0a) {
+ log.debug("GET_KEY_PRESSED: 0x0a (all keys cleared");
+ pinGUI.allKeysCleared();
+ } else {
+ log.error("unexpected response to GET_KEY_PRESSED: " +
+ Integer.toHexString(resp));
+ throw new CardException("unexpected response to GET_KEY_PRESSED: " +
+ Integer.toHexString(resp));
+ }
+ } while (true);
+
+ return VERIFY_PIN_FINISH(icc);
+ }
+
+ /**
+ * does not display the first pin dialog (enterCurrentPIN or enterNewPIN, depends on bConfirmPIN),
+ * since this is easier to do in calling modify()
+ */
+ private byte[] modifyPin(Card icc, byte[] PIN_MODIFY, ModifyPINGUI pinGUI, PINSpec pINSpec)
+ throws PINOperationAbortedException, CardException {
+
+ byte pinConfirmations = (byte) 0x00; //b0: new pin not entered (0) / entered (1)
+ //b1: current pin not entered (0) / entered (1)
+ byte bConfirmPIN = PIN_MODIFY[9];
+
+// if ((bConfirmPIN & (byte) 0x02) == 0) {
+// log.debug("no current PIN entry requested");
+// pinGUI.enterNewPIN(pINSpec);
+// } else {
+// log.debug("current PIN entry requested");
+// pinGUI.enterCurrentPIN(pINSpec, retries);
+// }
+
+ log.debug("MODIFY_PIN_START [" + FEATURES[FEATURE_MODIFY_PIN_START] + "]");
+ MODIFY_PIN_START(icc, PIN_MODIFY);
+
+ byte resp;
+ while (true) {
+ resp = GET_KEY_PRESSED(icc);
+ if (resp == (byte) 0x00) {
+ synchronized(this) {
+ try {
+ wait(PIN_ENTRY_POLLING_INTERVAL);
+ } catch (InterruptedException ex) {
+ log.error("interrupted in MODIFY_PIN");
+ }
+ }
+ } else if (resp == (byte) 0x0d) {
+ if (log.isTraceEnabled()) {
+ log.trace("requested pin confirmations: 0b" + Integer.toBinaryString(bConfirmPIN & 0xff));
+ log.trace("performed pin confirmations: 0b" + Integer.toBinaryString(pinConfirmations & 0xff));
+ }
+ log.debug("GET_KEY_PRESSED: 0x0d (user confirmed)");
+ if (pinConfirmations == bConfirmPIN) {
+ break;
+ } else if ((bConfirmPIN & (byte) 0x02) == 0 ||
+ (pinConfirmations & (byte) 0x02) == (byte) 0x02) {
+ // no current pin entry or current pin entry already performed
+ if ((pinConfirmations & (byte) 0x01) == 0) {
+ // new pin
+ pinConfirmations |= (byte) 0x01;
+ pinGUI.confirmNewPIN(pINSpec);
+ } // else: new pin confirmed
+ } else {
+ // current pin entry
+ pinConfirmations |= (byte) 0x02;
+ pinGUI.enterNewPIN(pINSpec);
+ }
+ } else if (resp == (byte) 0x2b) {
+ log.trace("GET_KEY_PRESSED: 0x2b (user entered valid key 0-9)");
+ pinGUI.validKeyPressed();
+ } else if (resp == (byte) 0x1b) {
+ log.debug("GET_KEY_PRESSED: 0x1b (user cancelled VERIFY_PIN via cancel button)");
+ break; // returns 0x6401
+ } else if (resp == (byte) 0x08) {
+ log.debug("GET_KEY_PRESSED: 0x08 (user pressed correction/backspace button)");
+ pinGUI.correctionButtonPressed();
+ } else if (resp == (byte) 0x0e) {
+ log.debug("GET_KEY_PRESSED: 0x0e (timeout occured)");
+ break; // return 0x6400
+ } else if (resp == (byte) 0x40) {
+ log.debug("GET_KEY_PRESSED: 0x40 (PIN_Operation_Aborted)");
+ throw new PINOperationAbortedException("PIN_Operation_Aborted (0x40)");
+ } else if (resp == (byte) 0x0a) {
+ log.debug("GET_KEY_PRESSED: 0x0a (all keys cleared");
+ pinGUI.allKeysCleared();
+ } else {
+ log.error("unexpected response to GET_KEY_PRESSED: " +
+ Integer.toHexString(resp));
+ throw new CardException("unexpected response to GET_KEY_PRESSED: " +
+ Integer.toHexString(resp));
+ }
+
+ }
+
+ pinGUI.finish();
+ return MODIFY_PIN_FINISH(icc);
+ }
+
+ private byte[] MODIFY_PIN_DIRECT(Card icc, byte[] PIN_MODIFY) throws CardException {
+ int ioctl = features.get(FEATURE_MODIFY_PIN_DIRECT);
+ if (log.isTraceEnabled()) {
+ log.trace("MODIFY_PIN_DIRECT (" + Integer.toHexString(ioctl) +
+ ") " + SMCCHelper.toString(PIN_MODIFY));
+ }
+ byte[] resp = icc.transmitControlCommand(ioctl, PIN_MODIFY);
+ if (log.isTraceEnabled()) {
+ log.trace("response " + SMCCHelper.toString(resp));
+ }
+ return resp;
+ }
+
+ protected byte[] createPINModifyStructure(NewReferenceDataAPDUSpec apduSpec, PINSpec pinSpec) {
+
+ ByteArrayOutputStream s = new ByteArrayOutputStream();
+ // bTimeOut
+ s.write(bTimeOut);
+ // bTimeOut2
+ s.write(bTimeOut2);
+ // bmFormatString
+ s.write(1 << 7 // system unit = byte
+ | (0xF & apduSpec.getPinPosition()) << 3
+ | (0x1 & apduSpec.getPinJustification() << 2)
+ | (0x3 & apduSpec.getPinFormat()));
+ // bmPINBlockString
+ s.write((0xF & apduSpec.getPinLengthSize()) << 4
+ | (0xF & apduSpec.getPinLength()));
+ // bmPINLengthFormat
+ s.write(// system unit = bit
+ (0xF & apduSpec.getPinLengthPos()));
+ // bInsertionOffsetOld
+ s.write(0x00);
+ // bInsertionOffsetNew
+ s.write(apduSpec.getPinInsertionOffsetNew());
+ // wPINMaxExtraDigit
+ s.write(Math.min(pinSpec.getMaxLength(), wPINMaxExtraDigitL));
+ s.write(Math.max(pinSpec.getMinLength(), wPINMaxExtraDigitH));
+ // bConfirmPIN
+ s.write(0x01);
+ // bEntryValidationCondition
+ s.write(bEntryValidationCondition);
+ // bNumberMessage
+ s.write(0x02);
+ // wLangId English (United States), see http://www.usb.org/developers/docs/USB_LANGIDs.pdf
+ s.write(0x09);
+ s.write(0x04);
+ // bMsgIndex1
+ s.write(0x01);
+ // bMsgIndex2
+ s.write(0x02);
+ // bMsgIndex3
+ s.write(0x00);
+
+ // bTeoPrologue
+ s.write(0x00);
+ s.write(0x00);
+ s.write(0x00);
+ // ulDataLength
+ s.write(apduSpec.getApdu().length);
+ s.write(0x00);
+ s.write(0x00);
+ s.write(0x00);
+ // abData
+ try {
+ s.write(apduSpec.getApdu());
+ } catch (IOException e) {
+ // As we are dealing with ByteArrayOutputStreams no exception is to be
+ // expected.
+ throw new RuntimeException(e);
+ }
+
+ return s.toByteArray();
+
+ }
+
+ protected byte[] createPINModifyStructure(ChangeReferenceDataAPDUSpec apduSpec, PINSpec pinSpec) {
+ //TODO bInsertionOffsetOld (0x00), bConfirmPIN (0x01), bNumberMessage (0x02), bMsgIndex1/2/3
+
+ ByteArrayOutputStream s = new ByteArrayOutputStream();
+ // bTimeOut
+ s.write(bTimeOut);
+ // bTimeOut2
+ s.write(bTimeOut2);
+ // bmFormatString
+ s.write(1 << 7 // system unit = byte
+ | (0xF & apduSpec.getPinPosition()) << 3
+ | (0x1 & apduSpec.getPinJustification() << 2)
+ | (0x3 & apduSpec.getPinFormat()));
+ // bmPINBlockString
+ s.write((0xF & apduSpec.getPinLengthSize()) << 4
+ | (0xF & apduSpec.getPinLength()));
+ // bmPINLengthFormat
+ s.write(// system unit = bit
+ (0xF & apduSpec.getPinLengthPos()));
+ // bInsertionOffsetOld (0x00 for no old pin?)
+ s.write(apduSpec.getPinInsertionOffsetOld());
+ // bInsertionOffsetNew
+ s.write(apduSpec.getPinInsertionOffsetNew());
+ // wPINMaxExtraDigit
+ s.write(Math.min(pinSpec.getMaxLength(), wPINMaxExtraDigitL));
+ s.write(Math.max(pinSpec.getMinLength(), wPINMaxExtraDigitH));
+ // bConfirmPIN
+ s.write(0x03);
+ // bEntryValidationCondition
+ s.write(bEntryValidationCondition);
+ // bNumberMessage
+ s.write(0x03);
+ // wLangId English (United States), see http://www.usb.org/developers/docs/USB_LANGIDs.pdf
+ s.write(0x09);
+ s.write(0x04);
+ // bMsgIndex1
+ s.write(0x00);
+ // bMsgIndex2
+ s.write(0x01);
+ // bMsgIndex3
+ s.write(0x02);
+
+ // bTeoPrologue
+ s.write(0x00);
+ s.write(0x00);
+ s.write(0x00);
+ // ulDataLength
+ s.write(apduSpec.getApdu().length);
+ s.write(0x00);
+ s.write(0x00);
+ s.write(0x00);
+ // abData
+ try {
+ s.write(apduSpec.getApdu());
+ } catch (IOException e) {
+ // As we are dealing with ByteArrayOutputStreams no exception is to be
+ // expected.
+ throw new RuntimeException(e);
+ }
+
+ return s.toByteArray();
+
+ }
+
+ protected byte[] createPINVerifyStructure(VerifyAPDUSpec apduSpec, PINSpec pinSpec) {
+
+ ByteArrayOutputStream s = new ByteArrayOutputStream();
+ // bTimeOut
+ s.write(bTimeOut);
+ // bTimeOut2
+ s.write(bTimeOut2);
+ // bmFormatString
+ s.write(1 << 7 // system unit = byte
+ | (0xF & apduSpec.getPinPosition()) << 3
+ | (0x1 & apduSpec.getPinJustification() << 2)
+ | (0x3 & apduSpec.getPinFormat()));
+ // bmPINBlockString
+ s.write((0xF & apduSpec.getPinLengthSize()) << 4
+ | (0xF & apduSpec.getPinLength()));
+ // bmPINLengthFormat
+ s.write(// system unit = bit
+ (0xF & apduSpec.getPinLengthPos()));
+ // wPINMaxExtraDigit
+ s.write(Math.min(pinSpec.getMaxLength(), wPINMaxExtraDigitL)); // max PIN length
+ s.write(Math.max(pinSpec.getMinLength(), wPINMaxExtraDigitH)); // min PIN length
+ // bEntryValidationCondition
+ s.write(bEntryValidationCondition);
+ // bNumberMessage
+ s.write(0x01);
+ // wLangId
+ s.write(0x09);
+ s.write(0x04);
+ // bMsgIndex
+ s.write(0x00);
+ // bTeoPrologue
+ s.write(0x00);
+ s.write(0x00);
+ s.write(0x00);
+ // ulDataLength
+ s.write(apduSpec.getApdu().length);
+ s.write(0x00);
+ s.write(0x00);
+ s.write(0x00);
+ // abData
+ try {
+ s.write(apduSpec.getApdu());
+ } catch (IOException e) {
+ // As we are dealing with ByteArrayOutputStreams no exception is to be
+ // expected.
+ throw new RuntimeException(e);
+ }
+
+ return s.toByteArray();
+
+ }
+
+ @Override
+ public ResponseAPDU verify(CardChannel channel, VerifyAPDUSpec apduSpec,
+ PINGUI pinGUI, PINSpec pinSpec, int retries)
+ throws SignatureCardException, CardException, InterruptedException {
+
+ ResponseAPDU resp = null;
+
+ byte[] s = createPINVerifyStructure(apduSpec, pinSpec);
+ Card icc = channel.getCard();
+
+ if (VERIFY) {
+ pinGUI.enterPIN(pinSpec, retries);
+ resp = new ResponseAPDU(verifyPin(icc, s, pinGUI));
+ } else if (VERIFY_DIRECT) {
+ pinGUI.enterPINDirect(pinSpec, retries);
+ log.debug("VERIFY_PIN_DIRECT [" + FEATURES[FEATURE_VERIFY_PIN_DIRECT] + "]");
+ resp = new ResponseAPDU(VERIFY_PIN_DIRECT(icc, s));
+ } else {
+ log.warn("falling back to default pin-entry");
+ return super.verify(channel, apduSpec, pinGUI, pinSpec, retries);
+ }
+
+ switch (resp.getSW()) {
+ case 0x6400:
+ log.debug("SPE operation timed out.");
+ throw new TimeoutException();
+ case 0x6401:
+ log.debug("SPE operation was cancelled by the 'Cancel' button.");
+ throw new CancelledException();
+ case 0x6403:
+ log.debug("User entered too short or too long PIN "
+ + "regarding MIN/MAX PIN length.");
+ throw new PINFormatException();
+ case 0x6480:
+ log.debug("SPE operation was aborted by the 'Cancel' operation "
+ + "at the host system.");
+ case 0x6b80:
+ log.info("Invalid parameter in passed structure.");
+ default:
+ return resp;
+ }
+ }
+
+ @Override
+ public ResponseAPDU modify(CardChannel channel, ChangeReferenceDataAPDUSpec apduSpec,
+ ModifyPINGUI pinGUI, PINSpec pinSpec, int retries)
+ throws SignatureCardException, CardException, InterruptedException {
+
+ ResponseAPDU resp = null;
+
+ byte[] s = createPINModifyStructure(apduSpec, pinSpec);
+ Card icc = channel.getCard();
+
+ if (MODIFY) {
+ pinGUI.enterCurrentPIN(pinSpec, retries);
+ resp = new ResponseAPDU(modifyPin(icc, s, pinGUI, pinSpec));
+ } else if (MODIFY_DIRECT) {
+ pinGUI.modifyPINDirect(pinSpec, retries);
+ log.debug("MODIFY_PIN_DIRECT [" + FEATURES[FEATURE_MODIFY_PIN_DIRECT] + "]");
+ resp = new ResponseAPDU(MODIFY_PIN_DIRECT(icc, s));
+ } else {
+ log.warn("falling back to default pin-entry");
+ return super.modify(channel, apduSpec, pinGUI, pinSpec, retries);
+ }
+
+ switch (resp.getSW()) {
+ case 0x6400:
+ log.debug("SPE operation timed out.");
+ throw new TimeoutException();
+ case 0x6401:
+ log.debug("SPE operation was cancelled by the 'Cancel' button.");
+ throw new CancelledException();
+ case 0x6402:
+ log.debug("Modify PIN operation failed because two 'new PIN' " +
+ "entries do not match");
+ throw new PINConfirmationException();
+ case 0x6403:
+ log.debug("User entered too short or too long PIN "
+ + "regarding MIN/MAX PIN length.");
+ throw new PINFormatException();
+ case 0x6480:
+ log.debug("SPE operation was aborted by the 'Cancel' operation "
+ + "at the host system.");
+ case 0x6b80:
+ log.info("Invalid parameter in passed structure.");
+ default:
+ return resp;
+ }
+ }
+
+ @Override
+ public ResponseAPDU modify(CardChannel channel, NewReferenceDataAPDUSpec apduSpec,
+ ModifyPINGUI pinGUI, PINSpec pinSpec)
+ throws SignatureCardException, CardException, InterruptedException {
+
+ ResponseAPDU resp = null;
+
+ byte[] s = createPINModifyStructure(apduSpec, pinSpec);
+ Card icc = channel.getCard();
+
+ if (MODIFY) {
+ pinGUI.enterNewPIN(pinSpec);
+ resp = new ResponseAPDU(modifyPin(icc, s, pinGUI, pinSpec));
+ } else if (MODIFY_DIRECT) {
+ pinGUI.modifyPINDirect(pinSpec, -1);
+ log.debug("MODIFY_PIN_DIRECT [" + FEATURES[FEATURE_MODIFY_PIN_DIRECT] + "]");
+ resp = new ResponseAPDU(MODIFY_PIN_DIRECT(icc, s));
+ } else {
+ log.warn("falling back to default pin-entry");
+ return super.modify(channel, apduSpec, pinGUI, pinSpec);
+ }
+
+ switch (resp.getSW()) {
+ case 0x6400:
+ log.debug("SPE operation timed out.");
+ throw new TimeoutException();
+ case 0x6401:
+ log.debug("SPE operation was cancelled by the 'Cancel' button.");
+ throw new CancelledException();
+ case 0x6402:
+ log.debug("Modify PIN operation failed because two 'new PIN' " +
+ "entries do not match");
+ throw new PINConfirmationException();
+ case 0x6403:
+ log.debug("User entered too short or too long PIN "
+ + "regarding MIN/MAX PIN length.");
+ throw new PINFormatException();
+ case 0x6480:
+ log.debug("SPE operation was aborted by the 'Cancel' operation "
+ + "at the host system.");
+ case 0x6b80:
+ log.info("Invalid parameter in passed structure.");
+ default:
+ return resp;
+ }
+ }
+
+ @Override
+ public ResponseAPDU modify(CardChannel channel, ResetRetryCounterAPDUSpec apduSpec,
+ ModifyPINGUI pinGUI, PINSpec pinSpec, int retries)
+ throws InterruptedException, CardException, SignatureCardException {
+ //TODO
+ return modify(channel, (ChangeReferenceDataAPDUSpec) apduSpec, pinGUI, pinSpec, retries);
+ }
+}
diff --git a/smcc/src/main/java/at/gv/egiz/smcc/reader/ReaderFactory.java b/smcc/src/main/java/at/gv/egiz/smcc/reader/ReaderFactory.java
new file mode 100644
index 00000000..eb197d9f
--- /dev/null
+++ b/smcc/src/main/java/at/gv/egiz/smcc/reader/ReaderFactory.java
@@ -0,0 +1,128 @@
+/*
+ * Copyright 2008 Federal Chancellery Austria and
+ * Graz University of Technology
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package at.gv.egiz.smcc.reader;
+
+import at.gv.egiz.smcc.conf.SMCCConfiguration;
+import at.gv.egiz.smcc.util.SMCCHelper;
+import java.util.HashMap;
+import java.util.Map;
+import javax.smartcardio.Card;
+import javax.smartcardio.CardException;
+import javax.smartcardio.CardTerminal;
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+
+/**
+ *
+ * @author Clemens Orthacker
+ */
+public class ReaderFactory {
+
+ protected final static Log log = LogFactory.getLog(ReaderFactory.class);
+
+ protected SMCCConfiguration configuration;
+
+ private ReaderFactory() {
+ }
+
+ /**
+ * @param configuration the configuration to set
+ */
+ public void setConfiguration(SMCCConfiguration configuration) {
+ this.configuration = configuration;
+ }
+
+ public static CardReader getReader(Card icc, CardTerminal ct) {
+
+ String name = ct.getName();
+ log.info("creating reader " + name);
+
+ Map features = queryFeatures(icc);
+ boolean disablePinpad = false;
+ CardReader reader;
+
+ //TODO query application context for reader config
+// if (configuration != null) {
+// String disablePinpad = configuration.getProperty(SMCCConfiguration.DISABLE_PINPAD_P);
+// log.debug("setting disablePinpad to " + Boolean.parseBoolean(disablePinpad));
+// reader.setDisablePinpad(Boolean.parseBoolean(disablePinpad));
+// }
+ log.warn("card reader configuration is not considered");
+
+ if (features.isEmpty() || disablePinpad) {
+ reader = new DefaultCardReader(ct);
+ } else {
+ reader = new PinpadCardReader(ct, features);
+ }
+
+ return reader;
+ }
+
+ private static int CTL_CODE(int code) {
+ String os_name = System.getProperty("os.name").toLowerCase();
+ if (os_name.indexOf("windows") > -1) {
+ // cf. WinIOCTL.h
+ return (0x31 << 16 | (code) << 2);
+ }
+ // cf. reader.h
+ return 0x42000000 + (code);
+ }
+
+ static int IOCTL_GET_FEATURE_REQUEST = CTL_CODE(3400);
+
+ private static Map queryFeatures(Card icc) {
+ Map features = new HashMap();
+
+ if (icc == null) {
+ log.warn("invalid card handle, cannot query ifd features");
+ } else {
+ try {
+ if (log.isTraceEnabled()) {
+ log.trace("GET_FEATURE_REQUEST " + Integer.toHexString(IOCTL_GET_FEATURE_REQUEST));
+ }
+ byte[] resp = icc.transmitControlCommand(IOCTL_GET_FEATURE_REQUEST,
+ new byte[0]);
+
+ if (log.isTraceEnabled()) {
+ log.trace("Response TLV " + SMCCHelper.toString(resp));
+ }
+ // tag
+ // length in bytes (always 4)
+ // control code value for supported feature (in big endian)
+ for (int i = 0; i < resp.length; i += 6) {
+ Byte feature = new Byte(resp[i]);
+ Integer ioctl = new Integer((0xff & resp[i + 2]) << 24) |
+ ((0xff & resp[i + 3]) << 16) |
+ ((0xff & resp[i + 4]) << 8) |
+ (0xff & resp[i + 5]);
+ if (log.isInfoEnabled()) {
+ log.info("IFD supports " + CardReader.FEATURES[feature.intValue()] +
+ ": " + Integer.toHexString(ioctl.intValue()));
+ }
+ features.put(feature, ioctl);
+ }
+ } catch (CardException ex) {
+ log.debug("Failed to query IFD features: " + ex.getMessage());
+ log.trace(ex);
+ log.info("IFD does not support secure pin entry");
+ }
+ }
+ return features;
+ }
+
+}
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/AbstractAppl.java b/smcc/src/test/java/at/gv/egiz/smcc/AbstractAppl.java
index 137de509..affb06ff 100644
--- a/smcc/src/test/java/at/gv/egiz/smcc/AbstractAppl.java
+++ b/smcc/src/test/java/at/gv/egiz/smcc/AbstractAppl.java
@@ -51,6 +51,7 @@ public abstract class AbstractAppl implements CardAppl {
return files;
}
+ @Override
public abstract void setPin(int kid, char[] value);
}
\ No newline at end of file
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/CardEmul.java b/smcc/src/test/java/at/gv/egiz/smcc/CardEmul.java
index 6017bcce..3dfc8510 100644
--- a/smcc/src/test/java/at/gv/egiz/smcc/CardEmul.java
+++ b/smcc/src/test/java/at/gv/egiz/smcc/CardEmul.java
@@ -28,15 +28,15 @@ import javax.smartcardio.CardException;
@SuppressWarnings("restriction")
public abstract class CardEmul extends Card {
- protected Thread exclThread = null;
- protected CardChannel channel = newCardChannel(this);
+ protected Thread exclThread; // = null;
+ protected CardChannel channel; // = newCardChannel(this);
protected List applications = new ArrayList();
public CardEmul() {
super();
}
- protected abstract CardChannelEmul newCardChannel(CardEmul cardEmul);
+// protected abstract CardChannelEmul newCardChannel(CardEmul cardEmul);
@Override
public void beginExclusive() throws CardException {
@@ -71,9 +71,9 @@ public abstract class CardEmul extends Card {
@Override
public void disconnect(boolean reset) throws CardException {
- if (reset) {
- channel = newCardChannel(this);
- }
+// if (reset) {
+// channel = newCardChannel(this);
+// }
}
@Override
@@ -93,7 +93,7 @@ public abstract class CardEmul extends Card {
}
public AbstractAppl getApplication(byte[] fid) {
-
+
for(AbstractAppl appl : applications) {
if (Arrays.equals(appl.getAID(), fid) || Arrays.equals(appl.getFID(), fid)) {
return appl;
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/CardTest.java b/smcc/src/test/java/at/gv/egiz/smcc/CardTest.java
index b3bd07ab..44e48836 100644
--- a/smcc/src/test/java/at/gv/egiz/smcc/CardTest.java
+++ b/smcc/src/test/java/at/gv/egiz/smcc/CardTest.java
@@ -16,12 +16,14 @@
*/
package at.gv.egiz.smcc;
+import at.gv.egiz.smcc.pin.gui.CancelPINProvider;
+import at.gv.egiz.smcc.pin.gui.InterruptPINProvider;
+import at.gv.egiz.smcc.pin.gui.CancelChangePINProvider;
import static org.junit.Assert.*;
import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.UnsupportedEncodingException;
-import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.util.Arrays;
import java.util.List;
@@ -32,119 +34,15 @@ import org.junit.Test;
import at.gv.egiz.smcc.SignatureCard.KeyboxName;
import at.gv.egiz.smcc.acos.A04ApplDEC;
+import at.gv.egiz.smcc.pin.gui.DummyPINGUI;
+import at.gv.egiz.smcc.pin.gui.ModifyPINGUI;
+import at.gv.egiz.smcc.pin.gui.PINGUI;
+import at.gv.egiz.smcc.pin.gui.SMCCTestPINProvider;
+import org.junit.Ignore;
@SuppressWarnings("restriction")
public abstract class CardTest {
- public class TestPINProvider implements PINProvider {
-
- int provided = 0;
-
- char[] pin;
-
- public TestPINProvider(char[] pin) {
- super();
- this.pin = pin;
- }
-
- @Override
- public char[] providePIN(PINSpec spec, int retries)
- throws CancelledException, InterruptedException {
- provided++;
- return pin;
- }
-
- public int getProvided() {
- return provided;
- }
-
- }
-
- public class TestChangePINProvider extends TestPINProvider implements
- ChangePINProvider {
-
- char[] oldPin;
-
- public TestChangePINProvider(char[] oldPin, char[] pin) {
- super(pin);
- this.oldPin = oldPin;
- }
-
- @Override
- public char[] provideOldPIN(PINSpec spec, int retries)
- throws CancelledException, InterruptedException {
- return oldPin;
- }
-
- }
-
- public class TestInvalidPINProvider implements PINProvider {
-
- int provided = 0;
- int numWrongTries = 0;
-
- char[] pin;
-
- public TestInvalidPINProvider(char[] pin, int numWrongTries) {
- super();
- this.pin = pin;
- this.numWrongTries = numWrongTries;
- }
-
- @Override
- public char[] providePIN(PINSpec spec, int retries)
- throws CancelledException, InterruptedException {
- if (provided >= numWrongTries) {
- throw new CancelledException("Number of wrong tries reached: " + provided);
- } else {
- provided++;
- return pin;
- }
- }
-
- public int getProvided() {
- return provided;
- }
- }
-
- public class TestInvalidChangePINProvider implements ChangePINProvider {
-
- int provided = 0;
- int numWrongTries = 0;
-
- char[] pin;
- char[] oldPin;
-
- /** emulate ChangePinProvider */
- public TestInvalidChangePINProvider(char[] oldPin, char[] newPin, int numWrongTries) {
- super();
- this.pin = newPin;
- this.oldPin = oldPin;
- this.numWrongTries = numWrongTries;
- }
-
- @Override
- public char[] providePIN(PINSpec spec, int retries)
- throws CancelledException, InterruptedException {
- return pin;
- }
-
- public int getProvided() {
- return provided;
- }
-
- @Override
- public char[] provideOldPIN(PINSpec spec, int retries)
- throws CancelledException, InterruptedException {
- if (provided >= numWrongTries) {
- throw new CancelledException("Number of wrong tries reached: " + provided);
- } else {
- provided++;
- return oldPin;
- }
- }
- }
-
public CardTest() {
super();
}
@@ -167,7 +65,7 @@ public abstract class CardTest {
SignatureCard signatureCard = createSignatureCard();
- TestPINProvider pinProvider = new TestPINProvider(pin);
+ SMCCTestPINProvider pinProvider = new SMCCTestPINProvider(pin);
byte[] idlink = signatureCard.getInfobox("IdentityLink",
pinProvider, null);
@@ -184,13 +82,7 @@ public abstract class CardTest {
SignatureCard signatureCard = createSignatureCard();
- PINProvider pinProvider = new PINProvider() {
- @Override
- public char[] providePIN(PINSpec spec, int retries)
- throws CancelledException, InterruptedException {
- throw new CancelledException();
- }
- };
+ PINGUI pinProvider = new CancelPINProvider();
signatureCard.createSignature(new ByteArrayInputStream("MOCCA"
.getBytes("ASCII")), KeyboxName.SECURE_SIGNATURE_KEYPAIR, pinProvider,
@@ -205,13 +97,7 @@ public abstract class CardTest {
SignatureCard signatureCard = createSignatureCard();
- PINProvider pinProvider = new PINProvider() {
- @Override
- public char[] providePIN(PINSpec spec, int retries)
- throws CancelledException, InterruptedException {
- throw new CancelledException();
- }
- };
+ PINGUI pinProvider = new CancelPINProvider();
signatureCard.createSignature(new ByteArrayInputStream("MOCCA"
.getBytes("ASCII")), KeyboxName.CERITIFIED_KEYPAIR,
@@ -226,13 +112,7 @@ public abstract class CardTest {
SignatureCard signatureCard = createSignatureCard();
- PINProvider pinProvider = new PINProvider() {
- @Override
- public char[] providePIN(PINSpec spec, int retries)
- throws CancelledException, InterruptedException {
- throw new InterruptedException();
- }
- };
+ PINGUI pinProvider = new InterruptPINProvider();
signatureCard.createSignature(new ByteArrayInputStream("MOCCA"
.getBytes("ASCII")), KeyboxName.SECURE_SIGNATURE_KEYPAIR,
@@ -247,13 +127,7 @@ public abstract class CardTest {
SignatureCard signatureCard = createSignatureCard();
- PINProvider pinProvider = new PINProvider() {
- @Override
- public char[] providePIN(PINSpec spec, int retries)
- throws CancelledException, InterruptedException {
- throw new InterruptedException();
- }
- };
+ PINGUI pinProvider = new InterruptPINProvider();
signatureCard.createSignature(new ByteArrayInputStream("MOCCA"
.getBytes("ASCII")), KeyboxName.CERITIFIED_KEYPAIR,
@@ -268,11 +142,11 @@ public abstract class CardTest {
final SignatureCard signatureCard = createSignatureCard();
- PINProvider pinProvider = new PINProvider() {
+ PINGUI pinProvider = new DummyPINGUI() {
@Override
public char[] providePIN(PINSpec spec, int retries)
throws CancelledException, InterruptedException {
-
+
try {
signatureCard.getCertificate(KeyboxName.SECURE_SIGNATURE_KEYPAIR);
assertTrue(false);
@@ -281,10 +155,10 @@ public abstract class CardTest {
// expected
throw new CancelledException();
}
-
+
}
};
-
+
signatureCard.createSignature(new ByteArrayInputStream("MOCCA"
.getBytes("ASCII")), KeyboxName.SECURE_SIGNATURE_KEYPAIR,
pinProvider, null);
@@ -298,7 +172,7 @@ public abstract class CardTest {
final SignatureCard signatureCard = createSignatureCard();
- PINProvider pinProvider = new PINProvider() {
+ PINGUI pinProvider = new DummyPINGUI() {
@Override
public char[] providePIN(PINSpec spec, int retries)
throws CancelledException, InterruptedException {
@@ -311,7 +185,6 @@ public abstract class CardTest {
// expected
throw new CancelledException();
}
-
}
};
@@ -339,13 +212,7 @@ public abstract class CardTest {
PINMgmtSignatureCard signatureCard = (PINMgmtSignatureCard) createSignatureCard();
- PINProvider pinProvider = new PINProvider() {
- @Override
- public char[] providePIN(PINSpec spec, int retries)
- throws CancelledException, InterruptedException {
- throw new CancelledException();
- }
- };
+ ModifyPINGUI pinProvider = new CancelChangePINProvider();
List specs = signatureCard.getPINSpecs();
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/PIN.java b/smcc/src/test/java/at/gv/egiz/smcc/PIN.java
index ae883727..2cda0c2f 100644
--- a/smcc/src/test/java/at/gv/egiz/smcc/PIN.java
+++ b/smcc/src/test/java/at/gv/egiz/smcc/PIN.java
@@ -23,19 +23,23 @@ public class PIN {
public static final int STATE_PIN_VERIFIED = 1;
public static final int STATE_PIN_BLOCKED = -1;
+
+ public static final int STATE_PIN_NOTACTIVE = 2;
public byte[] pin;
public int kid;
- public int state = STATE_RESET;
+ public int state; // = STATE_RESET;
- public int kfpc = 10;
+ public int kfpc; // = 10;
- public PIN(byte[] pin, int kid, int kfpc) {
+ //TODO also provde default constructor without state param
+ public PIN(byte[] pin, int kid, int kfpc, int state) {
this.pin = pin;
this.kid = kid;
this.kfpc = kfpc;
+ this.state = state;
}
}
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/acos/A03ApplDEC.java b/smcc/src/test/java/at/gv/egiz/smcc/acos/A03ApplDEC.java
index 9fd96d73..f4ac5c35 100644
--- a/smcc/src/test/java/at/gv/egiz/smcc/acos/A03ApplDEC.java
+++ b/smcc/src/test/java/at/gv/egiz/smcc/acos/A03ApplDEC.java
@@ -40,7 +40,7 @@ public class A03ApplDEC extends ACOSApplDEC {
putFile(new File(FID_EF_INFOBOX, EF_INFOBOX, FCI_EF_INFOBOX, KID_PIN_INF));
try {
- pins.put(KID_PIN_INF, new PIN("0000\0\0\0\0".getBytes("ASCII"), KID_PIN_INF, 10));
+ pins.put(KID_PIN_INF, new PIN("0000\0\0\0\0".getBytes("ASCII"), KID_PIN_INF, 10, PIN.STATE_RESET));
} catch (UnsupportedEncodingException e) {
throw new RuntimeException(e);
}
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/acos/A03CardEmul.java b/smcc/src/test/java/at/gv/egiz/smcc/acos/A03CardEmul.java
index 58216b6b..7394bae7 100644
--- a/smcc/src/test/java/at/gv/egiz/smcc/acos/A03CardEmul.java
+++ b/smcc/src/test/java/at/gv/egiz/smcc/acos/A03CardEmul.java
@@ -24,13 +24,8 @@ import at.gv.egiz.smcc.CardEmul;
public class A03CardEmul extends ACOSCardEmul {
public A03CardEmul(A03ApplSIG applSIG, A03ApplDEC applDEC) {
+ channel = new A03CardChannelEmul(this);
applications.add(applSIG);
applications.add(applDEC);
}
-
- @Override
- protected CardChannelEmul newCardChannel(CardEmul cardEmul) {
- return new A03CardChannelEmul(this);
- }
-
}
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/acos/A03CardTest.java b/smcc/src/test/java/at/gv/egiz/smcc/acos/A03CardTest.java
index 776c0370..3a8ac41c 100644
--- a/smcc/src/test/java/at/gv/egiz/smcc/acos/A03CardTest.java
+++ b/smcc/src/test/java/at/gv/egiz/smcc/acos/A03CardTest.java
@@ -22,15 +22,16 @@ import java.util.Arrays;
import org.junit.Test;
-import at.gv.egiz.smcc.ACOSCard;
import at.gv.egiz.smcc.CancelledException;
import at.gv.egiz.smcc.CardEmul;
import at.gv.egiz.smcc.CardNotSupportedException;
import at.gv.egiz.smcc.CardTerminalEmul;
+import at.gv.egiz.smcc.pin.gui.ChangePINProvider;
import at.gv.egiz.smcc.LockedException;
import at.gv.egiz.smcc.NotActivatedException;
import at.gv.egiz.smcc.PINFormatException;
import at.gv.egiz.smcc.PINMgmtSignatureCard;
+import at.gv.egiz.smcc.pin.gui.SMCCTestPINProvider;
import at.gv.egiz.smcc.PINSpec;
import at.gv.egiz.smcc.SignatureCard;
import at.gv.egiz.smcc.SignatureCardException;
@@ -74,12 +75,12 @@ public class A03CardTest extends ACOSCardTest {
char[] pin = defaultPin;
for (int i = pinSpec.getMinLength(); i <= pinSpec.getMaxLength(); i++) {
- signatureCard.verifyPIN(pinSpec, new TestPINProvider(pin));
+ signatureCard.verifyPIN(pinSpec, new SMCCTestPINProvider(pin));
char[] newPin = new char[i];
Arrays.fill(newPin, '0');
signatureCard
- .changePIN(pinSpec, new TestChangePINProvider(pin, newPin));
- signatureCard.verifyPIN(pinSpec, new TestPINProvider(newPin));
+ .changePIN(pinSpec, new ChangePINProvider(pin, newPin));
+ signatureCard.verifyPIN(pinSpec, new SMCCTestPINProvider(newPin));
pin = newPin;
}
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/acos/A04CardEmul.java b/smcc/src/test/java/at/gv/egiz/smcc/acos/A04CardEmul.java
index 70925aa6..dd44d05b 100644
--- a/smcc/src/test/java/at/gv/egiz/smcc/acos/A04CardEmul.java
+++ b/smcc/src/test/java/at/gv/egiz/smcc/acos/A04CardEmul.java
@@ -24,14 +24,9 @@ import at.gv.egiz.smcc.CardEmul;
public class A04CardEmul extends ACOSCardEmul {
public A04CardEmul(A04ApplSIG applSIG, A04ApplDEC applDEC) {
+ channel = new A04CardChannelEmul(this);
applications.add(applSIG);
applications.add(applDEC);
}
-
- @Override
- protected CardChannelEmul newCardChannel(CardEmul cardEmul) {
- return new A04CardChannelEmul(this);
- }
-
}
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/acos/A04CardTest.java b/smcc/src/test/java/at/gv/egiz/smcc/acos/A04CardTest.java
index d15e80d7..1cbea1b3 100644
--- a/smcc/src/test/java/at/gv/egiz/smcc/acos/A04CardTest.java
+++ b/smcc/src/test/java/at/gv/egiz/smcc/acos/A04CardTest.java
@@ -28,7 +28,6 @@ import java.util.Arrays;
import org.junit.BeforeClass;
import org.junit.Test;
-import at.gv.egiz.smcc.ACOSCard;
import at.gv.egiz.smcc.CancelledException;
import at.gv.egiz.smcc.CardEmul;
import at.gv.egiz.smcc.CardNotSupportedException;
@@ -41,7 +40,8 @@ import at.gv.egiz.smcc.PINSpec;
import at.gv.egiz.smcc.SignatureCard;
import at.gv.egiz.smcc.SignatureCardException;
import at.gv.egiz.smcc.SignatureCardFactory;
-import at.gv.egiz.smcc.CardTest.TestPINProvider;
+import at.gv.egiz.smcc.pin.gui.ChangePINProvider;
+import at.gv.egiz.smcc.pin.gui.SMCCTestPINProvider;
public class A04CardTest extends ACOSCardTest {
@@ -88,8 +88,8 @@ public class A04CardTest extends ACOSCardTest {
char[] newPin = new char[i];
Arrays.fill(newPin, '0');
signatureCard
- .changePIN(pinSpec, new TestChangePINProvider(pin, newPin));
- signatureCard.verifyPIN(pinSpec, new TestPINProvider(newPin));
+ .changePIN(pinSpec, new ChangePINProvider(pin, newPin));
+ signatureCard.verifyPIN(pinSpec, new SMCCTestPINProvider(newPin));
pin = newPin;
}
@@ -111,7 +111,7 @@ public class A04CardTest extends ACOSCardTest {
SignatureCard signatureCard = factory.createSignatureCard(card,
new CardTerminalEmul(card));
- TestPINProvider pinProvider = new TestPINProvider(pin);
+ SMCCTestPINProvider pinProvider = new SMCCTestPINProvider(pin);
byte[] idlink = signatureCard.getInfobox("IdentityLink",
pinProvider, null);
@@ -129,7 +129,7 @@ public class A04CardTest extends ACOSCardTest {
SignatureCard signatureCard = createSignatureCard();
- TestPINProvider pinProvider = new TestPINProvider(pin);
+ SMCCTestPINProvider pinProvider = new SMCCTestPINProvider(pin);
byte[] idlink = signatureCard.getInfobox("IdentityLink",
pinProvider, null);
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/acos/ACOSApplDEC.java b/smcc/src/test/java/at/gv/egiz/smcc/acos/ACOSApplDEC.java
index 08979536..09a754f3 100644
--- a/smcc/src/test/java/at/gv/egiz/smcc/acos/ACOSApplDEC.java
+++ b/smcc/src/test/java/at/gv/egiz/smcc/acos/ACOSApplDEC.java
@@ -297,7 +297,7 @@ public abstract class ACOSApplDEC extends ACOSAppl {
System.arraycopy(C_CH_EKEY, 0, EF_C_CH_EKEY, 0, C_CH_EKEY.length);
putFile(new File(FID_EF_C_CH_EKEY, EF_C_CH_EKEY, FCI_EF_C_CH_EKEY));
try {
- pins.put(KID_PIN_DEC, new PIN("1234\0\0\0\0".getBytes("ASCII"), KID_PIN_DEC, 10));
+ pins.put(KID_PIN_DEC, new PIN("1234\0\0\0\0".getBytes("ASCII"), KID_PIN_DEC, 10, PIN.STATE_RESET));
} catch (UnsupportedEncodingException e) {
throw new RuntimeException(e);
}
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/acos/ACOSApplSIG.java b/smcc/src/test/java/at/gv/egiz/smcc/acos/ACOSApplSIG.java
index e476b434..6ab5903a 100644
--- a/smcc/src/test/java/at/gv/egiz/smcc/acos/ACOSApplSIG.java
+++ b/smcc/src/test/java/at/gv/egiz/smcc/acos/ACOSApplSIG.java
@@ -221,7 +221,7 @@ public abstract class ACOSApplSIG extends ACOSAppl {
// PINs
try {
- pins.put(KID_PIN_SIG, new PIN(Arrays.copyOf("123456".getBytes("ASCII"), 8), KID_PIN_SIG, 3));
+ pins.put(KID_PIN_SIG, new PIN(Arrays.copyOf("123456".getBytes("ASCII"), 8), KID_PIN_SIG, 3, PIN.STATE_RESET));
} catch (UnsupportedEncodingException e) {
throw new RuntimeException(e);
}
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/acos/ACOSCardTest.java b/smcc/src/test/java/at/gv/egiz/smcc/acos/ACOSCardTest.java
index 56d1e4b2..4f012739 100644
--- a/smcc/src/test/java/at/gv/egiz/smcc/acos/ACOSCardTest.java
+++ b/smcc/src/test/java/at/gv/egiz/smcc/acos/ACOSCardTest.java
@@ -16,26 +16,23 @@
*/
package at.gv.egiz.smcc.acos;
-import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertNull;
import static org.junit.Assert.assertTrue;
import java.io.ByteArrayInputStream;
import java.io.IOException;
-import java.io.UnsupportedEncodingException;
-import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.util.Arrays;
import org.junit.Test;
-import at.gv.egiz.smcc.ACOSCard;
import at.gv.egiz.smcc.CardEmul;
import at.gv.egiz.smcc.CardNotSupportedException;
import at.gv.egiz.smcc.CardTest;
import at.gv.egiz.smcc.LockedException;
import at.gv.egiz.smcc.NotActivatedException;
+import at.gv.egiz.smcc.pin.gui.SMCCTestPINProvider;
import at.gv.egiz.smcc.SignatureCard;
import at.gv.egiz.smcc.SignatureCardException;
import at.gv.egiz.smcc.SignatureCard.KeyboxName;
@@ -60,7 +57,7 @@ public abstract class ACOSCardTest extends CardTest {
appl.clearInfobox();
byte[] idlink = signatureCard.getInfobox("IdentityLink",
- new TestPINProvider(pin), null);
+ new SMCCTestPINProvider(pin), null);
assertNull(idlink);
}
@@ -76,7 +73,7 @@ public abstract class ACOSCardTest extends CardTest {
ACOSApplDEC appl = (ACOSApplDEC) card.getApplication(ACOSAppl.AID_DEC);
appl.setInfoboxHeader((byte) 0xFF);
- signatureCard.getInfobox("IdentityLink", new TestPINProvider(pin), null);
+ signatureCard.getInfobox("IdentityLink", new SMCCTestPINProvider(pin), null);
}
@@ -138,7 +135,7 @@ public abstract class ACOSCardTest extends CardTest {
byte[] signature = signatureCard.createSignature(new ByteArrayInputStream("MOCCA"
.getBytes("ASCII")),
- KeyboxName.SECURE_SIGNATURE_KEYPAIR, new TestPINProvider(pin), null);
+ KeyboxName.SECURE_SIGNATURE_KEYPAIR, new SMCCTestPINProvider(pin), null);
assertNotNull(signature);
@@ -158,7 +155,7 @@ public abstract class ACOSCardTest extends CardTest {
byte[] signature = signatureCard.createSignature(new ByteArrayInputStream("MOCCA"
.getBytes("ASCII")),
- KeyboxName.CERITIFIED_KEYPAIR, new TestPINProvider(pin), null);
+ KeyboxName.CERITIFIED_KEYPAIR, new SMCCTestPINProvider(pin), null);
assertNotNull(signature);
@@ -171,7 +168,7 @@ public abstract class ACOSCardTest extends CardTest {
SignatureCard signatureCard = createSignatureCard();
- TestPINProvider pinProvider = new TestPINProvider("000000".toCharArray());
+ SMCCTestPINProvider pinProvider = new SMCCTestPINProvider("000000".toCharArray());
signatureCard.createSignature(new ByteArrayInputStream("MOCCA"
.getBytes("ASCII")), KeyboxName.SECURE_SIGNATURE_KEYPAIR,
@@ -186,7 +183,7 @@ public abstract class ACOSCardTest extends CardTest {
SignatureCard signatureCard = createSignatureCard();
- TestPINProvider pinProvider = new TestPINProvider("0000".toCharArray());
+ SMCCTestPINProvider pinProvider = new SMCCTestPINProvider("0000".toCharArray());
signatureCard.createSignature(new ByteArrayInputStream("MOCCA"
.getBytes("ASCII")), KeyboxName.CERITIFIED_KEYPAIR,
@@ -204,7 +201,7 @@ public abstract class ACOSCardTest extends CardTest {
ACOSApplSIG appl = (ACOSApplSIG) card.getApplication(ACOSAppl.AID_SIG);
appl.setPin(ACOSApplSIG.KID_PIN_SIG, null);
- TestPINProvider pinProvider = new TestPINProvider("000000".toCharArray());
+ SMCCTestPINProvider pinProvider = new SMCCTestPINProvider("000000".toCharArray());
signatureCard.createSignature(new ByteArrayInputStream("MOCCA"
.getBytes("ASCII")), KeyboxName.SECURE_SIGNATURE_KEYPAIR,
@@ -222,7 +219,7 @@ public abstract class ACOSCardTest extends CardTest {
ACOSApplDEC appl = (ACOSApplDEC) card.getApplication(ACOSAppl.AID_DEC);
appl.setPin(ACOSApplDEC.KID_PIN_DEC, null);
- TestPINProvider pinProvider = new TestPINProvider("0000".toCharArray());
+ SMCCTestPINProvider pinProvider = new SMCCTestPINProvider("0000".toCharArray());
signatureCard.createSignature(new ByteArrayInputStream("MOCCA"
.getBytes("ASCII")), KeyboxName.CERITIFIED_KEYPAIR,
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/CancelChangePINProvider.java b/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/CancelChangePINProvider.java
new file mode 100644
index 00000000..dffe7e29
--- /dev/null
+++ b/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/CancelChangePINProvider.java
@@ -0,0 +1,39 @@
+/*
+ * Copyright 2008 Federal Chancellery Austria and
+ * Graz University of Technology
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package at.gv.egiz.smcc.pin.gui;
+
+import at.gv.egiz.smcc.CancelledException;
+import at.gv.egiz.smcc.PINSpec;
+
+public class CancelChangePINProvider extends DummyChangePINGUI implements ModifyPINGUI {
+
+ public CancelChangePINProvider() {
+ }
+
+ @Override
+ public char[] provideCurrentPIN(PINSpec spec, int retries)
+ throws CancelledException, InterruptedException {
+ throw new CancelledException("cancelled by cancelPINProvider");
+ }
+
+ @Override
+ public char[] provideNewPIN(PINSpec spec)
+ throws CancelledException, InterruptedException {
+ throw new CancelledException("cancelled by cancelPINProvider");
+ }
+
+}
\ No newline at end of file
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/CancelPINProvider.java b/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/CancelPINProvider.java
new file mode 100644
index 00000000..77f19345
--- /dev/null
+++ b/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/CancelPINProvider.java
@@ -0,0 +1,29 @@
+/*
+ * Copyright 2008 Federal Chancellery Austria and
+ * Graz University of Technology
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package at.gv.egiz.smcc.pin.gui;
+
+import at.gv.egiz.smcc.CancelledException;
+import at.gv.egiz.smcc.PINSpec;
+
+public class CancelPINProvider extends DummyPINGUI implements PINGUI {
+
+ @Override
+ public char[] providePIN(PINSpec spec, int retries)
+ throws CancelledException, InterruptedException {
+ throw new CancelledException("cancelled by cancelPINProvider");
+ }
+}
\ No newline at end of file
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/ChangePINProvider.java b/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/ChangePINProvider.java
new file mode 100644
index 00000000..5eb8b9a1
--- /dev/null
+++ b/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/ChangePINProvider.java
@@ -0,0 +1,49 @@
+/*
+ * Copyright 2008 Federal Chancellery Austria and
+ * Graz University of Technology
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package at.gv.egiz.smcc.pin.gui;
+
+import at.gv.egiz.smcc.CancelledException;
+import at.gv.egiz.smcc.PINSpec;
+
+public class ChangePINProvider extends DummyChangePINGUI implements ModifyPINGUI {
+
+ int provided = 0;
+ char[] pin;
+ char[] oldPin;
+
+ public ChangePINProvider(char[] oldPin, char[] pin) {
+ this.pin = pin;
+ this.oldPin = oldPin;
+ }
+
+ public int getProvided() {
+ return provided;
+ }
+
+ @Override
+ public char[] provideCurrentPIN(PINSpec spec, int retries)
+ throws CancelledException, InterruptedException {
+ provided++;
+ return oldPin;
+ }
+
+ @Override
+ public char[] provideNewPIN(PINSpec spec) {
+ return pin;
+ }
+
+}
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/DummyChangePINGUI.java b/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/DummyChangePINGUI.java
new file mode 100644
index 00000000..fff89409
--- /dev/null
+++ b/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/DummyChangePINGUI.java
@@ -0,0 +1,68 @@
+/*
+ * Copyright 2008 Federal Chancellery Austria and
+ * Graz University of Technology
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package at.gv.egiz.smcc.pin.gui;
+
+import at.gv.egiz.smcc.CancelledException;
+import at.gv.egiz.smcc.PINSpec;
+
+public abstract class DummyChangePINGUI implements ModifyPINGUI {
+
+ @Override
+ public void validKeyPressed() {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+
+ @Override
+ public void correctionButtonPressed() {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+
+ @Override
+ public void allKeysCleared() {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+
+ @Override
+ public void finish() {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+
+ @Override
+ public void finishDirect() {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+
+ @Override
+ public void modifyPINDirect(PINSpec spec, int retries) throws CancelledException, InterruptedException {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+
+ @Override
+ public void enterCurrentPIN(PINSpec spec, int retries) {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+
+ @Override
+ public void enterNewPIN(PINSpec spec) {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+
+ @Override
+ public void confirmNewPIN(PINSpec spec) {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+}
\ No newline at end of file
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/DummyPINGUI.java b/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/DummyPINGUI.java
new file mode 100644
index 00000000..4d99b5c1
--- /dev/null
+++ b/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/DummyPINGUI.java
@@ -0,0 +1,48 @@
+/*
+ * Copyright 2008 Federal Chancellery Austria and
+ * Graz University of Technology
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package at.gv.egiz.smcc.pin.gui;
+
+import at.gv.egiz.smcc.CancelledException;
+import at.gv.egiz.smcc.PINSpec;
+
+public abstract class DummyPINGUI implements PINGUI {
+
+ @Override
+ public void enterPINDirect(PINSpec spec, int retries) throws CancelledException, InterruptedException {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+
+ @Override
+ public void enterPIN(PINSpec spec, int retries) throws CancelledException, InterruptedException {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+
+ @Override
+ public void validKeyPressed() {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+
+ @Override
+ public void correctionButtonPressed() {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+
+ @Override
+ public void allKeysCleared() {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+}
\ No newline at end of file
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/InterruptPINProvider.java b/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/InterruptPINProvider.java
new file mode 100644
index 00000000..5706b888
--- /dev/null
+++ b/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/InterruptPINProvider.java
@@ -0,0 +1,34 @@
+/*
+ * Copyright 2008 Federal Chancellery Austria and
+ * Graz University of Technology
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package at.gv.egiz.smcc.pin.gui;
+
+import at.gv.egiz.smcc.CancelledException;
+import at.gv.egiz.smcc.PINSpec;
+
+@SuppressWarnings("restriction")
+public class InterruptPINProvider extends DummyPINGUI implements PINGUI {
+
+ public InterruptPINProvider() {
+ }
+
+ @Override
+ public char[] providePIN(PINSpec spec, int retries)
+ throws CancelledException, InterruptedException {
+ throw new InterruptedException("interrupted by cancelPINProvider");
+ }
+
+}
\ No newline at end of file
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/InvalidChangePINProvider.java b/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/InvalidChangePINProvider.java
new file mode 100644
index 00000000..69c9f42a
--- /dev/null
+++ b/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/InvalidChangePINProvider.java
@@ -0,0 +1,56 @@
+/*
+ * Copyright 2008 Federal Chancellery Austria and
+ * Graz University of Technology
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package at.gv.egiz.smcc.pin.gui;
+
+import at.gv.egiz.smcc.CancelledException;
+import at.gv.egiz.smcc.PINSpec;
+
+public class InvalidChangePINProvider extends DummyChangePINGUI implements ModifyPINGUI {
+
+ int provided = 0;
+ int numWrongTries = 0;
+ char[] pin;
+ char[] oldPin;
+
+ /** emulate ChangePinProvider */
+ public InvalidChangePINProvider(char[] oldPin, char[] newPin, int numWrongTries) {
+ super();
+ this.pin = newPin;
+ this.oldPin = oldPin;
+ this.numWrongTries = numWrongTries;
+ }
+
+ @Override
+ public char[] provideCurrentPIN(PINSpec spec, int retries)
+ throws CancelledException, InterruptedException {
+ if (provided >= numWrongTries) {
+ throw new CancelledException("Number of wrong tries reached: " + provided);
+ } else {
+ provided++;
+ return oldPin;
+ }
+ }
+
+ public int getProvided() {
+ return provided;
+ }
+
+ @Override
+ public char[] provideNewPIN(PINSpec spec) {
+ return pin;
+ }
+}
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/InvalidPINProvider.java b/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/InvalidPINProvider.java
new file mode 100644
index 00000000..db01fd0d
--- /dev/null
+++ b/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/InvalidPINProvider.java
@@ -0,0 +1,48 @@
+/*
+ * Copyright 2008 Federal Chancellery Austria and
+ * Graz University of Technology
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package at.gv.egiz.smcc.pin.gui;
+
+import at.gv.egiz.smcc.CancelledException;
+import at.gv.egiz.smcc.PINSpec;
+
+public class InvalidPINProvider extends DummyPINGUI implements PINGUI {
+
+ int provided = 0;
+ int numWrongTries = 0;
+ char[] pin;
+
+ public InvalidPINProvider(char[] pin, int numWrongTries) {
+ super();
+ this.pin = pin;
+ this.numWrongTries = numWrongTries;
+ }
+
+ @Override
+ public char[] providePIN(PINSpec spec, int retries)
+ throws CancelledException, InterruptedException {
+ if (provided >= numWrongTries) {
+ throw new CancelledException("Number of wrong tries reached: " + provided);
+ } else {
+ provided++;
+ return pin;
+ }
+ }
+
+ public int getProvided() {
+ return provided;
+ }
+}
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/SMCCTestPINProvider.java b/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/SMCCTestPINProvider.java
new file mode 100644
index 00000000..dffc90d7
--- /dev/null
+++ b/smcc/src/test/java/at/gv/egiz/smcc/pin/gui/SMCCTestPINProvider.java
@@ -0,0 +1,43 @@
+/*
+ * Copyright 2008 Federal Chancellery Austria and
+ * Graz University of Technology
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package at.gv.egiz.smcc.pin.gui;
+
+import at.gv.egiz.smcc.CancelledException;
+import at.gv.egiz.smcc.PINSpec;
+
+public class SMCCTestPINProvider extends DummyPINGUI implements PINGUI {
+
+ public int provided = 0;
+ char[] pin;
+
+ public SMCCTestPINProvider(char[] pin) {
+ this.pin = pin;
+ }
+
+ @Override
+ public char[] providePIN(PINSpec spec, int retries)
+ throws CancelledException, InterruptedException {
+ provided++;
+ return pin;
+ }
+
+ public int getProvided() {
+ return provided;
+ }
+
+
+}
\ No newline at end of file
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSAppl.java b/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSAppl.java
index 2ca63eea..62528e6e 100644
--- a/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSAppl.java
+++ b/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSAppl.java
@@ -69,27 +69,4 @@ public abstract class STARCOSAppl extends AbstractAppl implements CardAppl {
pin.next().state = PIN.STATE_RESET;
}
}
-
- public void setPin(int kid, char[] value) {
- PIN pin = pins.get(kid);
- if (pin != null) {
- if (value == null) {
- pin.pin = null;
- } else {
- byte[] b = new byte[8];
- b[0] = (byte) (0x20 | value.length);
- for(int i = 1, j = 0; i < b.length; i++) {
- int h = ((j < value.length)
- ? Character.digit(value[j++], 10)
- : 0x0F);
- int l = ((j < value.length)
- ? Character.digit(value[j++], 10)
- : 0x0F);
- b[i] = (byte) ((h << 4) | l);
- }
- pin.pin = b;
- }
- }
- }
-
}
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSApplGewoehnlicheSignatur.java b/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSApplGewoehnlicheSignatur.java
index cec305da..8741dd2d 100644
--- a/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSApplGewoehnlicheSignatur.java
+++ b/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSApplGewoehnlicheSignatur.java
@@ -16,7 +16,6 @@
*/
package at.gv.egiz.smcc.starcos;
-import java.io.UnsupportedEncodingException;
import java.util.Arrays;
import java.util.Random;
@@ -200,12 +199,18 @@ public class STARCOSApplGewoehnlicheSignatur extends STARCOSAppl {
protected byte[] EF_C_X509_CH_AUT = new byte[2000];
-
- public STARCOSApplGewoehnlicheSignatur(STARCOSCardChannelEmul channel) {
+
+ protected byte[] dst;
+
+ public static final byte[] DST = new byte[] { (byte) 0x84, (byte) 0x03, (byte) 0x80, (byte) 0x02, (byte) 0x00, (byte) 0x89, (byte) 0x03, (byte) 0x13, (byte) 0x35, (byte) 0x10};
+ public static final byte[] DST_G3 = new byte[] { (byte) 0x84, (byte) 0x03, (byte) 0x80, (byte) 0x02, (byte) 0x00, (byte) 0x80, (byte) 0x01, (byte) 0x04 };
+
+ public STARCOSApplGewoehnlicheSignatur(STARCOSCardChannelEmul channel, byte[] dst) {
super(channel);
// Files
System.arraycopy(C_X509_CH_AUT, 0, EF_C_X509_CH_AUT, 0, C_X509_CH_AUT.length);
putFile(new File(FID_EF_C_X509_CH_AUT, EF_C_X509_CH_AUT, FCI_EF_C_X509_CH_AUT));
+ this.dst = dst;
}
@Override
@@ -240,12 +245,19 @@ public class STARCOSApplGewoehnlicheSignatur extends STARCOSAppl {
case 0x81:
// EXTERNAL AUTHENTICATE
}
+ case 0xAA:
+ switch (command.getP1()) {
+ case 0x41:
+ if (Arrays.equals(new byte[] {(byte) 0x80, (byte) 0x01, (byte) 0x10}, command.getData())) {
+ return new ResponseAPDU(new byte[] {(byte) 0x90, (byte) 0x00});
+ }
+ default:
+ return new ResponseAPDU(new byte[] {(byte) 0x6A, (byte) 0x80});
+ }
case 0xB6:
switch (command.getP1()) {
case 0x41: {
// PSO - COMPUTE DIGITAL SIGNATURE
- byte[] dst = new byte[] { (byte) 0x84, (byte) 0x03, (byte) 0x80,
- (byte) 0x02, (byte) 0x00, (byte) 0x89, (byte) 0x03, (byte) 0x13, (byte) 0x35, (byte) 0x10};
if (Arrays.equals(dst, command.getData())) {
securityEnv = command.getData();
return new ResponseAPDU(new byte[] {(byte) 0x90, (byte) 0x00});
@@ -328,5 +340,10 @@ public class STARCOSApplGewoehnlicheSignatur extends STARCOSAppl {
}
+ @Override
+ public void setPin(int kid, char[] value) {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+
}
\ No newline at end of file
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSApplInfobox.java b/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSApplInfobox.java
index b7835a43..c470351a 100644
--- a/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSApplInfobox.java
+++ b/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSApplInfobox.java
@@ -156,5 +156,10 @@ public class STARCOSApplInfobox extends STARCOSAppl {
throw new CardException("Not supported.");
}
+ @Override
+ public void setPin(int kid, char[] value) {
+ throw new UnsupportedOperationException("Not supported yet.");
+ }
+
}
\ No newline at end of file
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSApplSichereSignatur.java b/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSApplSichereSignatur.java
index 9fb5ad37..4036ca41 100644
--- a/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSApplSichereSignatur.java
+++ b/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSApplSichereSignatur.java
@@ -213,16 +213,14 @@ public class STARCOSApplSichereSignatur extends STARCOSAppl {
protected byte[] EF_C_X509_CH_DS = new byte[2000];
- public STARCOSApplSichereSignatur(STARCOSCardChannelEmul channel) {
+ public STARCOSApplSichereSignatur(STARCOSCardChannelEmul channel, byte[] SS_pin, int pinState) {
super(channel);
// Files
System.arraycopy(C_X509_CH_DS, 0, EF_C_X509_CH_DS, 0, C_X509_CH_DS.length);
putFile(new File(FID_EF_C_X509_CH_DS, EF_C_X509_CH_DS, FCI_EF_C_X509_CH_DS));
// PINs
- pins.put(KID_PIN_SS, new PIN(new byte[] { (byte) 0x24, (byte) 0x12,
- (byte) 0x34, (byte) 0x56, (byte) 0xFF, (byte) 0xFF, (byte) 0xFF,
- (byte) 0xFF }, KID_PIN_SS, 3));
+ pins.put(KID_PIN_SS, new PIN(SS_pin, KID_PIN_SS, 3, pinState));
}
@Override
@@ -344,4 +342,34 @@ public class STARCOSApplSichereSignatur extends STARCOSAppl {
}
+ /**
+ * set and activate pin
+ * @param value if null, pin will be set to NOTACTIVE
+ */
+ @Override
+ public void setPin(int kid, char[] value) {
+ PIN pin = pins.get(kid);
+ if (pin != null) {
+ if (value == null) {
+// pin.pin = null;
+ //TransportPIN
+// pin.pin = new byte[] { (byte) 0x26, (byte) 0x12, (byte) 0x34, (byte) 0x56, (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff};
+ pin.state = PIN.STATE_PIN_NOTACTIVE;
+ } else {
+ byte[] b = new byte[8];
+ b[0] = (byte) (0x20 | value.length);
+ for(int i = 1, j = 0; i < b.length; i++) {
+ int h = ((j < value.length)
+ ? Character.digit(value[j++], 10)
+ : 0x0F);
+ int l = ((j < value.length)
+ ? Character.digit(value[j++], 10)
+ : 0x0F);
+ b[i] = (byte) ((h << 4) | l);
+ }
+ pin.pin = b;
+ pin.state = PIN.STATE_RESET;
+ }
+ }
+ }
}
\ No newline at end of file
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSCardChannelEmul.java b/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSCardChannelEmul.java
index 89030894..2e0c54eb 100644
--- a/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSCardChannelEmul.java
+++ b/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSCardChannelEmul.java
@@ -16,7 +16,6 @@
*/
package at.gv.egiz.smcc.starcos;
-import java.io.UnsupportedEncodingException;
import java.util.Arrays;
import java.util.HashMap;
@@ -30,6 +29,8 @@ import at.gv.egiz.smcc.CardChannelEmul;
import at.gv.egiz.smcc.CardEmul;
import at.gv.egiz.smcc.File;
import at.gv.egiz.smcc.PIN;
+import java.util.ArrayList;
+import java.util.List;
@SuppressWarnings("restriction")
public class STARCOSCardChannelEmul extends CardChannelEmul {
@@ -40,14 +41,13 @@ public class STARCOSCardChannelEmul extends CardChannelEmul {
*
*/
protected CardEmul cardEmul;
-
+
+ public final List globalFiles = new ArrayList();
public final HashMap globalPins = new HashMap();
- public STARCOSCardChannelEmul(CardEmul cardEmul) {
+ public STARCOSCardChannelEmul(CardEmul cardEmul, byte[] Glob_PIN, int PIN_STATE) {
this.cardEmul = cardEmul;
- globalPins.put(KID_PIN_Glob, new PIN(new byte[] { (byte) 0x24, (byte) 0x00,
- (byte) 0x00, (byte) 0xFF, (byte) 0xFF, (byte) 0xFF, (byte) 0xFF,
- (byte) 0xFF }, KID_PIN_Glob, 10));
+ globalPins.put(KID_PIN_Glob, new PIN(Glob_PIN, KID_PIN_Glob, 10, PIN_STATE));
}
@Override
@@ -88,6 +88,21 @@ public class STARCOSCardChannelEmul extends CardChannelEmul {
}
}
return new ResponseAPDU(new byte[] {(byte) 0x6A, (byte) 0x82});
+ } else if (globalFiles != null) {
+ if (command.getP2() != 0x04) {
+ throw new CardException("Not supported.");
+ }
+ for (File file : globalFiles) {
+ if (Arrays.equals(fid, file.fid)) {
+ currentFile = file;
+ byte[] response = new byte[file.fcx.length + 2];
+ System.arraycopy(file.fcx, 0, response, 0, file.fcx.length);
+ response[file.fcx.length] = (byte) 0x90;
+ response[file.fcx.length + 1] = (byte) 0x00;
+ return new ResponseAPDU(response);
+ }
+ }
+ return new ResponseAPDU(new byte[] {(byte) 0x6A, (byte) 0x82});
} else {
throw new CardException("Not supported.");
}
@@ -121,6 +136,23 @@ public class STARCOSCardChannelEmul extends CardChannelEmul {
}
+ protected ResponseAPDU cmdREAD_RECORD(CommandAPDU command) throws CardException {
+ if (command.getINS() != 0xB2) {
+ throw new IllegalArgumentException("INS has to be 0xB2");
+ }
+ if (currentFile == null) {
+ return new ResponseAPDU(new byte[]{ (byte) 0x69, (byte) 0x86 });
+ }
+ if (command.getP1() != 0x01 || command.getP2() != 0x04) {
+ throw new CardException("Not implemented.");
+ }
+ byte[] response = new byte[currentFile.file.length + 2];
+ System.arraycopy(currentFile.file, 0, response, 0, currentFile.file.length);
+ response[currentFile.file.length] = (byte) 0x90;
+ response[currentFile.file.length + 1] = (byte) 0x00;
+ return new ResponseAPDU(response);
+ }
+
protected ResponseAPDU cmdREAD_BINARY(CommandAPDU command) throws CardException {
if (command.getINS() != 0xB0) {
@@ -192,6 +224,10 @@ public class STARCOSCardChannelEmul extends CardChannelEmul {
case 0xB0:
return cmdREAD_BINARY(command);
+ // READ RECORD
+ case 0xB2:
+ return cmdREAD_RECORD(command);
+
// VERIFY
case 0x20:
return cmdVERIFY(command);
@@ -248,9 +284,15 @@ public class STARCOSCardChannelEmul extends CardChannelEmul {
}
if (pin != null) {
-
- if (reference.length == 0) {
- return new ResponseAPDU(new byte[] { (byte) 0x63, (byte) (pin.kfpc | 0xC0)});
+
+ if (reference == null || reference.length == 0) {
+ if (pin.state == PIN.STATE_PIN_NOTACTIVE) {
+ return new ResponseAPDU(new byte[] { (byte) 0x69, (byte) 0x84 });
+ } else if (pin.state == PIN.STATE_PIN_BLOCKED) {
+ return new ResponseAPDU(new byte[] { (byte) 0x63, (byte) 0xc0 });
+ } else {
+ return new ResponseAPDU(new byte[] { (byte) 0x63, (byte) (pin.kfpc | 0xC0)});
+ }
}
if (reference.length != 8) {
@@ -264,7 +306,7 @@ public class STARCOSCardChannelEmul extends CardChannelEmul {
case PIN.STATE_RESET:
pin.state = PIN.STATE_PIN_VERIFIED;
-
+
default:
pin.kfpc = 10;
return new ResponseAPDU(new byte[] { (byte) 0x90, (byte) 0x00 });
@@ -321,7 +363,20 @@ public class STARCOSCardChannelEmul extends CardChannelEmul {
return new ResponseAPDU(new byte[] {(byte) 0x67, (byte) 0x00});
}
- response = verifyPin(0xFF & command.getP2(), data);
+ PIN pin;
+ if (currentAppl != null) {
+ pin = currentAppl.pins.get(command.getP2());
+ } else {
+ pin = globalPins.get(command.getP2());
+ }
+ if (pin.state == PIN.STATE_PIN_NOTACTIVE) {
+ pin.pin = data;
+ pin.state = PIN.STATE_RESET;
+ response = new ResponseAPDU(new byte[] { (byte) 0x90, (byte) 0x00 });
+ } else {
+ // P1 == 0x01 not allowed on active pin (?)
+ response = new ResponseAPDU(new byte[] { (byte) 0x6A, (byte) 0x86});
+ }
} else if (command.getP1() == 0x00) {
@@ -330,21 +385,22 @@ public class STARCOSCardChannelEmul extends CardChannelEmul {
}
response = verifyPin(0xFF & command.getP2(), Arrays.copyOf(data, 8));
-
+
+ if (response.getSW() == 0x9000) {
+ PIN pin;
+ if (currentAppl != null) {
+ pin = currentAppl.pins.get(command.getP2());
+ } else {
+ pin = globalPins.get(command.getP2());
+ }
+ pin.pin = Arrays.copyOfRange(data, 8, 16);
+ pin.state = PIN.STATE_PIN_VERIFIED;
+ }
+
} else {
return new ResponseAPDU(new byte[] { (byte) 0x6A, (byte) 0x81 });
}
- if (response.getSW() == 0x9000) {
- PIN pin;
- if (currentAppl != null) {
- pin = currentAppl.pins.get(command.getP2());
- } else {
- pin = globalPins.get(command.getP2());
- }
- pin.pin = Arrays.copyOfRange(data, 8, 16);
- }
-
return response;
}
@@ -353,7 +409,10 @@ public class STARCOSCardChannelEmul extends CardChannelEmul {
PIN pin = globalPins.get(kid);
if (pin != null) {
if (value == null) {
- pin.pin = null;
+// pin.pin = null;
+ //TransportPIN
+// pin.pin = new byte[] { (byte) 0x24, (byte) 0x12, (byte) 0x34, (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff};
+ pin.state = PIN.STATE_PIN_NOTACTIVE;
} else {
byte[] b = new byte[8];
b[0] = (byte) (0x20 | value.length);
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSCardEmul.java b/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSCardEmul.java
index 7b2f3fbe..5963fb63 100644
--- a/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSCardEmul.java
+++ b/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSCardEmul.java
@@ -21,30 +21,34 @@ import javax.smartcardio.ATR;
import at.gv.egiz.smcc.CardChannelEmul;
import at.gv.egiz.smcc.CardEmul;
+import at.gv.egiz.smcc.PIN;
@SuppressWarnings("restriction")
public class STARCOSCardEmul extends CardEmul {
-
+
+ public static byte[] DEFAULT_SS_PIN = new byte[] { (byte) 0x26, (byte) 0x12, (byte) 0x34, (byte) 0x56, (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff};
+ public static byte[] DEFAULT_Glob_PIN = new byte[] { (byte) 0x24, (byte) 0x00, (byte) 0x00, (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff};
+
protected static ATR ATR = new ATR(new byte[] {
(byte) 0x3b, (byte) 0xbd, (byte) 0x18, (byte) 0x00, (byte) 0x81, (byte) 0x31, (byte) 0xfe, (byte) 0x45,
(byte) 0x80, (byte) 0x51, (byte) 0x02, (byte) 0x67, (byte) 0x05, (byte) 0x18, (byte) 0xb1, (byte) 0x02,
(byte) 0x02, (byte) 0x02, (byte) 0x01, (byte) 0x81, (byte) 0x05, (byte) 0x31
});
-
+
public STARCOSCardEmul() {
- applications.add(new STARCOSApplSichereSignatur((STARCOSCardChannelEmul) channel));
+ this(DEFAULT_SS_PIN, DEFAULT_Glob_PIN, PIN.STATE_RESET);
+ }
+
+ public STARCOSCardEmul(byte[] SS_PIN, byte[] Glob_PIN, int PIN_STATE) {
+ channel = new STARCOSCardChannelEmul(this, Glob_PIN, PIN_STATE);
+ applications.add(new STARCOSApplSichereSignatur((STARCOSCardChannelEmul) channel, SS_PIN, PIN_STATE));
applications.add(new STARCOSApplInfobox((STARCOSCardChannelEmul) channel));
- applications.add(new STARCOSApplGewoehnlicheSignatur((STARCOSCardChannelEmul) channel));
+ applications.add(new STARCOSApplGewoehnlicheSignatur((STARCOSCardChannelEmul) channel,
+ STARCOSApplGewoehnlicheSignatur.DST));
}
@Override
public ATR getATR() {
return ATR;
}
-
- @Override
- protected CardChannelEmul newCardChannel(CardEmul cardEmul) {
- return new STARCOSCardChannelEmul(this);
- }
-
}
\ No newline at end of file
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSCardTest.java b/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSCardTest.java
index b7dc9a0c..154884d4 100644
--- a/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSCardTest.java
+++ b/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSCardTest.java
@@ -22,12 +22,9 @@ import static org.junit.Assert.assertTrue;
import java.io.ByteArrayInputStream;
import java.io.IOException;
-import java.io.UnsupportedEncodingException;
-import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.util.Arrays;
-import javax.smartcardio.CardChannel;
import org.junit.Test;
@@ -36,25 +33,20 @@ import at.gv.egiz.smcc.CardEmul;
import at.gv.egiz.smcc.CardNotSupportedException;
import at.gv.egiz.smcc.CardTerminalEmul;
import at.gv.egiz.smcc.CardTest;
+import at.gv.egiz.smcc.pin.gui.ChangePINProvider;
+import at.gv.egiz.smcc.pin.gui.InvalidChangePINProvider;
+import at.gv.egiz.smcc.pin.gui.InvalidPINProvider;
import at.gv.egiz.smcc.LockedException;
import at.gv.egiz.smcc.NotActivatedException;
+import at.gv.egiz.smcc.PIN;
import at.gv.egiz.smcc.PINFormatException;
import at.gv.egiz.smcc.PINMgmtSignatureCard;
import at.gv.egiz.smcc.PINSpec;
-import at.gv.egiz.smcc.STARCOSCard;
import at.gv.egiz.smcc.SignatureCard;
import at.gv.egiz.smcc.SignatureCardException;
import at.gv.egiz.smcc.SignatureCardFactory;
-import at.gv.egiz.smcc.CardTest.TestChangePINProvider;
-import at.gv.egiz.smcc.CardTest.TestPINProvider;
-import at.gv.egiz.smcc.PINProvider;
+import at.gv.egiz.smcc.pin.gui.SMCCTestPINProvider;
import at.gv.egiz.smcc.SignatureCard.KeyboxName;
-import at.gv.egiz.smcc.acos.A03ApplDEC;
-import at.gv.egiz.smcc.acos.A04ApplDEC;
-import at.gv.egiz.smcc.acos.A04ApplSIG;
-import at.gv.egiz.smcc.acos.ACOSAppl;
-import at.gv.egiz.smcc.acos.ACOSApplDEC;
-import at.gv.egiz.smcc.acos.ACOSApplSIG;
import org.junit.Ignore;
public class STARCOSCardTest extends CardTest {
@@ -69,7 +61,17 @@ public class STARCOSCardTest extends CardTest {
assertTrue(signatureCard instanceof PINMgmtSignatureCard);
return signatureCard;
}
-
+
+ protected SignatureCard createSignatureCard(byte[] SS_PIN, byte[] Glob_PIN, int pinState)
+ throws CardNotSupportedException {
+ SignatureCardFactory factory = SignatureCardFactory.getInstance();
+ STARCOSCardEmul card = new STARCOSCardEmul(SS_PIN, Glob_PIN, pinState);
+ SignatureCard signatureCard = factory.createSignatureCard(card,
+ new CardTerminalEmul(card));
+ assertTrue(signatureCard instanceof PINMgmtSignatureCard);
+ return signatureCard;
+ }
+
@Test
public void testGetInfoboxIdentityLinkEmpty() throws SignatureCardException,
InterruptedException, CardNotSupportedException {
@@ -82,7 +84,7 @@ public class STARCOSCardTest extends CardTest {
appl.clearInfobox();
byte[] idlink = signatureCard.getInfobox("IdentityLink",
- new TestPINProvider(pin), null);
+ new SMCCTestPINProvider(pin), null);
assertNull(idlink);
}
@@ -98,10 +100,10 @@ public class STARCOSCardTest extends CardTest {
STARCOSApplInfobox appl = (STARCOSApplInfobox) card.getApplication(STARCOSAppl.AID_Infobox);
appl.setInfoboxHeader((byte) 0xFF);
- signatureCard.getInfobox("IdentityLink", new TestPINProvider(pin), null);
+ signatureCard.getInfobox("IdentityLink", new SMCCTestPINProvider(pin), null);
}
-
+
@Test
public void testGetCerts() throws SignatureCardException,
InterruptedException, CardNotSupportedException {
@@ -145,7 +147,7 @@ public class STARCOSCardTest extends CardTest {
signatureCard.getCertificate(KeyboxName.CERITIFIED_KEYPAIR);
}
-
+
@Test
public void testSignSichereSignatur() throws SignatureCardException,
InterruptedException, CardNotSupportedException,
@@ -160,7 +162,7 @@ public class STARCOSCardTest extends CardTest {
byte[] signature = signatureCard.createSignature(new ByteArrayInputStream("MOCCA"
.getBytes("ASCII")),
- KeyboxName.SECURE_SIGNATURE_KEYPAIR, new TestPINProvider(pin), null);
+ KeyboxName.SECURE_SIGNATURE_KEYPAIR, new SMCCTestPINProvider(pin), null);
assertNotNull(signature);
@@ -180,12 +182,12 @@ public class STARCOSCardTest extends CardTest {
byte[] signature = signatureCard.createSignature(new ByteArrayInputStream("MOCCA"
.getBytes("ASCII")),
- KeyboxName.CERITIFIED_KEYPAIR, new TestPINProvider(pin), null);
+ KeyboxName.CERITIFIED_KEYPAIR, new SMCCTestPINProvider(pin), null);
assertNotNull(signature);
}
-
+
@Test(expected = LockedException.class)
public void testSignSichereSignaturInvalidPin() throws SignatureCardException,
InterruptedException, CardNotSupportedException,
@@ -193,7 +195,7 @@ public class STARCOSCardTest extends CardTest {
SignatureCard signatureCard = createSignatureCard();
- TestPINProvider pinProvider = new TestPINProvider("000000".toCharArray());
+ SMCCTestPINProvider pinProvider = new SMCCTestPINProvider("000000".toCharArray());
signatureCard.createSignature(new ByteArrayInputStream("MOCCA"
.getBytes("ASCII")), KeyboxName.SECURE_SIGNATURE_KEYPAIR,
@@ -208,7 +210,7 @@ public class STARCOSCardTest extends CardTest {
SignatureCard signatureCard = createSignatureCard();
- TestPINProvider pinProvider = new TestPINProvider("1234".toCharArray());
+ SMCCTestPINProvider pinProvider = new SMCCTestPINProvider("1234".toCharArray());
signatureCard.createSignature(new ByteArrayInputStream("MOCCA"
.getBytes("ASCII")), KeyboxName.CERITIFIED_KEYPAIR,
@@ -221,12 +223,9 @@ public class STARCOSCardTest extends CardTest {
InterruptedException, CardNotSupportedException,
NoSuchAlgorithmException, IOException {
- SignatureCard signatureCard = createSignatureCard();
- CardEmul card = (CardEmul) signatureCard.getCard();
- STARCOSApplSichereSignatur appl = (STARCOSApplSichereSignatur) card.getApplication(STARCOSApplSichereSignatur.AID_SichereSignatur);
- appl.setPin(STARCOSApplSichereSignatur.KID_PIN_SS, null);
+ SignatureCard signatureCard = createSignatureCard(null, null, PIN.STATE_PIN_BLOCKED);
- TestPINProvider pinProvider = new TestPINProvider("000000".toCharArray());
+ SMCCTestPINProvider pinProvider = new SMCCTestPINProvider("000000".toCharArray());
assertTrue(pinProvider.getProvided() <= 0);
signatureCard.createSignature(new ByteArrayInputStream("MOCCA"
@@ -240,68 +239,79 @@ public class STARCOSCardTest extends CardTest {
InterruptedException, CardNotSupportedException,
NoSuchAlgorithmException, IOException {
- SignatureCard signatureCard = createSignatureCard();
- CardEmul card = (CardEmul) signatureCard.getCard();
- STARCOSCardChannelEmul channel = (STARCOSCardChannelEmul) card.getBasicChannel();
- channel.setPin(STARCOSCardChannelEmul.KID_PIN_Glob, null);
-
- TestPINProvider pinProvider = new TestPINProvider("0000".toCharArray());
+ SignatureCard signatureCard = createSignatureCard(null, null, PIN.STATE_PIN_BLOCKED);
+
+ SMCCTestPINProvider pinProvider = new SMCCTestPINProvider("0000".toCharArray());
signatureCard.createSignature(new ByteArrayInputStream("MOCCA"
.getBytes("ASCII")), KeyboxName.CERITIFIED_KEYPAIR,
pinProvider, null);
}
-
+
@Test
public void testChangePin() throws CardNotSupportedException,
LockedException, NotActivatedException, CancelledException,
PINFormatException, SignatureCardException, InterruptedException {
- char[] defaultPin = "123456".toCharArray();
-
- PINMgmtSignatureCard signatureCard = (PINMgmtSignatureCard) createSignatureCard();
- CardEmul card = (CardEmul) signatureCard.getCard();
- STARCOSCardChannelEmul channel = (STARCOSCardChannelEmul) card.getBasicChannel();
- channel.setPin(STARCOSCardChannelEmul.KID_PIN_Glob, defaultPin);
- STARCOSApplSichereSignatur appl = (STARCOSApplSichereSignatur) card.getApplication(STARCOSApplSichereSignatur.AID_SichereSignatur);
- appl.setPin(STARCOSApplSichereSignatur.KID_PIN_SS, defaultPin);
+ // set all initial pins to DEFAULT_SS_PIN (123456)
+ PINMgmtSignatureCard signatureCard = (PINMgmtSignatureCard) createSignatureCard(
+ STARCOSCardEmul.DEFAULT_SS_PIN, STARCOSCardEmul.DEFAULT_SS_PIN, PIN.STATE_RESET);
for (PINSpec pinSpec : signatureCard.getPINSpecs()) {
- char[] pin = defaultPin;
+ char[] pin = "123456".toCharArray();
for (int i = pinSpec.getMinLength(); i <= pinSpec.getMaxLength(); i++) {
- signatureCard.verifyPIN(pinSpec, new TestPINProvider(pin));
+ signatureCard.verifyPIN(pinSpec, new SMCCTestPINProvider(pin));
char[] newPin = new char[i];
Arrays.fill(newPin, '0');
signatureCard
- .changePIN(pinSpec, new TestChangePINProvider(pin, newPin));
- signatureCard.verifyPIN(pinSpec, new TestPINProvider(newPin));
+ .changePIN(pinSpec, new ChangePINProvider(pin, newPin));
+ signatureCard.verifyPIN(pinSpec, new SMCCTestPINProvider(newPin));
pin = newPin;
}
}
}
@Test
- public void testVerifyInvalidPin() throws CardNotSupportedException,
+ @Override
+ public void testActivatePin() throws CardNotSupportedException,
LockedException, NotActivatedException, CancelledException,
PINFormatException, SignatureCardException, InterruptedException {
- char[] defaultPin = "123456".toCharArray();
+ PINMgmtSignatureCard signatureCard = (PINMgmtSignatureCard) createSignatureCard(
+ null, null, PIN.STATE_PIN_NOTACTIVE);
+
+ for (PINSpec pinSpec : signatureCard.getPINSpecs()) {
+
+ char[] pin = "1234567890".substring(0, pinSpec.getMinLength()).toCharArray();
+
+ boolean notActive = false;
+ try {
+ signatureCard.verifyPIN(pinSpec, new SMCCTestPINProvider(pin));
+ } catch (NotActivatedException ex) {
+ notActive = true;
+ }
+ assertTrue(notActive);
+
+ signatureCard.activatePIN(pinSpec, new ChangePINProvider(null, pin));
+ signatureCard.verifyPIN(pinSpec, new SMCCTestPINProvider(pin));
+ }
+ }
+
+ @Test
+ public void testVerifyInvalidPin() throws CardNotSupportedException,
+ LockedException, NotActivatedException, CancelledException,
+ PINFormatException, SignatureCardException, InterruptedException {
PINMgmtSignatureCard signatureCard = (PINMgmtSignatureCard) createSignatureCard();
- CardEmul card = (CardEmul) signatureCard.getCard();
- STARCOSCardChannelEmul channel = (STARCOSCardChannelEmul) card.getBasicChannel();
- channel.setPin(STARCOSCardChannelEmul.KID_PIN_Glob, defaultPin);
- STARCOSApplSichereSignatur appl = (STARCOSApplSichereSignatur) card.getApplication(STARCOSApplSichereSignatur.AID_SichereSignatur);
- appl.setPin(STARCOSApplSichereSignatur.KID_PIN_SS, defaultPin);
for (PINSpec pinSpec : signatureCard.getPINSpecs()) {
char[] invalidPin = "999999".toCharArray();
int numInvalidTries = 2;
- TestInvalidPINProvider invalidPinProvider = new TestInvalidPINProvider(invalidPin, numInvalidTries);
+ InvalidPINProvider invalidPinProvider = new InvalidPINProvider(invalidPin, numInvalidTries);
try {
signatureCard.verifyPIN(pinSpec, invalidPinProvider);
} catch (CancelledException ex) {
@@ -315,21 +325,15 @@ public class STARCOSCardTest extends CardTest {
public void testChangeInvalidPin() throws CardNotSupportedException,
LockedException, NotActivatedException, CancelledException,
PINFormatException, SignatureCardException, InterruptedException {
- char[] defaultPin = "123456".toCharArray();
PINMgmtSignatureCard signatureCard = (PINMgmtSignatureCard) createSignatureCard();
- CardEmul card = (CardEmul) signatureCard.getCard();
- STARCOSCardChannelEmul channel = (STARCOSCardChannelEmul) card.getBasicChannel();
- channel.setPin(STARCOSCardChannelEmul.KID_PIN_Glob, defaultPin);
- STARCOSApplSichereSignatur appl = (STARCOSApplSichereSignatur) card.getApplication(STARCOSApplSichereSignatur.AID_SichereSignatur);
- appl.setPin(STARCOSApplSichereSignatur.KID_PIN_SS, defaultPin);
-
+
for (PINSpec pinSpec : signatureCard.getPINSpecs()) {
char[] invalidPin = "999999".toCharArray();
int numInvalidTries = 2;
- TestInvalidChangePINProvider invalidPinProvider =
- new TestInvalidChangePINProvider(invalidPin, defaultPin, numInvalidTries);
+ InvalidChangePINProvider invalidPinProvider =
+ new InvalidChangePINProvider(invalidPin, invalidPin, numInvalidTries);
try {
signatureCard.changePIN(pinSpec, invalidPinProvider);
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSG3CardChannelEmul.java b/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSG3CardChannelEmul.java
new file mode 100644
index 00000000..dc6836ae
--- /dev/null
+++ b/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSG3CardChannelEmul.java
@@ -0,0 +1,46 @@
+/*
+ * Copyright 2008 Federal Chancellery Austria and
+ * Graz University of Technology
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package at.gv.egiz.smcc.starcos;
+
+import at.gv.egiz.smcc.CardEmul;
+import at.gv.egiz.smcc.File;
+import at.gv.egiz.smcc.PIN;
+
+/**
+ *
+ * @author clemens
+ */
+public class STARCOSG3CardChannelEmul extends STARCOSCardChannelEmul {
+
+ public STARCOSG3CardChannelEmul(CardEmul cardEmul, byte[] Glob_PIN, int PIN_STATE) {
+ super(cardEmul, Glob_PIN, PIN_STATE);
+
+ // G3 version file
+ byte[] versionFileFID = new byte[]{(byte) 0x00, (byte) 0x32};
+ byte[] versionFile = new byte[]{
+ (byte) 0xa5, (byte) 0x0e, (byte) 0x53, (byte) 0x02, (byte) 0x01, (byte) 0x20, (byte) 0x54, (byte) 0x08,
+ (byte) 0x01, (byte) 0x01, (byte) 0x03, (byte) 0x01, (byte) 0x04, (byte) 0x01, (byte) 0x70, (byte) 0x01};
+ byte[] versionFileFCX = new byte[]{
+ (byte) 0x62, (byte) 0x1a, (byte) 0x80, (byte) 0x02, (byte) 0x00, (byte) 0x14, (byte) 0x82, (byte) 0x05,
+ (byte) 0x44, (byte) 0x41, (byte) 0x00, (byte) 0x14, (byte) 0x01, (byte) 0x83, (byte) 0x02, (byte) 0x00,
+ (byte) 0x32, (byte) 0x88, (byte) 0x01, (byte) 0xd8, (byte) 0x8a, (byte) 0x01, (byte) 0x05, (byte) 0xa1,
+ (byte) 0x03, (byte) 0x8b, (byte) 0x01, (byte) 0x03};
+
+ globalFiles.add(new File(versionFileFID, versionFile, versionFileFCX));
+
+ }
+ }
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSG3CardEmul.java b/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSG3CardEmul.java
new file mode 100644
index 00000000..7583b3ad
--- /dev/null
+++ b/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSG3CardEmul.java
@@ -0,0 +1,57 @@
+/*
+ * Copyright 2008 Federal Chancellery Austria and
+ * Graz University of Technology
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package at.gv.egiz.smcc.starcos;
+
+import at.gv.egiz.smcc.CardEmul;
+import javax.smartcardio.ATR;
+
+import at.gv.egiz.smcc.PIN;
+
+@SuppressWarnings("restriction")
+public class STARCOSG3CardEmul extends CardEmul {
+
+ public static byte[] TRANSPORT_SS_PIN = new byte[] { (byte) 0x26, (byte) 0x12, (byte) 0x34, (byte) 0x56, (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff};
+ public static byte[] TRANSPORT_Glob_PIN = new byte[] { (byte) 0x24, (byte) 0x12, (byte) 0x34, (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff};
+
+ public static byte[] DEFAULT_SS_PIN = TRANSPORT_SS_PIN;
+ public static byte[] DEFAULT_Glob_PIN = new byte[] { (byte) 0x24, (byte) 0x00, (byte) 0x00, (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff, (byte) 0xff};
+
+ protected static ATR ATR = new ATR(new byte[] {
+ (byte) 0x3b, (byte) 0xbd, (byte) 0x18, (byte) 0x00, (byte) 0x81, (byte) 0x31, (byte) 0xfe, (byte) 0x45,
+ (byte) 0x80, (byte) 0x51, (byte) 0x02, (byte) 0x67, (byte) 0x05, (byte) 0x18, (byte) 0xb1, (byte) 0x02,
+ (byte) 0x02, (byte) 0x02, (byte) 0x01, (byte) 0x81, (byte) 0x05, (byte) 0x31
+ });
+
+ public STARCOSG3CardEmul(byte[] SS_PIN, byte[] Glob_PIN, int PIN_STATE){
+ channel = new STARCOSG3CardChannelEmul(this, Glob_PIN, PIN_STATE);
+ applications.add(new STARCOSApplSichereSignatur((STARCOSCardChannelEmul) channel,
+ SS_PIN, PIN_STATE));
+ applications.add(new STARCOSApplInfobox((STARCOSCardChannelEmul) channel));
+ applications.add(new STARCOSApplGewoehnlicheSignatur((STARCOSCardChannelEmul) channel,
+ STARCOSApplGewoehnlicheSignatur.DST_G3));
+ }
+
+
+ public STARCOSG3CardEmul() {
+ this(DEFAULT_SS_PIN, DEFAULT_Glob_PIN, PIN.STATE_RESET);
+ }
+
+ @Override
+ public ATR getATR() {
+ return ATR;
+ }
+}
diff --git a/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSG3CardTest.java b/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSG3CardTest.java
new file mode 100644
index 00000000..06744c82
--- /dev/null
+++ b/smcc/src/test/java/at/gv/egiz/smcc/starcos/STARCOSG3CardTest.java
@@ -0,0 +1,119 @@
+/*
+* Copyright 2008 Federal Chancellery Austria and
+* Graz University of Technology
+*
+* Licensed under the Apache License, Version 2.0 (the "License");
+* you may not use this file except in compliance with the License.
+* You may obtain a copy of the License at
+*
+* http://www.apache.org/licenses/LICENSE-2.0
+*
+* Unless required by applicable law or agreed to in writing, software
+* distributed under the License is distributed on an "AS IS" BASIS,
+* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+* See the License for the specific language governing permissions and
+* limitations under the License.
+*/
+package at.gv.egiz.smcc.starcos;
+
+import static org.junit.Assert.assertTrue;
+
+import java.util.Arrays;
+
+
+import org.junit.Test;
+
+import at.gv.egiz.smcc.CancelledException;
+import at.gv.egiz.smcc.CardEmul;
+import at.gv.egiz.smcc.CardNotSupportedException;
+import at.gv.egiz.smcc.CardTerminalEmul;
+import at.gv.egiz.smcc.CardTest;
+import at.gv.egiz.smcc.pin.gui.ChangePINProvider;
+import at.gv.egiz.smcc.LockedException;
+import at.gv.egiz.smcc.NotActivatedException;
+import at.gv.egiz.smcc.PIN;
+import at.gv.egiz.smcc.PINFormatException;
+import at.gv.egiz.smcc.PINMgmtSignatureCard;
+import at.gv.egiz.smcc.PINSpec;
+import at.gv.egiz.smcc.SignatureCard;
+import at.gv.egiz.smcc.SignatureCardException;
+import at.gv.egiz.smcc.SignatureCardFactory;
+import at.gv.egiz.smcc.pin.gui.SMCCTestPINProvider;
+import org.junit.Ignore;
+
+public class STARCOSG3CardTest extends CardTest {
+
+ @Override
+ protected SignatureCard createSignatureCard()
+ throws CardNotSupportedException {
+ SignatureCardFactory factory = SignatureCardFactory.getInstance();
+ STARCOSG3CardEmul card = new STARCOSG3CardEmul();
+ SignatureCard signatureCard = factory.createSignatureCard(card,
+ new CardTerminalEmul(card));
+ assertTrue(signatureCard instanceof PINMgmtSignatureCard);
+ return signatureCard;
+ }
+
+ protected SignatureCard createSignatureCard(byte[] SS_PIN, byte[] Glob_PIN, int pinState)
+ throws CardNotSupportedException {
+ SignatureCardFactory factory = SignatureCardFactory.getInstance();
+ STARCOSG3CardEmul card = new STARCOSG3CardEmul(SS_PIN, Glob_PIN, pinState);
+ SignatureCard signatureCard = factory.createSignatureCard(card,
+ new CardTerminalEmul(card));
+ assertTrue(signatureCard instanceof PINMgmtSignatureCard);
+ return signatureCard;
+ }
+
+ @Test
+ public void testChangePin() throws CardNotSupportedException,
+ LockedException, NotActivatedException, CancelledException,
+ PINFormatException, SignatureCardException, InterruptedException {
+
+ PINMgmtSignatureCard signatureCard = (PINMgmtSignatureCard) createSignatureCard(
+ STARCOSG3CardEmul.DEFAULT_SS_PIN, STARCOSG3CardEmul.DEFAULT_SS_PIN, PIN.STATE_RESET);
+
+ for (PINSpec pinSpec : signatureCard.getPINSpecs()) {
+
+ char[] pin = "123456".toCharArray();
+
+ for (int i = pinSpec.getMinLength(); i <= pinSpec.getMaxLength(); i++) {
+ signatureCard.verifyPIN(pinSpec, new SMCCTestPINProvider(pin));
+ char[] newPin = new char[i];
+ Arrays.fill(newPin, '0');
+ signatureCard
+ .changePIN(pinSpec, new ChangePINProvider(pin, newPin));
+ signatureCard.verifyPIN(pinSpec, new SMCCTestPINProvider(newPin));
+ pin = newPin;
+ }
+ }
+ }
+
+ @Test
+ @Override
+ public void testActivatePin() throws CardNotSupportedException,
+ LockedException, NotActivatedException, CancelledException,
+ PINFormatException, SignatureCardException, InterruptedException {
+
+ PINMgmtSignatureCard signatureCard = (PINMgmtSignatureCard) createSignatureCard(
+ STARCOSG3CardEmul.TRANSPORT_SS_PIN, STARCOSG3CardEmul.TRANSPORT_SS_PIN, PIN.STATE_PIN_NOTACTIVE);
+
+ for (PINSpec pinSpec : signatureCard.getPINSpecs()) {
+
+ char[] pin = "123456789".substring(0, pinSpec.getMinLength()).toCharArray();
+ char[] transportPIN = "123456".toCharArray();
+
+ boolean notActive = false;
+ try {
+ signatureCard.verifyPIN(pinSpec, new SMCCTestPINProvider(pin));
+ } catch (NotActivatedException ex) {
+ notActive = true;
+ }
+ assertTrue(notActive);
+
+ signatureCard.activatePIN(pinSpec, new ChangePINProvider(transportPIN, pin));
+ signatureCard.verifyPIN(pinSpec, new SMCCTestPINProvider(pin));
+ }
+ }
+
+
+}
diff --git a/smccSTAL/src/main/java/META-INF/MANIFEST.MF b/smccSTAL/src/main/java/META-INF/MANIFEST.MF
deleted file mode 100644
index 5e949512..00000000
--- a/smccSTAL/src/main/java/META-INF/MANIFEST.MF
+++ /dev/null
@@ -1,3 +0,0 @@
-Manifest-Version: 1.0
-Class-Path:
-
diff --git a/smccSTAL/src/main/java/at/gv/egiz/bku/pin/gui/AbstractPINProvider.java b/smccSTAL/src/main/java/at/gv/egiz/bku/pin/gui/AbstractPINProvider.java
new file mode 100644
index 00000000..00738188
--- /dev/null
+++ b/smccSTAL/src/main/java/at/gv/egiz/bku/pin/gui/AbstractPINProvider.java
@@ -0,0 +1,60 @@
+/*
+ * Copyright 2008 Federal Chancellery Austria and
+ * Graz University of Technology
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package at.gv.egiz.bku.pin.gui;
+
+import at.gv.egiz.smcc.pin.gui.PINProvider;
+import java.awt.event.ActionEvent;
+import java.awt.event.ActionListener;
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+
+/**
+ * common super class providing action listener for all PIN GUIs
+ * @author Clemens Orthacker
+ */
+public abstract class AbstractPINProvider implements ActionListener {
+
+ protected static final Log log = LogFactory.getLog(AbstractPINProvider.class);
+
+ protected String action;
+ protected boolean actionPerformed;
+
+ protected synchronized void waitForAction() throws InterruptedException {
+ try {
+ while (!actionPerformed) {
+ this.wait();
+ }
+ } catch (InterruptedException e) {
+ log.error("[" + Thread.currentThread().getName() + "] interrupt in waitForAction");
+ throw e;
+ }
+ actionPerformed = false;
+ }
+
+ private synchronized void actionPerformed() {
+ actionPerformed = true;
+ notify();//All();
+ }
+
+ @Override
+ public void actionPerformed(ActionEvent e) {
+ log.debug("[" + Thread.currentThread().getName() + "] action performed - " + e.getActionCommand());
+ action = e.getActionCommand();
+ actionPerformed();
+ }
+}
diff --git a/smccSTAL/src/main/java/at/gv/egiz/bku/pin/gui/SignPINGUI.java b/smccSTAL/src/main/java/at/gv/egiz/bku/pin/gui/SignPINGUI.java
new file mode 100644
index 00000000..81db0e90
--- /dev/null
+++ b/smccSTAL/src/main/java/at/gv/egiz/bku/pin/gui/SignPINGUI.java
@@ -0,0 +1,136 @@
+/*
+ * Copyright 2008 Federal Chancellery Austria and
+ * Graz University of Technology
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package at.gv.egiz.bku.pin.gui;
+
+import at.gv.egiz.bku.gui.BKUGUIFacade;
+import at.gv.egiz.bku.smccstal.SecureViewer;
+import at.gv.egiz.smcc.CancelledException;
+import at.gv.egiz.smcc.PINSpec;
+import at.gv.egiz.smcc.pin.gui.PINGUI;
+import at.gv.egiz.stal.signedinfo.SignedInfoType;
+import java.security.DigestException;
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+
+/**
+ * The number of retries is not fixed and there is no way (?) to obtain this value.
+ * A PINProvider should therefore maintain an internal retry counter or flag
+ * to decide whether or not to warn the user (num retries passed in providePIN).
+ *
+ * Therefore PINProvider objects should not be reused.
+ *
+ * (ACOS: reload counter: between 0 and 15, where 15 meens deactivated)
+ *
+ * @author Clemens Orthacker
+ */
+public class SignPINGUI extends SignPINProvider implements PINGUI {
+
+ protected static final Log log = LogFactory.getLog(SignPINGUI.class);
+
+ private boolean retry = false;
+
+ public SignPINGUI(BKUGUIFacade gui, SecureViewer viewer, SignedInfoType signedInfo) {
+ super(gui, viewer, signedInfo);
+ }
+
+ @Override
+ public void enterPINDirect(PINSpec spec, int retries)
+ throws CancelledException, InterruptedException {
+ if (retry) {
+ gui.showEnterPINDirect(spec, retries);
+ } else {
+ showSignatureData(spec);
+ gui.showEnterPINDirect(spec, -1);
+ retry = true;
+ }
+ }
+
+ @Override
+ public void enterPIN(PINSpec spec, int retries)
+ throws CancelledException, InterruptedException {
+ if (retry) {
+ gui.showEnterPIN(spec, retries);
+ } else {
+ showSignatureData(spec);
+ gui.showEnterPIN(spec, -1);
+ retry = true;
+ }
+ }
+
+ private void showSignatureData(PINSpec spec)
+ throws CancelledException, InterruptedException {
+
+ gui.showSignatureDataDialog(spec,
+ this, "enterPIN",
+ this, "cancel",
+ this, "secureViewer");
+
+ do {
+ log.trace("[" + Thread.currentThread().getName() + "] wait for action");
+ waitForAction();
+ log.trace("[" + Thread.currentThread().getName() + "] received action " + action);
+
+ if ("secureViewer".equals(action)) {
+ try {
+ viewer.displayDataToBeSigned(signedInfo, this, "signatureData");
+ } catch (DigestException ex) {
+ log.error("Bad digest value: " + ex.getMessage());
+ gui.showErrorDialog(BKUGUIFacade.ERR_INVALID_HASH,
+ new Object[]{ex.getMessage()},
+ this, "error");
+ } catch (Exception ex) {
+ log.error("Could not display hashdata inputs: " +
+ ex.getMessage());
+ gui.showErrorDialog(BKUGUIFacade.ERR_DISPLAY_HASHDATA,
+ new Object[]{ex.getMessage()},
+ this, "error");
+ }
+ } else if ("signatureData".equals(action)) {
+ gui.showSignatureDataDialog(spec,
+ this, "enterPIN",
+ this, "cancel",
+ this, "secureViewer");
+ } else if ("enterPIN".equals(action)) {
+ return;
+ } else if ("cancel".equals(action) ||
+ "error".equals(action)) {
+ gui.showMessageDialog(BKUGUIFacade.TITLE_WAIT,
+ BKUGUIFacade.MESSAGE_WAIT);
+ throw new CancelledException(spec.getLocalizedName() +
+ " entry cancelled");
+ } else {
+ log.error("unknown action command " + action);
+ }
+ } while (true);
+ }
+
+ @Override
+ public void validKeyPressed() {
+ gui.validKeyPressed();
+ }
+
+ @Override
+ public void correctionButtonPressed() {
+ gui.correctionButtonPressed();
+ }
+
+ @Override
+ public void allKeysCleared() {
+ gui.allKeysCleared();
+ }
+
+}
diff --git a/smccSTAL/src/main/java/at/gv/egiz/bku/pin/gui/SignPINProvider.java b/smccSTAL/src/main/java/at/gv/egiz/bku/pin/gui/SignPINProvider.java
new file mode 100644
index 00000000..fc1d39af
--- /dev/null
+++ b/smccSTAL/src/main/java/at/gv/egiz/bku/pin/gui/SignPINProvider.java
@@ -0,0 +1,105 @@
+/*
+ * Copyright 2008 Federal Chancellery Austria and
+ * Graz University of Technology
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package at.gv.egiz.bku.pin.gui;
+
+import at.gv.egiz.bku.gui.BKUGUIFacade;
+import at.gv.egiz.bku.smccstal.SecureViewer;
+import at.gv.egiz.smcc.CancelledException;
+import at.gv.egiz.smcc.PINSpec;
+import at.gv.egiz.smcc.pin.gui.PINProvider;
+import at.gv.egiz.stal.signedinfo.SignedInfoType;
+import java.security.DigestException;
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+
+/**
+ * The number of retries is not fixed and there is no way (?) to obtain this value.
+ * A PINProvider should therefore maintain an internal retry counter or flag
+ * to decide whether or not to warn the user (num retries passed in providePIN).
+ *
+ * Therefore PINProvider objects should not be reused.
+ *
+ * (ACOS: reload counter: between 0 and 15, where 15 meens deactivated)
+ *
+ * @author Clemens Orthacker
+ */
+public class SignPINProvider extends AbstractPINProvider implements PINProvider {
+
+ protected static final Log log = LogFactory.getLog(SignPINProvider.class);
+
+ protected BKUGUIFacade gui;
+ protected SecureViewer viewer;
+ protected SignedInfoType signedInfo;
+ private boolean retry = false;
+
+ public SignPINProvider(BKUGUIFacade gui, SecureViewer viewer, SignedInfoType signedInfo) {
+ this.gui = gui;
+ this.viewer = viewer;
+ this.signedInfo = signedInfo;
+ }
+
+ @Override
+ public char[] providePIN(PINSpec spec, int retries)
+ throws CancelledException, InterruptedException {
+
+ gui.showSignaturePINDialog(spec, (retry) ? retries : -1,
+ this, "sign",
+ this, "cancel",
+ this, "secureViewer");
+
+ do {
+ log.trace("[" + Thread.currentThread().getName() + "] wait for action");
+ waitForAction();
+ log.trace("[" + Thread.currentThread().getName() + "] received action " + action);
+
+ if ("secureViewer".equals(action)) {
+ try {
+ viewer.displayDataToBeSigned(signedInfo, this, "pinEntry");
+ } catch (DigestException ex) {
+ log.error("Bad digest value: " + ex.getMessage());
+ gui.showErrorDialog(BKUGUIFacade.ERR_INVALID_HASH,
+ new Object[]{ex.getMessage()},
+ this, "error");
+ } catch (Exception ex) {
+ log.error("Could not display hashdata inputs: " +
+ ex.getMessage());
+ gui.showErrorDialog(BKUGUIFacade.ERR_DISPLAY_HASHDATA,
+ new Object[]{ex.getMessage()},
+ this, "error");
+ }
+ } else if ("sign".equals(action)) {
+ gui.showMessageDialog(BKUGUIFacade.TITLE_WAIT,
+ BKUGUIFacade.MESSAGE_WAIT);
+ retry = true;
+ return gui.getPin();
+ } else if ("pinEntry".equals(action)) {
+ gui.showSignaturePINDialog(spec, (retry) ? retries : -1,
+ this, "sign",
+ this, "cancel",
+ this, "secureViewer");
+ } else if ("cancel".equals(action) ||
+ "error".equals(action)) {
+ gui.showMessageDialog(BKUGUIFacade.TITLE_WAIT,
+ BKUGUIFacade.MESSAGE_WAIT);
+ throw new CancelledException(spec.getLocalizedName() +
+ " entry cancelled");
+ } else {
+ log.error("unknown action command " + action);
+ }
+ } while (true);
+ }
+}
diff --git a/smccSTAL/src/main/java/at/gv/egiz/bku/pin/gui/VerifyPINGUI.java b/smccSTAL/src/main/java/at/gv/egiz/bku/pin/gui/VerifyPINGUI.java
new file mode 100644
index 00000000..dc21492e
--- /dev/null
+++ b/smccSTAL/src/main/java/at/gv/egiz/bku/pin/gui/VerifyPINGUI.java
@@ -0,0 +1,76 @@
+/*
+ * Copyright 2008 Federal Chancellery Austria and
+ * Graz University of Technology
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package at.gv.egiz.bku.pin.gui;
+
+import at.gv.egiz.bku.gui.BKUGUIFacade;
+import at.gv.egiz.smcc.CancelledException;
+import at.gv.egiz.smcc.PINSpec;
+import at.gv.egiz.smcc.pin.gui.PINGUI;
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+
+/**
+ * The number of retries is not fixed and there is no way (?) to obtain this value.
+ * A PINProvider should therefore maintain an internal retry counter or flag
+ * to decide whether or not to warn the user (num retries passed in providePIN).
+ *
+ * Therefore PINProvider objects should not be reused.
+ *
+ * (ACOS: reload counter: between 0 and 15, where 15 meens deactivated)
+ *
+ * @author Clemens Orthacker
+ */
+public class VerifyPINGUI extends VerifyPINProvider implements PINGUI {
+
+ protected static final Log log = LogFactory.getLog(VerifyPINGUI.class);
+
+ private boolean retry = false;
+
+ public VerifyPINGUI(BKUGUIFacade gui) {
+ super(gui);
+ }
+
+ @Override
+ public void enterPINDirect(PINSpec spec, int retries)
+ throws CancelledException, InterruptedException {
+ gui.showEnterPINDirect(spec, (retry) ? retries : -1);
+ retry = true;
+ }
+
+ @Override
+ public void enterPIN(PINSpec spec, int retries) {
+ gui.showEnterPIN(spec, (retry) ? retries : -1);
+ retry = true;
+ }
+
+
+ @Override
+ public void validKeyPressed() {
+ gui.validKeyPressed();
+ }
+
+ @Override
+ public void correctionButtonPressed() {
+ gui.correctionButtonPressed();
+ }
+
+ @Override
+ public void allKeysCleared() {
+ gui.allKeysCleared();
+ }
+
+}
diff --git a/smccSTAL/src/main/java/at/gv/egiz/bku/pin/gui/VerifyPINProvider.java b/smccSTAL/src/main/java/at/gv/egiz/bku/pin/gui/VerifyPINProvider.java
new file mode 100644
index 00000000..fda1e402
--- /dev/null
+++ b/smccSTAL/src/main/java/at/gv/egiz/bku/pin/gui/VerifyPINProvider.java
@@ -0,0 +1,72 @@
+/*
+ * Copyright 2008 Federal Chancellery Austria and
+ * Graz University of Technology
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package at.gv.egiz.bku.pin.gui;
+
+import at.gv.egiz.bku.gui.BKUGUIFacade;
+import at.gv.egiz.smcc.CancelledException;
+import at.gv.egiz.smcc.PINSpec;
+import at.gv.egiz.smcc.pin.gui.PINProvider;
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+
+/**
+ * The number of retries is not fixed and there is no way (?) to obtain this value.
+ * A PINProvider should therefore maintain an internal retry counter or flag
+ * to decide whether or not to warn the user (num retries passed in providePIN).
+ *
+ * Therefore PINProvider objects should not be reused.
+ *
+ * (ACOS: reload counter: between 0 and 15, where 15 meens deactivated)
+ *
+ * @author Clemens Orthacker
+ */
+public class VerifyPINProvider extends AbstractPINProvider implements PINProvider {
+
+ protected static final Log log = LogFactory.getLog(VerifyPINProvider.class);
+
+ protected BKUGUIFacade gui;
+ private boolean retry = false;
+
+ public VerifyPINProvider(BKUGUIFacade gui) {
+ this.gui = gui;
+ }
+
+ @Override
+ public char[] providePIN(PINSpec spec, int retries)
+ throws CancelledException, InterruptedException {
+
+ gui.showVerifyPINDialog(spec, (retry) ? retries : -1,
+ this, "verify",
+ this, "cancel");
+
+ log.trace("[" + Thread.currentThread().getName() + "] wait for action");
+ waitForAction();
+ log.trace("[" + Thread.currentThread().getName() + "] received action " + action);
+
+ if ("cancel".equals(action)) {
+ gui.showMessageDialog(BKUGUIFacade.TITLE_WAIT,
+ BKUGUIFacade.MESSAGE_WAIT);
+ throw new CancelledException(spec.getLocalizedName() +
+ " entry cancelled");
+ }
+
+ gui.showMessageDialog(BKUGUIFacade.TITLE_WAIT,
+ BKUGUIFacade.MESSAGE_WAIT);
+ retry = true;
+ return gui.getPin();
+ }
+}
diff --git a/smccSTAL/src/main/java/at/gv/egiz/bku/smccstal/AbstractPINProvider.java b/smccSTAL/src/main/java/at/gv/egiz/bku/smccstal/AbstractPINProvider.java
deleted file mode 100644
index bc52c955..00000000
--- a/smccSTAL/src/main/java/at/gv/egiz/bku/smccstal/AbstractPINProvider.java
+++ /dev/null
@@ -1,67 +0,0 @@
-/*
- * Copyright 2008 Federal Chancellery Austria and
- * Graz University of Technology
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package at.gv.egiz.bku.smccstal;
-
-import at.gv.egiz.smcc.PINProvider;
-import java.awt.event.ActionEvent;
-import java.awt.event.ActionListener;
-import org.apache.commons.logging.Log;
-import org.apache.commons.logging.LogFactory;
-
-/**
- *
- * @author Clemens Orthacker
- */
-public abstract class AbstractPINProvider implements PINProvider, ActionListener {
-
- protected static final Log log = LogFactory.getLog(AbstractPINProvider.class);
-
- protected boolean retry = false;
-
- protected String action;
-
- protected boolean actionPerformed;
-
-// protected void waitForAction() throws InterruptedException {
-// super.wait();
-// }
-
- protected synchronized void waitForAction() throws InterruptedException {
- try {
- while (!actionPerformed) {
- this.wait();
- }
- } catch (InterruptedException e) {
- log.error("[" + Thread.currentThread().getName() + "] interrupt in waitForAction");
- throw e;
- }
- actionPerformed = false;
- }
-
- private synchronized void actionPerformed() {
- actionPerformed = true;
- notify();//All();
- }
-
- @Override
- public void actionPerformed(ActionEvent e) {
- log.debug("[" + Thread.currentThread().getName() + "] action performed - " + e.getActionCommand());
- action = e.getActionCommand();
- actionPerformed();
- }
-}
diff --git a/smccSTAL/src/main/java/at/gv/egiz/bku/smccstal/InfoBoxReadRequestHandler.java b/smccSTAL/src/main/java/at/gv/egiz/bku/smccstal/InfoBoxReadRequestHandler.java
index 32e990c5..b34ab862 100644
--- a/smccSTAL/src/main/java/at/gv/egiz/bku/smccstal/InfoBoxReadRequestHandler.java
+++ b/smccSTAL/src/main/java/at/gv/egiz/bku/smccstal/InfoBoxReadRequestHandler.java
@@ -17,14 +17,13 @@
package at.gv.egiz.bku.smccstal;
import at.gv.egiz.bku.gui.BKUGUIFacade;
+import at.gv.egiz.bku.pin.gui.VerifyPINGUI;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import at.gv.egiz.smcc.CancelledException;
import at.gv.egiz.smcc.LockedException;
import at.gv.egiz.smcc.NotActivatedException;
-import at.gv.egiz.smcc.PINProvider;
-import at.gv.egiz.smcc.PINSpec;
import at.gv.egiz.smcc.SignatureCard;
import at.gv.egiz.smcc.SignatureCardException;
import at.gv.egiz.stal.ErrorResponse;
@@ -49,8 +48,7 @@ public class InfoBoxReadRequestHandler extends AbstractRequestHandler {
newSTALMessage("Message.RequestCaption", "Message.IdentityLink");
log.debug("Handling identitylink infobox");
byte[] resp = card.getInfobox(infoBox.getInfoboxIdentifier(),
- new PINProviderFactory(card.getReader(), gui)
- .getCardPINProvider(),
+ new VerifyPINGUI(gui),
infoBox.getDomainIdentifier());
if (resp == null) {
log.info("Infobox doesn't contain any data. Assume card is not activated.");
@@ -97,8 +95,7 @@ public class InfoBoxReadRequestHandler extends AbstractRequestHandler {
log.warn("Unknown infobox identifier: "
+ infoBox.getInfoboxIdentifier() + " trying generic request");
byte[] resp = card.getInfobox(infoBox.getInfoboxIdentifier(),
- new PINProviderFactory(card.getReader(), gui)
- .getCardPINProvider(),
+ new VerifyPINGUI(gui),
infoBox.getDomainIdentifier());
if (resp == null) {
return new ErrorResponse(6001);
diff --git a/smccSTAL/src/main/java/at/gv/egiz/bku/smccstal/PINProviderFactory.java b/smccSTAL/src/main/java/at/gv/egiz/bku/smccstal/PINProviderFactory.java
deleted file mode 100644
index e5afe0ae..00000000
--- a/smccSTAL/src/main/java/at/gv/egiz/bku/smccstal/PINProviderFactory.java
+++ /dev/null
@@ -1,327 +0,0 @@
-/*
- * Copyright 2008 Federal Chancellery Austria and
- * Graz University of Technology
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package at.gv.egiz.bku.smccstal;
-
-import at.gv.egiz.bku.gui.BKUGUIFacade;
-import at.gv.egiz.smcc.CancelledException;
-import at.gv.egiz.smcc.ccid.CCID;
-import at.gv.egiz.smcc.PINProvider;
-import at.gv.egiz.smcc.PINSpec;
-import at.gv.egiz.stal.signedinfo.SignedInfoType;
-import java.security.DigestException;
-import org.apache.commons.logging.Log;
-import org.apache.commons.logging.LogFactory;
-
-/**
- * don't reuse the instance if the card reader might have changed!
- * @author Clemens Orthacker
- */
-public class PINProviderFactory {
-
- protected static final Log log = LogFactory.getLog(PINProviderFactory.class);
-
- protected CCID reader;
- protected BKUGUIFacade gui;
-
- /**
- * don't reuse the instance if the card reader might have changed!
- * @param reader
- * @param gui
- */
- public PINProviderFactory(CCID reader, BKUGUIFacade gui) {
- log.trace("PINProviderFactory for " + reader.getName());
- this.reader = reader;
- this.gui = gui;
- }
-
-
-
-// public static PINProviderFactory getInstance(SignatureCard forCard,
-// BKUGUIFacade gui) {
-// if (forCard.getReader().hasFeature(CCID.FEATURE_VERIFY_PIN_DIRECT) ||
-// forCard.getReader().hasFeature(CCID.FEATURE_VERIFY_PIN_DIRECT)) {
-// return new PinpadPINProviderFactory(gui);
-// } else {
-// return new SoftwarePINProviderFactory(gui);
-// }
-// }
-
- /**
- * don't reuse the instance if the card reader might have changed!
- * @param reader
- * @param gui
- * @return
- */
-// public static PINProviderFactory getInstance(CCID reader, BKUGUIFacade gui) {
-// log.trace("PINProviderFactory for " + reader.getName());
-// return new PINProviderFactory(reader, gui);
-// }
-
- public PINProvider getSignaturePINProvider(SecureViewer viewer,
- SignedInfoType signedInfo) {
- if (reader.hasFeature(CCID.FEATURE_VERIFY_PIN_START) ||
- reader.hasFeature(CCID.FEATURE_VERIFY_PIN_DIRECT)) {
- log.debug("pinpad signature-pin provider");
- return new PinpadSignaturePinProvider(viewer, signedInfo);
- } else {
- log.debug("software signature-pin provider");
- return new SoftwareSignaturePinProvider(viewer, signedInfo);
- }
- }
-
- public PINProvider getCardPINProvider() {
- if (reader.hasFeature(CCID.FEATURE_VERIFY_PIN_START) ||
- reader.hasFeature(CCID.FEATURE_VERIFY_PIN_DIRECT)) {
- log.debug("pinpad card-pin provider");
- return new PinpadCardPinProvider();
- } else {
- log.debug("software card-pin provider");
- return new SoftwareCardPinProvider();
- }
- }
-
- class SoftwareSignaturePinProvider extends AbstractPINProvider {
-
- protected SecureViewer viewer;
- protected SignedInfoType signedInfo;
-
- private SoftwareSignaturePinProvider(SecureViewer viewer,
- SignedInfoType signedInfo) {
- this.viewer = viewer;
- this.signedInfo = signedInfo;
- }
-
- @Override
- public char[] providePIN(PINSpec spec, int retries)
- throws CancelledException, InterruptedException {
-
- gui.showSignaturePINDialog(spec, (retry) ? retries : -1,
- this, "sign",
- this, "cancel",
- this, "secureViewer");
-
- do {
- log.debug("[" + Thread.currentThread().getName() + "] wait for action");
- waitForAction();
- log.debug("[" + Thread.currentThread().getName() + "] received action");
-
- if ("secureViewer".equals(action)) {
- try {
- viewer.displayDataToBeSigned(signedInfo, this, "pinEntry");
- } catch (DigestException ex) {
- log.error("Bad digest value: " + ex.getMessage());
- gui.showErrorDialog(BKUGUIFacade.ERR_INVALID_HASH,
- new Object[]{ex.getMessage()},
- this, "error");
- } catch (Exception ex) {
- log.error("Could not display hashdata inputs: " +
- ex.getMessage());
- gui.showErrorDialog(BKUGUIFacade.ERR_DISPLAY_HASHDATA,
- new Object[]{ex.getMessage()},
- this, "error");
- }
- } else if ("sign".equals(action)) {
- gui.showMessageDialog(BKUGUIFacade.TITLE_WAIT,
- BKUGUIFacade.MESSAGE_WAIT);
- retry = true;
- return gui.getPin();
- } else if ("pinEntry".equals(action)) {
- gui.showSignaturePINDialog(spec, (retry) ? retries : -1,
- this, "sign",
- this, "cancel",
- this, "secureViewer");
- } else if ("cancel".equals(action) ||
- "error".equals(action)) {
- gui.showMessageDialog(BKUGUIFacade.TITLE_WAIT,
- BKUGUIFacade.MESSAGE_WAIT);
- throw new CancelledException(spec.getLocalizedName() +
- " entry cancelled");
- } else {
- log.error("unknown action command " + action);
- }
- } while (true);
- }
- }
-
- class SoftwareCardPinProvider extends AbstractPINProvider {
-
- private SoftwareCardPinProvider() {
- }
-
- @Override
- public char[] providePIN(PINSpec spec, int retries)
- throws CancelledException, InterruptedException {
-
- gui.showCardPINDialog(spec, (retry) ? retries : -1,
- this, "ok",
- this, "cancel");
-
- log.debug("[" + Thread.currentThread().getName() + "] wait for action");
- waitForAction();
-
- gui.showMessageDialog(BKUGUIFacade.TITLE_WAIT,
- BKUGUIFacade.MESSAGE_WAIT);
-
- if ("cancel".equals(action)) {
- throw new CancelledException(spec.getLocalizedName() +
- " entry cancelled");
- }
- retry = true;
- return gui.getPin();
- }
- }
-
- class PinpadSignaturePinProvider extends AbstractPINProvider {
-
-// protected BKUGUIFacade gui;
- protected SecureViewer viewer;
- protected ViewerThread viewerThread;
- protected SignedInfoType signedInfo;
-
-
- private PinpadSignaturePinProvider(SecureViewer viewer,
- SignedInfoType signedInfo) {
- this.viewer = viewer;
- this.signedInfo = signedInfo;
- }
-
- protected class ViewerThread extends Thread {
-
- PINSpec pinSpec;
- int retries;
-
- public ViewerThread(PINSpec pinSpec, int retries) {
- this.pinSpec = pinSpec;
- this.retries = retries;
- }
-
- @Override
- public void run() {
-
- try {
-
- gui.showPinpadSignaturePINDialog(pinSpec, retries,
- PinpadSignaturePinProvider.this, "secureViewer");
-
- while (true) {
- log.debug("[" + Thread.currentThread().getName() + "] wait for action");
- waitForAction();
- log.debug("[" + Thread.currentThread().getName() + "] received action");
-
- if ("secureViewer".equals(action)) {
- viewer.displayDataToBeSigned(signedInfo,
- PinpadSignaturePinProvider.this, "pinEntry");
- } else if ("pinEntry".equals(action)) {
- gui.showPinpadSignaturePINDialog(pinSpec, retries,
- PinpadSignaturePinProvider.this, "secureViewer");
- } else {
- log.error("unsupported action command: " + action);
- }
- }
-
- } catch (DigestException ex) {
- log.error("Bad digest value: " + ex.getMessage());
- gui.showErrorDialog(BKUGUIFacade.ERR_INVALID_HASH,
- new Object[]{ex.getMessage()});
- } catch (InterruptedException ex) {
- log.info("pinpad secure viewer thread interrupted");
- } catch (Exception ex) {
- log.error("Could not display hashdata inputs: " +
- ex.getMessage());
- gui.showErrorDialog(BKUGUIFacade.ERR_DISPLAY_HASHDATA,
- new Object[]{ex.getMessage()});
- }
- }
- }
-
- @Override
- public char[] providePIN(PINSpec spec, int retries)
- throws CancelledException, InterruptedException {
-
- if (viewerThread != null) {
- updateViewerThread(retries);
- } else {
- viewerThread = new ViewerThread(spec, -1);
- viewerThread.start();
- }
-// if (viewerThread != null) {
-// log.trace("interrupt old secure viewer thread");
-// viewerThread.interrupt();
-// }
-// viewerThread = new ViewerThread(spec, (retry) ? retries : -1);
-// log.trace("start new secure viewer thread");
-// viewerThread.start();
-
- retry = true;
- return null;
- }
-
- private synchronized void updateViewerThread(int retries) {
- log.trace("update viewer thread");
- viewerThread.retries = retries;
- action = "pinEntry";
- actionPerformed = true;
- notify();
- }
-
-
-// @Override
-// protected void finalize() throws Throwable {
-// if (viewerThread != null) {
-// viewerThread.interrupt();
-// }
-// log.info("finalizing Pinpad SignaturePinProvider");
-// super.finalize();
-// }
- }
-
- class PinpadCardPinProvider extends AbstractPINProvider {
-
- private PinpadCardPinProvider() {
- }
-
- @Override
- public char[] providePIN(PINSpec spec, int retries)
- throws CancelledException, InterruptedException {
-
- showPinpadPINDialog(retries, spec);
- retry = true;
- return null;
-
- }
-
- private void showPinpadPINDialog(int retries, PINSpec pinSpec) {
- String title, message;
- Object[] params;
- if (retry) {
- title = BKUGUIFacade.TITLE_RETRY;
- message = BKUGUIFacade.MESSAGE_RETRIES;
- params = new Object[]{String.valueOf(retries)};
- } else {
- title = BKUGUIFacade.TITLE_CARDPIN;
- message = BKUGUIFacade.MESSAGE_ENTERPIN_PINPAD;
- String pinSize = String.valueOf(pinSpec.getMinLength());
- if (pinSpec.getMinLength() != pinSpec.getMaxLength()) {
- pinSize += "-" + pinSpec.getMaxLength();
- }
- params = new Object[]{pinSpec.getLocalizedName(), pinSize};
- }
- gui.showMessageDialog(title, message, params);
- }
- }
-}
diff --git a/smccSTAL/src/main/java/at/gv/egiz/bku/smccstal/SignRequestHandler.java b/smccSTAL/src/main/java/at/gv/egiz/bku/smccstal/SignRequestHandler.java
index 58d7b305..5b436d16 100644
--- a/smccSTAL/src/main/java/at/gv/egiz/bku/smccstal/SignRequestHandler.java
+++ b/smccSTAL/src/main/java/at/gv/egiz/bku/smccstal/SignRequestHandler.java
@@ -17,6 +17,7 @@
package at.gv.egiz.bku.smccstal;
import at.gv.egiz.bku.gui.BKUGUIFacade;
+import at.gv.egiz.bku.pin.gui.SignPINGUI;
import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;
@@ -78,8 +79,7 @@ public class SignRequestHandler extends AbstractRequestHandler {
KeyboxName kb = SignatureCard.KeyboxName.getKeyboxName(signReq.getKeyIdentifier());
byte[] resp = card.createSignature(new ByteArrayInputStream(signReq.getSignedInfo()), kb,
- new PINProviderFactory(card.getReader(), gui)
- .getSignaturePINProvider(secureViewer, si.getValue()), signatureMethod);
+ new SignPINGUI(gui, secureViewer, si.getValue()), signatureMethod);
if (resp == null) {
return new ErrorResponse(6001);
}
diff --git a/smccSTAL/src/test/java/at/gv/egiz/smcc/AbstractSMCCSTALTest.java b/smccSTAL/src/test/java/at/gv/egiz/smcc/AbstractSMCCSTALTest.java
index 16d3efa9..bf57b0a6 100644
--- a/smccSTAL/src/test/java/at/gv/egiz/smcc/AbstractSMCCSTALTest.java
+++ b/smccSTAL/src/test/java/at/gv/egiz/smcc/AbstractSMCCSTALTest.java
@@ -16,7 +16,7 @@ import org.junit.Test;
import at.gv.egiz.bku.gui.BKUGUIFacade;
import at.gv.egiz.bku.smccstal.AbstractSMCCSTAL;
import at.gv.egiz.bku.smccstal.SMCCSTALRequestHandler;
-import at.gv.egiz.smcc.ccid.CCID;
+import at.gv.egiz.smcc.pin.gui.PINGUI;
import at.gv.egiz.stal.ErrorResponse;
import at.gv.egiz.stal.InfoboxReadRequest;
import at.gv.egiz.stal.InfoboxReadResponse;
@@ -39,7 +39,7 @@ public class AbstractSMCCSTALTest extends AbstractSMCCSTAL implements
@Override
public byte[] createSignature(InputStream input, KeyboxName keyboxName,
- PINProvider provider, String alg) throws SignatureCardException {
+ PINGUI provider, String alg) throws SignatureCardException {
// TODO Auto-generated method stub
return null;
}
@@ -58,7 +58,7 @@ public class AbstractSMCCSTALTest extends AbstractSMCCSTAL implements
}
@Override
- public byte[] getInfobox(String infobox, PINProvider provider,
+ public byte[] getInfobox(String infobox, PINGUI provider,
String domainId) throws SignatureCardException {
// TODO Auto-generated method stub
return null;
@@ -87,13 +87,6 @@ public class AbstractSMCCSTALTest extends AbstractSMCCSTAL implements
// TODO Auto-generated method stub
}
-
- @Override
- public CCID getReader() {
- // TODO Auto-generated method stub
- return null;
- }
-
};
return false;
}
diff --git a/smccSTALExt/src/main/java/at/gv/egiz/bku/pin/gui/ManagementPINGUI.java b/smccSTALExt/src/main/java/at/gv/egiz/bku/pin/gui/ManagementPINGUI.java
new file mode 100644
index 00000000..26a24609
--- /dev/null
+++ b/smccSTALExt/src/main/java/at/gv/egiz/bku/pin/gui/ManagementPINGUI.java
@@ -0,0 +1,88 @@
+/*
+ * Copyright 2008 Federal Chancellery Austria and
+ * Graz University of Technology
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package at.gv.egiz.bku.pin.gui;
+
+import at.gv.egiz.bku.gui.BKUGUIFacade;
+import at.gv.egiz.bku.gui.PINManagementGUIFacade;
+import at.gv.egiz.bku.gui.PINManagementGUIFacade.DIALOG;
+import at.gv.egiz.smcc.CancelledException;
+import at.gv.egiz.smcc.PINSpec;
+import at.gv.egiz.smcc.pin.gui.ModifyPINGUI;
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+
+public class ManagementPINGUI extends ManagementPINProvider implements ModifyPINGUI {
+
+ protected static final Log log = LogFactory.getLog(ManagementPINGUI.class);
+
+ private boolean retry = false;
+
+ public ManagementPINGUI(PINManagementGUIFacade gui, DIALOG type) {
+ super(gui, type);
+ }
+
+ @Override
+ public void modifyPINDirect(PINSpec spec, int retries)
+ throws CancelledException, InterruptedException {
+ gui.showModifyPINDirect(type, spec, (retry) ? retries : -1);
+ retry = true;
+ }
+
+ @Override
+ public void finishDirect() {
+ gui.showMessageDialog(BKUGUIFacade.TITLE_WAIT, BKUGUIFacade.MESSAGE_WAIT);
+ }
+
+ @Override
+ public void enterCurrentPIN(PINSpec spec, int retries) {
+ gui.showEnterCurrentPIN(type, spec, (retry) ? retries : -1);
+ retry = true;
+ }
+
+ @Override
+ public void enterNewPIN(PINSpec spec) {
+ gui.showEnterNewPIN(type, spec);
+ retry = true;
+ }
+
+ @Override
+ public void confirmNewPIN(PINSpec spec) {
+ gui.showConfirmNewPIN(type, spec);
+ retry = true;
+ }
+
+
+ @Override
+ public void validKeyPressed() {
+ gui.validKeyPressed();
+ }
+
+ @Override
+ public void correctionButtonPressed() {
+ gui.correctionButtonPressed();
+ }
+
+ @Override
+ public void allKeysCleared() {
+ gui.allKeysCleared();
+ }
+
+ @Override
+ public void finish() {
+ gui.showMessageDialog(BKUGUIFacade.TITLE_WAIT, BKUGUIFacade.MESSAGE_WAIT);
+ }
+}
diff --git a/smccSTALExt/src/main/java/at/gv/egiz/bku/pin/gui/ManagementPINProvider.java b/smccSTALExt/src/main/java/at/gv/egiz/bku/pin/gui/ManagementPINProvider.java
new file mode 100644
index 00000000..8d842d13
--- /dev/null
+++ b/smccSTALExt/src/main/java/at/gv/egiz/bku/pin/gui/ManagementPINProvider.java
@@ -0,0 +1,89 @@
+/*
+ * Copyright 2008 Federal Chancellery Austria and
+ * Graz University of Technology
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package at.gv.egiz.bku.pin.gui;
+
+import at.gv.egiz.bku.gui.BKUGUIFacade;
+import at.gv.egiz.bku.gui.PINManagementGUIFacade;
+import at.gv.egiz.smcc.CancelledException;
+import at.gv.egiz.smcc.PINSpec;
+import at.gv.egiz.smcc.pin.gui.ModifyPINProvider;
+import org.apache.commons.logging.Log;
+import org.apache.commons.logging.LogFactory;
+
+public class ManagementPINProvider extends AbstractPINProvider implements ModifyPINProvider {
+
+ protected static final Log log = LogFactory.getLog(ManagementPINProvider.class);
+ protected PINManagementGUIFacade gui;
+ protected PINManagementGUIFacade.DIALOG type;
+ private boolean retry = false;
+
+ public ManagementPINProvider(PINManagementGUIFacade gui, PINManagementGUIFacade.DIALOG type) {
+ this.gui = gui;
+ this.type = type;
+ }
+
+ @Override
+ public char[] provideCurrentPIN(PINSpec spec, int retries)
+ throws CancelledException, InterruptedException {
+
+ gui.showPINDialog(type, spec, (retry) ? retries : -1,
+ this, "change",
+ this, "cancel");
+
+ log.trace("[" + Thread.currentThread().getName() + "] wait for action");
+ waitForAction();
+ log.trace("[" + Thread.currentThread().getName() + "] received action " + action);
+
+ gui.showMessageDialog(BKUGUIFacade.TITLE_WAIT,
+ BKUGUIFacade.MESSAGE_WAIT);
+
+ if ("cancel".equals(action)) {
+ throw new CancelledException(spec.getLocalizedName() +
+ " entry cancelled");
+ }
+ retry = true;
+ return gui.getOldPin();
+ }
+
+ @Override
+ public char[] provideNewPIN(PINSpec spec)
+ throws CancelledException, InterruptedException {
+
+ char[] pin = gui.getPin();
+ if (pin != null) {
+ // change pin dialog also returns new pin
+ return pin;
+ }
+
+ gui.showPINDialog(type, spec, -1,
+ this, "activate",
+ this, "cancel");
+
+ log.trace("[" + Thread.currentThread().getName() + "] wait for action");
+ waitForAction();
+ log.trace("[" + Thread.currentThread().getName() + "] received action " + action);
+
+ gui.showMessageDialog(BKUGUIFacade.TITLE_WAIT,
+ BKUGUIFacade.MESSAGE_WAIT);
+
+ if ("cancel".equals(action)) {
+ throw new CancelledException(spec.getLocalizedName() +
+ " entry cancelled");
+ }
+ return gui.getPin();
+ }
+}
diff --git a/smccSTALExt/src/main/java/at/gv/egiz/bku/smccstal/ManagementPINProviderFactory.java b/smccSTALExt/src/main/java/at/gv/egiz/bku/smccstal/ManagementPINProviderFactory.java
deleted file mode 100644
index 493733b8..00000000
--- a/smccSTALExt/src/main/java/at/gv/egiz/bku/smccstal/ManagementPINProviderFactory.java
+++ /dev/null
@@ -1,246 +0,0 @@
-/*
- * Copyright 2008 Federal Chancellery Austria and
- * Graz University of Technology
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package at.gv.egiz.bku.smccstal;
-
-import at.gv.egiz.bku.gui.BKUGUIFacade;
-import at.gv.egiz.smcc.ChangePINProvider;
-import at.gv.egiz.bku.gui.PINManagementGUIFacade;
-import at.gv.egiz.bku.smccstal.AbstractPINProvider;
-import at.gv.egiz.bku.smccstal.PINProviderFactory;
-import at.gv.egiz.smcc.CancelledException;
-import at.gv.egiz.smcc.ccid.CCID;
-import at.gv.egiz.smcc.PINProvider;
-import at.gv.egiz.smcc.PINSpec;
-import at.gv.egiz.smcc.SignatureCard;
-
-/**
- *
- * @author Clemens Orthacker
- */
-public class ManagementPINProviderFactory extends PINProviderFactory {
-
- public ManagementPINProviderFactory(CCID reader, PINManagementGUIFacade gui) {
- super(reader, gui);
- }
-
-// public static ManagementPINProviderFactory getInstance(SignatureCard forCard,
-// PINManagementGUIFacade gui) {
-// if (forCard.getReader().hasFeature(CCID.FEATURE_VERIFY_PIN_DIRECT)) {
-// return new PinpadPINProviderFactory(gui);
-//
-// } else {
-// return new SoftwarePINProviderFactory(gui);
-// }
-// }
-
- public PINProvider getVerifyPINProvider() {
- if (reader.hasFeature(CCID.FEATURE_VERIFY_PIN_START)) {
- return new PinpadGenericPinProvider(PINManagementGUIFacade.DIALOG.VERIFY);
- } else if (reader.hasFeature(CCID.FEATURE_VERIFY_PIN_DIRECT)) {
- return new PinpadGenericPinProvider(PINManagementGUIFacade.DIALOG.VERIFY);
- } else {
- return new SoftwareGenericPinProvider(PINManagementGUIFacade.DIALOG.VERIFY);
- }
- }
-
- public PINProvider getActivatePINProvider() {
- if (reader.hasFeature(CCID.FEATURE_MODIFY_PIN_START)) {
- return new PinpadGenericPinProvider(PINManagementGUIFacade.DIALOG.ACTIVATE);
- } else if (reader.hasFeature(CCID.FEATURE_MODIFY_PIN_DIRECT)) {
- return new PinpadGenericPinProvider(PINManagementGUIFacade.DIALOG.ACTIVATE);
- } else {
- return new SoftwareGenericPinProvider(PINManagementGUIFacade.DIALOG.ACTIVATE);
- }
- }
-
- public ChangePINProvider getChangePINProvider() {
- if (reader.hasFeature(CCID.FEATURE_MODIFY_PIN_START)) {
- return new PinpadGenericPinProvider(PINManagementGUIFacade.DIALOG.CHANGE);
- } else if (reader.hasFeature(CCID.FEATURE_MODIFY_PIN_DIRECT)) {
- return new PinpadGenericPinProvider(PINManagementGUIFacade.DIALOG.CHANGE);
- } else {
- return new ChangePinProvider();
- }
- }
-
- public PINProvider getUnblockPINProvider() {
- if (reader.hasFeature(CCID.FEATURE_VERIFY_PIN_START)) {
- return new PinpadGenericPinProvider(PINManagementGUIFacade.DIALOG.UNBLOCK);
- } else if (reader.hasFeature(CCID.FEATURE_VERIFY_PIN_DIRECT)) {
- return new PinpadGenericPinProvider(PINManagementGUIFacade.DIALOG.UNBLOCK);
- } else {
- return new SoftwareGenericPinProvider(PINManagementGUIFacade.DIALOG.UNBLOCK);
- }
- }
-
- class PinpadGenericPinProvider extends AbstractPINProvider
- implements ChangePINProvider {
-
- protected PINManagementGUIFacade.DIALOG type;
-
- private PinpadGenericPinProvider(PINManagementGUIFacade.DIALOG type) {
- this.type = type;
- }
-
- @Override
- public char[] providePIN(PINSpec spec, int retries)
- throws CancelledException, InterruptedException {
-
- showPinpadPINDialog(retries, spec);
- retry = true;
- return null;
- }
-
- /**
- * do not call this method without calling providePIN()
- * (no message is displayed)
- * @param spec
- * @param retries
- * @return
- */
- @Override
- public char[] provideOldPIN(PINSpec spec, int retries) {
- return null;
- }
-
- private void showPinpadPINDialog(int retries, PINSpec pinSpec) {
- String title, message;
- Object[] params;
- if (retry) {
- if (retries == 1) {
- message = BKUGUIFacade.MESSAGE_LAST_RETRY_PINPAD;
- } else {
- message = BKUGUIFacade.MESSAGE_RETRIES_PINPAD;
- }
- title = BKUGUIFacade.TITLE_RETRY;
- params = new Object[]{String.valueOf(retries)};
- } else if (type == PINManagementGUIFacade.DIALOG.VERIFY) {
- title = PINManagementGUIFacade.TITLE_VERIFY_PIN;
- message = BKUGUIFacade.MESSAGE_ENTERPIN_PINPAD;
- params = new Object[]{pinSpec.getLocalizedName(), pinSpec.getLocalizedLength()};
- } else if (type == PINManagementGUIFacade.DIALOG.ACTIVATE) {
- title = PINManagementGUIFacade.TITLE_ACTIVATE_PIN;
- message = PINManagementGUIFacade.MESSAGE_ACTIVATEPIN_PINPAD;
- params = new Object[]{pinSpec.getLocalizedName(), pinSpec.getLocalizedLength()};
- } else if (type == PINManagementGUIFacade.DIALOG.CHANGE) {
- title = PINManagementGUIFacade.TITLE_CHANGE_PIN;
- message = PINManagementGUIFacade.MESSAGE_CHANGEPIN_PINPAD;
- params = new Object[]{pinSpec.getLocalizedName(), pinSpec.getLocalizedLength()};
- } else { //if (type == DIALOG.UNBLOCK) {
- title = PINManagementGUIFacade.TITLE_UNBLOCK_PIN;
- message = PINManagementGUIFacade.MESSAGE_UNBLOCKPIN_PINPAD;
- params = new Object[]{pinSpec.getLocalizedName(), pinSpec.getLocalizedLength()};
- }
- gui.showMessageDialog(title, message, params);
- }
- }
-
-
- class SoftwareGenericPinProvider extends AbstractPINProvider {
-
-// protected PINManagementGUIFacade gui;
- protected PINManagementGUIFacade.DIALOG type;
-
- private SoftwareGenericPinProvider(PINManagementGUIFacade.DIALOG type) {
- this.type = type;
- }
-
- @Override
- public char[] providePIN(PINSpec spec, int retries)
- throws CancelledException, InterruptedException {
-
- ((PINManagementGUIFacade) gui).showPINDialog(type, spec,
- (retry) ? retries : -1,
- this, "exec",
- this, "back");
-
- waitForAction();
-
- if ("exec".equals(action)) {
- gui.showMessageDialog(BKUGUIFacade.TITLE_WAIT,
- BKUGUIFacade.MESSAGE_WAIT);
- retry = true;
- return gui.getPin();
- } else if ("back".equals(action)) {
- throw new CancelledException();
- } else {
- log.error("unsupported command " + action);
- throw new CancelledException();
- }
- }
- }
-
- class ChangePinProvider extends AbstractPINProvider
- implements ChangePINProvider {
-
-// protected PINManagementGUIFacade gui;
-
- private char[] oldPin;
- private char[] newPin;
-
- private ChangePinProvider() {
- }
-
- @Override
- public char[] providePIN(PINSpec spec, int retries)
- throws CancelledException, InterruptedException {
- if (newPin == null) {
- getPINs(spec, retries);
- }
- char[] pin = newPin;
- newPin = null;
- return pin;
- }
-
- @Override
- public char[] provideOldPIN(PINSpec spec, int retries)
- throws CancelledException, InterruptedException {
- if (oldPin == null) {
- getPINs(spec, retries);
- }
- char[] pin = oldPin;
- oldPin = null;
- return pin;
- }
-
- private void getPINs(PINSpec spec, int retries)
- throws InterruptedException, CancelledException {
-
- ((PINManagementGUIFacade) gui).showPINDialog(
- PINManagementGUIFacade.DIALOG.CHANGE, spec,
- (retry) ? retries : -1,
- this, "exec",
- this, "back");
-
- waitForAction();
-
- if ("exec".equals(action)) {
- gui.showMessageDialog(BKUGUIFacade.TITLE_WAIT,
- BKUGUIFacade.MESSAGE_WAIT);
- retry = true;
- oldPin = ((PINManagementGUIFacade) gui).getOldPin();
- newPin = gui.getPin();
- } else if ("back".equals(action)) {
- throw new CancelledException();
- } else {
- log.error("unsupported command " + action);
- throw new CancelledException();
- }
- }
- }
-}
diff --git a/smccSTALExt/src/main/java/at/gv/egiz/bku/smccstal/PINManagementRequestHandler.java b/smccSTALExt/src/main/java/at/gv/egiz/bku/smccstal/PINManagementRequestHandler.java
index bfeb90b0..0d49afd0 100644
--- a/smccSTALExt/src/main/java/at/gv/egiz/bku/smccstal/PINManagementRequestHandler.java
+++ b/smccSTALExt/src/main/java/at/gv/egiz/bku/smccstal/PINManagementRequestHandler.java
@@ -23,9 +23,11 @@ import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import at.gv.egiz.bku.gui.BKUGUIFacade;
+import at.gv.egiz.bku.gui.PINManagementGUI;
import at.gv.egiz.bku.gui.PINManagementGUIFacade;
import at.gv.egiz.bku.gui.PINManagementGUIFacade.STATUS;
-import at.gv.egiz.bku.smccstal.AbstractRequestHandler;
+import at.gv.egiz.bku.pin.gui.ManagementPINGUI;
+import at.gv.egiz.bku.pin.gui.VerifyPINGUI;
import at.gv.egiz.smcc.CancelledException;
import at.gv.egiz.smcc.LockedException;
import at.gv.egiz.smcc.NotActivatedException;
@@ -96,40 +98,15 @@ public class PINManagementRequestHandler extends AbstractRequestHandler {
throw new NullPointerException("no PIN selected for activation/change");
}
- ManagementPINProviderFactory ppfac =
- new ManagementPINProviderFactory(card.getReader(), gui);
-
try {
if ("activate_enterpin".equals(actionCommand)) {
- log.info("activate " + selectedPIN.getLocalizedName());
- ((PINMgmtSignatureCard) card).activatePIN(selectedPIN,
- ppfac.getActivatePINProvider());
- updatePINState(selectedPIN, STATUS.ACTIV);
- gui.showMessageDialog(PINManagementGUIFacade.TITLE_ACTIVATE_SUCCESS,
- PINManagementGUIFacade.MESSAGE_ACTIVATE_SUCCESS,
- new Object[] {selectedPIN.getLocalizedName()},
- BKUGUIFacade.BUTTON_OK, this, "ok");
- waitForAction();
+ activatePIN(selectedPIN);
} else if ("change_enterpin".equals(actionCommand)) {
- log.info("change " + selectedPIN.getLocalizedName());
- ((PINMgmtSignatureCard) card).changePIN(selectedPIN,
- ppfac.getChangePINProvider());
- updatePINState(selectedPIN, STATUS.ACTIV);
- gui.showMessageDialog(PINManagementGUIFacade.TITLE_CHANGE_SUCCESS,
- PINManagementGUIFacade.MESSAGE_CHANGE_SUCCESS,
- new Object[] {selectedPIN.getLocalizedName()},
- BKUGUIFacade.BUTTON_OK, this, "ok");
- waitForAction();
-
+ changePIN(selectedPIN);
} else if ("unblock_enterpuk".equals(actionCommand)) {
- log.info("unblock " + selectedPIN.getLocalizedName());
- ((PINMgmtSignatureCard) card).unblockPIN(selectedPIN,
- ppfac.getUnblockPINProvider());
+ unblockPIN(selectedPIN);
} else if ("verify_enterpin".equals(actionCommand)) {
- log.info("verify " + selectedPIN.getLocalizedName());
- ((PINMgmtSignatureCard) card).verifyPIN(selectedPIN,
- ppfac.getVerifyPINProvider());
- updatePINState(selectedPIN, STATUS.ACTIV);
+ verifyPIN(selectedPIN);
}
} catch (CancelledException ex) {
log.trace("cancelled");
@@ -154,29 +131,17 @@ public class PINManagementRequestHandler extends AbstractRequestHandler {
new Object[] {selectedPIN.getLocalizedName()},
this, null);
waitForAction();
- } catch (PINConfirmationException ex) {
- log.error("confirmation pin does not match new " + selectedPIN.getLocalizedName());
- gui.showErrorDialog(PINManagementGUIFacade.ERR_PIN_CONFIRMATION,
- new Object[] {selectedPIN.getLocalizedName()},
- this, null);
- waitForAction();
+
+ // inner loop for pinConfirmation and pinFormat ex
+// } catch (PINConfirmationException ex) {
+// } catch (PINFormatException ex) {
+
} catch (PINOperationAbortedException ex) {
log.error("pin operation aborted without further details");
gui.showErrorDialog(PINManagementGUIFacade.ERR_PIN_OPERATION_ABORTED,
new Object[] {selectedPIN.getLocalizedName()},
this, null);
waitForAction();
- } catch (PINFormatException ex) {
- log.error("wrong format of new " + selectedPIN.getLocalizedName());
-// updatePINStatus(selectedPIN, STATUS.NOT_ACTIV);
- String pinSize = String.valueOf(selectedPIN.getMinLength());
- if (selectedPIN.getMinLength() != selectedPIN.getMaxLength()) {
- pinSize += "-" + selectedPIN.getMaxLength();
- }
- gui.showErrorDialog(PINManagementGUIFacade.ERR_PIN_FORMAT,
- new Object[] {selectedPIN.getLocalizedName(), pinSize},
- this, null);
- waitForAction();
}
} // end if
@@ -206,6 +171,157 @@ public class PINManagementRequestHandler extends AbstractRequestHandler {
}
}
+ private void activatePIN(PINSpec selectedPIN)
+ throws InterruptedException, SignatureCardException, GetPINStatusException {
+
+ log.info("activate " + selectedPIN.getLocalizedName());
+ ManagementPINGUI pinGUI = new ManagementPINGUI((PINManagementGUI) gui,
+ PINManagementGUIFacade.DIALOG.ACTIVATE);
+
+ boolean reentry;
+ do {
+ try {
+ reentry = false;
+ ((PINMgmtSignatureCard) card).activatePIN(selectedPIN, pinGUI);
+ } catch (PINConfirmationException ex) {
+ reentry = true;
+ log.error("confirmation pin does not match new " + selectedPIN.getLocalizedName());
+ gui.showErrorDialog(PINManagementGUIFacade.ERR_PIN_CONFIRMATION,
+ new Object[] {selectedPIN.getLocalizedName()},
+ this, null);
+ waitForAction();
+ } catch (PINFormatException ex) {
+ reentry = true;
+ log.error("wrong format of new " + selectedPIN.getLocalizedName());
+ String pinSize = String.valueOf(selectedPIN.getMinLength());
+ if (selectedPIN.getMinLength() != selectedPIN.getMaxLength()) {
+ pinSize += "-" + selectedPIN.getMaxLength();
+ }
+ gui.showErrorDialog(PINManagementGUIFacade.ERR_PIN_FORMAT,
+ new Object[] {selectedPIN.getLocalizedName(), pinSize},
+ this, null);
+ waitForAction();
+ }
+ } while (reentry);
+
+ updatePINState(selectedPIN, STATUS.ACTIV);
+ gui.showMessageDialog(PINManagementGUIFacade.TITLE_ACTIVATE_SUCCESS,
+ PINManagementGUIFacade.MESSAGE_ACTIVATE_SUCCESS,
+ new Object[]{selectedPIN.getLocalizedName()},
+ BKUGUIFacade.BUTTON_OK, this, "ok");
+ waitForAction();
+ }
+
+ private void verifyPIN(PINSpec selectedPIN)
+ throws InterruptedException, SignatureCardException, GetPINStatusException {
+
+ log.info("verify " + selectedPIN.getLocalizedName());
+ VerifyPINGUI pinGUI = new VerifyPINGUI(gui);
+
+ boolean reentry;
+ do {
+ try {
+ reentry = false;
+ ((PINMgmtSignatureCard) card).verifyPIN(selectedPIN, pinGUI);
+ } catch (PINFormatException ex) {
+ reentry = true;
+ log.error("wrong format of new " + selectedPIN.getLocalizedName());
+ String pinSize = String.valueOf(selectedPIN.getMinLength());
+ if (selectedPIN.getMinLength() != selectedPIN.getMaxLength()) {
+ pinSize += "-" + selectedPIN.getMaxLength();
+ }
+ gui.showErrorDialog(PINManagementGUIFacade.ERR_PIN_FORMAT,
+ new Object[] {selectedPIN.getLocalizedName(), pinSize},
+ this, null);
+ waitForAction();
+ }
+ } while (reentry);
+
+ updatePINState(selectedPIN, STATUS.ACTIV);
+ }
+
+ private void changePIN(PINSpec selectedPIN)
+ throws SignatureCardException, GetPINStatusException, InterruptedException {
+
+ log.info("change " + selectedPIN.getLocalizedName());
+ ManagementPINGUI pinGUI = new ManagementPINGUI((PINManagementGUI) gui,
+ PINManagementGUIFacade.DIALOG.CHANGE);
+
+ boolean reentry;
+ do {
+ try {
+ reentry = false;
+ ((PINMgmtSignatureCard) card).changePIN(selectedPIN, pinGUI);
+ } catch (PINConfirmationException ex) {
+ reentry = true;
+ log.error("confirmation pin does not match new " + selectedPIN.getLocalizedName());
+ gui.showErrorDialog(PINManagementGUIFacade.ERR_PIN_CONFIRMATION,
+ new Object[] {selectedPIN.getLocalizedName()},
+ this, null);
+ waitForAction();
+ } catch (PINFormatException ex) {
+ reentry = true;
+ log.error("wrong format of new " + selectedPIN.getLocalizedName());
+ String pinSize = String.valueOf(selectedPIN.getMinLength());
+ if (selectedPIN.getMinLength() != selectedPIN.getMaxLength()) {
+ pinSize += "-" + selectedPIN.getMaxLength();
+ }
+ gui.showErrorDialog(PINManagementGUIFacade.ERR_PIN_FORMAT,
+ new Object[] {selectedPIN.getLocalizedName(), pinSize},
+ this, null);
+ waitForAction();
+ }
+ } while (reentry);
+
+ updatePINState(selectedPIN, STATUS.ACTIV);
+ gui.showMessageDialog(PINManagementGUIFacade.TITLE_CHANGE_SUCCESS,
+ PINManagementGUIFacade.MESSAGE_CHANGE_SUCCESS,
+ new Object[]{selectedPIN.getLocalizedName()},
+ BKUGUIFacade.BUTTON_OK, this, "ok");
+ waitForAction();
+ }
+
+ private void unblockPIN(PINSpec selectedPIN)
+ throws SignatureCardException, GetPINStatusException, InterruptedException {
+
+ log.info("unblock " + selectedPIN.getLocalizedName());
+ ManagementPINGUI pinGUI = new ManagementPINGUI((PINManagementGUI) gui,
+ PINManagementGUIFacade.DIALOG.UNBLOCK);
+
+ boolean reentry;
+ do {
+ try {
+ reentry = false;
+ ((PINMgmtSignatureCard) card).unblockPIN(selectedPIN, pinGUI);
+ } catch (PINConfirmationException ex) {
+ reentry = true;
+ log.error("confirmation pin does not match new " + selectedPIN.getLocalizedName());
+ gui.showErrorDialog(PINManagementGUIFacade.ERR_PIN_CONFIRMATION,
+ new Object[] {selectedPIN.getLocalizedName()},
+ this, null);
+ waitForAction();
+ } catch (PINFormatException ex) {
+ reentry = true;
+ log.error("wrong format of new " + selectedPIN.getLocalizedName());
+ String pinSize = String.valueOf(selectedPIN.getMinLength());
+ if (selectedPIN.getMinLength() != selectedPIN.getMaxLength()) {
+ pinSize += "-" + selectedPIN.getMaxLength();
+ }
+ gui.showErrorDialog(PINManagementGUIFacade.ERR_PIN_FORMAT,
+ new Object[] {selectedPIN.getLocalizedName(), pinSize},
+ this, null);
+ waitForAction();
+ }
+ } while (reentry);
+
+ updatePINState(selectedPIN, STATUS.ACTIV);
+ gui.showMessageDialog(PINManagementGUIFacade.TITLE_UNBLOCK_SUCCESS,
+ PINManagementGUIFacade.MESSAGE_UNBLOCK_SUCCESS,
+ new Object[]{selectedPIN.getLocalizedName()},
+ BKUGUIFacade.BUTTON_OK, this, "ok");
+ waitForAction();
+ }
+
@Override
public boolean requireCard() {
return true;
--
cgit v1.2.3