You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@harmony.apache.org by te...@apache.org on 2006/12/12 17:34:59 UTC
svn commit: r486218 - in
/harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner:
ArgParser.java JSHelper.java JSParameters.java JSSigner.java
JSVerifier.java Main.java TimeStampGenerator.java UserInteractor.java
Author: tellison
Date: Tue Dec 12 08:34:58 2006
New Revision: 486218
URL: http://svn.apache.org/viewvc?view=rev&rev=486218
Log:
Apply patch HARMONY-2312 ([classlib][tools] JarSigner implementation update)
Added:
harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/JSHelper.java (with props)
Modified:
harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/ArgParser.java
harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/JSParameters.java
harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/JSSigner.java
harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/JSVerifier.java
harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/Main.java
harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/TimeStampGenerator.java
harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/UserInteractor.java
Modified: harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/ArgParser.java
URL: http://svn.apache.org/viewvc/harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/ArgParser.java?view=diff&rev=486218&r1=486217&r2=486218
==============================================================================
--- harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/ArgParser.java (original)
+++ harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/ArgParser.java Tue Dec 12 08:34:58 2006
@@ -23,17 +23,15 @@
import java.security.KeyStore;
import java.security.KeyStoreException;
import java.security.NoSuchAlgorithmException;
-import java.security.NoSuchProviderException;
import java.security.Provider;
import java.security.Security;
import java.security.UnrecoverableKeyException;
-import java.security.cert.CertificateException;
+import java.util.logging.Logger;
/**
* The class to parse the program arguments.
*/
-public class ArgParser {
- // TODO
+class ArgParser {
// options names to compare to //
final static String sVerify = "-verify";
@@ -57,26 +55,36 @@
final static String sSectionsOnly = "-sectionsonly";
- final static String sProvider = "-provider";
+ final static String sProvider = "-providerclass";
final static String sProviderName = "-providername";
- final static String sCertProvider = "-certprovider";
+ final static String sCertProvider = "-certproviderclass";
final static String sCertProviderName = "-certprovidername";
- final static String sSigProvider = "-sigprovider";
+ final static String sSigProvider = "-sigproviderclass";
final static String sSigProviderName = "-sigprovidername";
- final static String sKSProvider = "-ksprovider";
+ final static String sKSProvider = "-ksproviderclass";
final static String sKSProviderName = "-ksprovidername";
+ final static String sMDProvider = "-mdproviderclass";
+
+ final static String sMDProviderName = "-mdprovidername";
+
final static String sTSA = "-tsa";
final static String sTSAcert = "-tsacert";
+ final static String sProxy = "-proxy";
+
+ final static String sProxyType = "-proxytype";
+
+ final static String sSilent = "-silent";
+
final static String sAltSigner = "-altsigner";
final static String sAltSignerPath = "-altsignerpath";
@@ -89,18 +97,16 @@
* zero-sized, an unknown option is found or an expected option
* value is not given or not of an expected type. If null is
* returned, the param object contents is not defined.
- * @throws JarSignerException
- * @throws IOException
- * @throws NoSuchAlgorithmException
- * @throws UnrecoverableKeyException
- * @throws KeyStoreException
- * @throws NoSuchProviderException
- * @throws CertificateException
+ *
+ * @throws JarSignerException
+ * @throws IOException
+ * @throws KeyStoreException
+ * @throws UnrecoverableKeyException
+ * @throws NoSuchAlgorithmException
*/
static JSParameters parseArgs(String[] args, JSParameters param)
- throws JarSignerException, KeyStoreException,
- UnrecoverableKeyException, NoSuchAlgorithmException, IOException,
- CertificateException, NoSuchProviderException {
+ throws JarSignerException, IOException, KeyStoreException,
+ UnrecoverableKeyException, NoSuchAlgorithmException {
if (args == null){
return null;
}
@@ -110,7 +116,7 @@
if (param == null){
param = new JSParameters();
} else {
- // clean param
+ // clean the param
param.setDefault();
}
@@ -152,6 +158,10 @@
param.setVerbose(true);
continue;
}
+ if (args[i].equalsIgnoreCase(sSilent)) {
+ param.setSilent(true);
+ continue;
+ }
if (args[i].equalsIgnoreCase(sInternalSF)) {
param.setInternalSF(true);
continue;
@@ -196,13 +206,21 @@
param.setKsProviderName(args[++i]);
continue;
}
+ if (args[i].equalsIgnoreCase(sMDProvider)) {
+ param.setMdProvider(args[++i]);
+ addProvider(args[i]);
+ continue;
+ }
+ if (args[i].equalsIgnoreCase(sMDProviderName)) {
+ param.setMdProviderName(args[++i]);
+ continue;
+ }
if (args[i].equalsIgnoreCase(sTSA)) {
try {
- // TODO: URI scheme
param.setTsaURI(new URI(args[++i]));
} catch (URISyntaxException e) {
throw new JarSignerException("Argument " + args[i]
- + " is not a path or URL");
+ + " is not an URI");
}
continue;
}
@@ -210,6 +228,26 @@
param.setTsaCertAlias(args[++i]);
continue;
}
+ if (args[i].equalsIgnoreCase(sProxy)) {
+ int colonPos = args[++i].lastIndexOf(':');
+ if (colonPos == -1) {
+ param.setProxy(args[i]);
+ continue;
+ }
+
+ String proxy = args[i].substring(0, colonPos);
+ int port;
+ try {
+ port = Integer.parseInt(args[i].substring(colonPos + 1,
+ args[i].length()));
+ } catch (NumberFormatException e) {
+ throw new JarSignerException(
+ "Proxy port must be an integer value.");
+ }
+ param.setProxy(proxy);
+ param.setProxyPort(port);
+ continue;
+ }
if (args[i].equalsIgnoreCase(sAltSigner)) {
param.setAltSigner(args[++i]);
continue;
@@ -221,13 +259,7 @@
if ((param.isVerify() && i == args.length - 1)
|| (!param.isVerify() && i == args.length - 2)) {
- try {
- // TODO: URI scheme
- param.setJarURI(new URI(args[i]));
- } catch (URISyntaxException e) {
- throw new JarSignerException("Argument " + args[i]
- + " is not a path or URL");
- }
+ param.setJarURIorPath(args[i]);
continue;
}
if (!param.isVerify() && i == args.length - 1){
@@ -243,6 +275,7 @@
}
// set specific provider names the same as the main provider name
+ // if their values are not set.
String providerName = param.getProviderName();
if (providerName != null){
if (param.getCertProviderName() == null){
@@ -254,22 +287,45 @@
if (param.getKsProviderName() == null){
param.setKsProviderName(providerName);
}
+ if (param.getMdProviderName() == null){
+ param.setMdProviderName(providerName);
+ }
}
// if the store password is not given, prompt for it
if (param.getStorePass() == null) {
param.setStorePass(UserInteractor
.getDataFromUser("Enter keystore password: "));
+ // ckeck the password
+ param.getKeyStore();
}
- if (param.getAlias() == null){
- // TODO
+ if (param.getAlias() == null && !param.isVerify()) {
+ param.setAlias(new String(UserInteractor
+ .getDataFromUser("Enter alias name: ")));
+ }
+ if (!param.getKeyStore().containsAlias(param.getAlias())) {
+ throw new JarSignerException("The alias " + param.getAlias()
+ + " does not exist in keystore");
}
+
// if key password is not given, try to inplace it with store password
- if (param.getKeyPass() == null){
+ if (param.getKeyPass() == null) {
param.setKeyPass(tryStorePassAsKeyPass(param.getKeyStore(), param
.getAlias(), param.getStorePass()));
}
+
+ // TODO: if decide to implement such abilities, remove this code
+ if (param.isInternalSF() || param.isSectionsOnly()
+ || param.getAltSigner() != null
+ || param.getAltSignerPath() != null) {
+ Logger.getLogger(JSParameters.loggerName).warning(
+ "Options " + sAltSigner + ", " + sAltSignerPath + ", "
+ + sInternalSF + ", " + sSectionsOnly
+ + " are currently ignored since they eliminate "
+ + "useful optimizations. ");
+ }
+
return param;
}
Added: harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/JSHelper.java
URL: http://svn.apache.org/viewvc/harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/JSHelper.java?view=auto&rev=486218
==============================================================================
--- harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/JSHelper.java (added)
+++ harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/JSHelper.java Tue Dec 12 08:34:58 2006
@@ -0,0 +1,98 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you 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 org.apache.harmony.tools.jarsigner;
+
+import java.util.logging.Logger;
+
+/**
+ * The class prints JarSigner help message.
+ */
+class JSHelper {
+ /**
+ * Prints help message.
+ */
+ static void printHelp(){
+ StringBuilder buf = new StringBuilder();
+ buf.append("JarSigner help.");
+ buf.append("\nUsage:");
+ buf.append("\tjarsigner {options} JAR-file alias");
+ buf.append("\n\tjarsigner -verify {options} JAR-file");
+
+ buf.append("\n\n-verify\t\t\t\t verify a signed JAR file");
+
+ buf.append("\n-keystore <keystore_path>\t location of the keystore");
+
+ buf.append("\n-storetype <keystore_type>\t type of the keystore");
+
+ buf.append("\n-storepass <keystore_password>\t keystore password");
+
+ buf.append("\n-keypass <key_password>\t\t private key password ");
+ buf.append("(if differs from <keystore_password>)");
+
+ buf.append("\n-signedjar <file_name>\t\t name of the signed JAR file");
+
+ buf.append("\n-sigfile <file_name>\t\t name of .SF and .DSA files");
+
+ buf.append("\n-verbose \t\t\t provide additional output");
+
+ buf.append("\n-silent \t\t\t provide as few output as possible");
+
+ buf.append("\n-certs \t\t\t\t display certificates ");
+ buf.append("(use with -veify and -verbose)");
+
+ buf.append("\n-tsa <TSA_URL>\t\t\t location of time-stamp authority");
+
+ buf.append("\n-tsacert <TSA_cert_alias>\t keystore alias of the ");
+ buf.append("TSA certificate");
+
+ buf.append("\n-proxy <host_address>{:<port>}\t proxy server host ");
+ buf.append("address and port, e.g. proxy.server.com:1234");
+
+ buf.append("\n-proxytype <type_name>\t\t type of the proxy server (HTTP or SOCKS)");
+
+ buf.append("\n-providerclass <class>\t\t class name of cryptographic ");
+ buf.append("service provider");
+
+ buf.append("\n-providername <name>\t\t provider name");
+
+ buf.append("\n-ksproviderclass <class>\t class name of cryptographic ");
+ buf.append("service provider for managing keystore");
+
+ buf.append("\n-ksprovidername <name>\t\t keystore provider name");
+
+ buf.append("\n-sigproviderclass <class>\t class name of cryptographic ");
+ buf.append("service provider for work with signatures");
+
+ buf.append("\n-sigprovidername <name>\t\t signature provider name");
+
+ buf.append("\n-certproviderclass <class>\t class name of cryptographic ");
+ buf.append("service provider for work with certificates");
+
+ buf.append("\n-certprovidername <name>\t certificate provider name");
+
+ buf.append("\n-mdproviderclass <class>\t class name of cryptographic ");
+ buf.append("service provider for work with message digests");
+
+ buf.append("\n-mdprovidername <name>\t\t message digest provider name");
+
+ Logger.getLogger(JSParameters.loggerName).info(buf.toString());
+ }
+}
+
Propchange: harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/JSHelper.java
------------------------------------------------------------------------------
svn:eol-style = native
Modified: harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/JSParameters.java
URL: http://svn.apache.org/viewvc/harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/JSParameters.java?view=diff&rev=486218&r1=486217&r2=486218
==============================================================================
--- harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/JSParameters.java (original)
+++ harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/JSParameters.java Tue Dec 12 08:34:58 2006
@@ -21,19 +21,21 @@
import java.io.IOException;
import java.net.Proxy;
import java.net.URI;
+import java.net.URISyntaxException;
import java.security.KeyStore;
import java.util.jar.JarFile;
import java.util.logging.Handler;
import java.util.logging.Level;
import java.util.logging.Logger;
+import org.apache.harmony.tools.keytool.KeytoolParameters;
import org.apache.harmony.tools.toolutils.KeyStoreLoaderSaver;
/**
* The class encapsulates paramaters for jarsigner most of which are ususally
* given in command line.
*/
-public class JSParameters {
+class JSParameters {
/**
* Default location of the keystore. Used when the value is not supplied by
* the user.
@@ -54,8 +56,8 @@
// JAR file to work with
private JarFile jarFile;
- // JAR file URL
- private URI jarURI;
+ // JAR file URI or path
+ private String jarURIPath;
// alias to access an entry in keystore
private String alias;
@@ -165,7 +167,7 @@
void setDefault(){
keyStore = null;
jarFile = null;
- jarURI = null;
+ jarURIPath = null;
alias = null;
storeURI = null;
storeType = KeyStore.getDefaultType();
@@ -199,7 +201,7 @@
isSilent = false;
proxy = null;
proxyPort = 8888;
- proxyType = null;
+ proxyType = Proxy.Type.HTTP;
}
// Getters and setters down here
@@ -301,10 +303,10 @@
}
/**
- * @param jarURI
+ * @param jarURIPath
*/
- public void setJarURI(URI jarURI) {
- this.jarURI = jarURI;
+ public void setJarURIorPath(String jarURIPath) {
+ this.jarURIPath = jarURIPath;
}
/**
@@ -575,10 +577,21 @@
JarFile getJarFile() throws IOException {
if (jarFile == null) {
try {
- jarFile = new JarFile(new File(jarURI), isVerify);
+ File file;
+ try {
+ // try to open the file as if jarURIPath is an URI
+ URI jarURI = new URI(jarURIPath);
+ file = new File(jarURI);
+ } catch (URISyntaxException e) {
+ // try to open the file as if jarURIPath is a path
+ file = new File(jarURIPath);
+ } catch (IllegalArgumentException e) {
+ file = new File(jarURIPath);
+ }
+ jarFile = new JarFile(file, isVerify);
} catch (IOException e) {
throw (IOException) new IOException("Failed to load JAR file "
- + jarURI).initCause(e);
+ + jarURIPath).initCause(e);
}
}
return jarFile;
@@ -587,8 +600,8 @@
/**
* @return
*/
- URI getJarURI() {
- return jarURI;
+ String getJarURIorPath() {
+ return jarURIPath;
}
/**
@@ -613,11 +626,17 @@
if (keyStore == null) {
String ksProvName = (ksProviderName != null) ? ksProviderName
: providerName;
+ // If the path to the store is not specified, try to open
+ // the store using the default path.
+ if (storeURI == null) {
+ storeURI = KeytoolParameters.defaultKeystorePath;
+ }
try {
keyStore = KeyStoreLoaderSaver.loadStore(storeURI, storeType,
storePass, ksProvName);
} catch (Exception e) {
- throw new JarSignerException("Cannot load the keystore " + storeURI, e);
+ throw new JarSignerException("Cannot load the keystore "
+ + storeURI, e);
}
}
return keyStore;
Modified: harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/JSSigner.java
URL: http://svn.apache.org/viewvc/harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/JSSigner.java?view=diff&rev=486218&r1=486217&r2=486218
==============================================================================
--- harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/JSSigner.java (original)
+++ harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/JSSigner.java Tue Dec 12 08:34:58 2006
@@ -22,5 +22,8 @@
*/
public class JSSigner {
// TODO
+ public static void signJar(JSParameters param){
+ // TODO
+ }
}
Modified: harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/JSVerifier.java
URL: http://svn.apache.org/viewvc/harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/JSVerifier.java?view=diff&rev=486218&r1=486217&r2=486218
==============================================================================
--- harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/JSVerifier.java (original)
+++ harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/JSVerifier.java Tue Dec 12 08:34:58 2006
@@ -22,5 +22,8 @@
*/
public class JSVerifier {
// TODO
+ public static void verifyJar(JSParameters param){
+ // TODO
+ }
}
Modified: harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/Main.java
URL: http://svn.apache.org/viewvc/harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/Main.java?view=diff&rev=486218&r1=486217&r2=486218
==============================================================================
--- harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/Main.java (original)
+++ harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/Main.java Tue Dec 12 08:34:58 2006
@@ -18,6 +18,9 @@
package org.apache.harmony.tools.jarsigner;
import java.io.OutputStream;
+import java.util.logging.Handler;
+import java.util.logging.Logger;
+import java.util.logging.StreamHandler;
/**
@@ -26,28 +29,34 @@
*/
public class Main {
/**
- * Does the actual work on JAR signing and verification, based on the
- * parameter param. If something goes wrong an exception is thrown.
- *
- * @param param
- * @throws Exception
- */
- static void doWork(JSParameters param) throws Exception {
- // TODO
- }
-
- /**
* The main method to run from another program.
+ * Parses the arguments, and performs the actual work
+ * on JAR signing and verification.
+ * If something goes wrong an exception is thrown.
*
* @param args -
* command line with options.
*/
public static void run(String[] args, OutputStream out) throws Exception {
- // TODO
- if (out != System.out){
- UserInteractor.setOutputStream(out);
- }
+ // set up logging
+ Logger logger = Logger.getLogger(JSParameters.loggerName);
+ logger.setUseParentHandlers(false);
+ Handler handler = new StreamHandler(out, new JSLogFormatter());
+ logger.addHandler(handler);
+ // parse command line arguments
+ JSParameters param = ArgParser.parseArgs(args, null);
+ // print help if incorrect or no arguments
+ if (param == null) {
+ JSHelper.printHelp();
+ return;
+ }
+ // do the actual work
+ if (param.isVerify()) {
+ JSVerifier.verifyJar(param);
+ } else {
+ JSSigner.signJar(param);
+ }
}
@@ -61,8 +70,11 @@
try {
run(args, System.out);
} catch (Exception e) {
- // System.out.println("JarSigner error: " + e);
- e.printStackTrace();
+ System.out.print("JarSigner error: "
+ + e
+ + ((e.getCause() != null) ? ", caused by " + e.getCause()
+ : ""));
+ //e.printStackTrace();
}
}
Modified: harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/TimeStampGenerator.java
URL: http://svn.apache.org/viewvc/harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/TimeStampGenerator.java?view=diff&rev=486218&r1=486217&r2=486218
==============================================================================
--- harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/TimeStampGenerator.java (original)
+++ harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/TimeStampGenerator.java Tue Dec 12 08:34:58 2006
@@ -17,10 +17,194 @@
package org.apache.harmony.tools.jarsigner;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.math.BigInteger;
+import java.net.HttpURLConnection;
+import java.net.InetSocketAddress;
+import java.net.ProtocolException;
+import java.net.Proxy;
+import java.net.URI;
+import java.net.URL;
+import java.security.NoSuchAlgorithmException;
+import java.security.SecureRandom;
+
+import org.apache.harmony.security.pkcs7.ContentInfo;
+import org.apache.harmony.security.x509.AlgorithmIdentifier;
+import org.apache.harmony.security.x509.tsp.MessageImprint;
+import org.apache.harmony.security.x509.tsp.TimeStampReq;
+import org.apache.harmony.security.x509.tsp.TimeStampResp;
+
+
/**
* Class to generate time stamps.
*/
-public class TimeStampGenerator {
- // TODO
+class TimeStampGenerator {
+
+
+ /**
+ * Generates a time-stamp request, sends it to the TSA, gets the response,
+ * decodes it and returns the TimeStampToken.
+ *
+ * @param digest
+ * @param algID
+ * @param tsaURI
+ * @param proxyAddr
+ * @param proxyPort
+ * @param proxyType
+ * @return
+ * @throws NoSuchAlgorithmException
+ * @throws IOException
+ */
+ static ContentInfo genTimeStamp(byte[] digest, AlgorithmIdentifier algID,
+ URI tsaURI, String proxyAddr, int proxyPort, Proxy.Type proxyType)
+ throws NoSuchAlgorithmException, IOException {
+
+ String errMsgAddrUsing = tsaURI
+ + " using "
+ + ((proxyAddr == null) ? "direct connection (no proxy)"
+ : proxyType + " proxy " + proxyAddr + ":" + proxyPort);
+
+ // create the time-stamp request
+ byte[] timeStampReq = generateTimeStampReq(digest, algID);
+
+ // set up the connection to TSA server
+ HttpURLConnection conn;
+ InputStream in;
+ OutputStream out;
+ try {
+ conn = setConnection(tsaURI, proxyAddr, proxyPort, proxyType,
+ timeStampReq.length);
+ conn.connect();
+ in = conn.getInputStream();
+ out = conn.getOutputStream();
+ } catch (IOException e) {
+ String errMsg = "Cannot connect to " + errMsgAddrUsing;
+ throw (IOException) new IOException(errMsg).initCause(e);
+ }
+
+ // send the request
+ try {
+ out.write(timeStampReq);
+ out.flush();
+ out.close();
+ } catch (IOException e) {
+ String errMsg = "Cannot post the request to " + errMsgAddrUsing;
+ throw (IOException) new IOException(errMsg).initCause(e);
+ }
+
+ // get the response
+ // byte buffer to contain the response from TSA
+ byte[] respBytes;
+ // total response length
+ int respLen = 0;
+ try {
+ // Time-stamp response is usually less than 8 Kbytes.
+ respBytes = new byte[8092];
+ // try to read the answer in several packets
+
+ // length of the current chunk of data
+ int chunkLen = 0;
+ do {
+ int freeRespBytesSpace = respBytes.length - respLen;
+ chunkLen = in.read(respBytes, respLen, freeRespBytesSpace);
+ if (chunkLen > 0) {
+ respLen += chunkLen;
+
+ // if the respBytes buffer is full
+ if (chunkLen == freeRespBytesSpace) {
+ byte [] biggerBuffer = new byte [respBytes.length * 2];
+ System.arraycopy(respBytes, 0, biggerBuffer, 0,
+ respBytes.length);
+ respBytes = biggerBuffer;
+ }
+ }
+ } while (chunkLen > 0);
+ } catch (IOException e) {
+ String errMsg = "Cannot get response from " + errMsgAddrUsing;
+ throw (IOException) new IOException(errMsg).initCause(e);
+ }
+ conn.disconnect();
+
+ // return the decoded response or throw an IOException
+ return decodeResponse(respBytes, respLen);
+ }
+
+ // generates a TimeStampReq and returns its ASN1 DER encoding
+ private static byte[] generateTimeStampReq(byte[] digest,
+ AlgorithmIdentifier algID) throws NoSuchAlgorithmException {
+ MessageImprint msgImprint = new MessageImprint(algID, digest);
+ SecureRandom random;
+ String randAlgName = "SHA1PRNG";
+ try {
+ random = SecureRandom.getInstance(randAlgName);
+ } catch (NoSuchAlgorithmException e) {
+ throw new NoSuchAlgorithmException("The algorithm " + randAlgName
+ + " is not available in current environment.", e);
+ }
+ BigInteger nonce = BigInteger.valueOf(random.nextLong());
+ TimeStampReq req = new TimeStampReq(1, // version
+ msgImprint, // message imprint
+ null, // not asking for a particular policy
+ nonce, // nonce
+ Boolean.FALSE, // don't need the certificte inside the stamp
+ null); // no extensions
+ return req.getEncoded();
+ }
+
+ // Creates a connection and sets up its properties,
+ // returns the created connection.
+ private static HttpURLConnection setConnection(URI tsaURI,
+ String proxyAddr, int proxyPort, Proxy.Type proxyType,
+ int contentLength) throws IOException {
+
+ URL tsaURL = tsaURI.toURL();
+
+ // FIXME: if proxy is not set!
+ InetSocketAddress proxyInetAddr = new InetSocketAddress(proxyAddr,
+ proxyPort);
+ Proxy proxy = new Proxy(proxyType, proxyInetAddr);
+ HttpURLConnection conn = (HttpURLConnection) tsaURL
+ .openConnection(proxy);
+ conn.setDoOutput(true);
+ conn.setDoInput(true);
+ try {
+ conn.setRequestMethod("POST");
+ } catch (ProtocolException e) {
+ // The exception cannot be thrown as it is thrown only if:
+ // - the method is called after the connection is set,
+ // - POST is not supported.
+ throw new RuntimeException("\"POST\" is not supported by "
+ + "the HTTP protocol implementation");
+ }
+ conn.setRequestProperty("accept", "application/timestamp-reply");
+ conn.setRequestProperty("content-type", "application/timestamp-query");
+ conn.setRequestProperty("Content-Length",
+ new String("" + contentLength));
+ return conn;
+ }
+
+ // decodes the response from TSA
+ private static ContentInfo decodeResponse(byte[] respBytes, int respLen)
+ throws IOException {
+ try {
+ TimeStampResp resp = (TimeStampResp) TimeStampResp.ASN1.decode(
+ respBytes, 0, respLen);
+ return resp.getTimeStampToken();
+ } catch (IOException e) {
+ // If failed to decode the response as a TimeStampResp,
+ // try to decode it as a TimeStampToken because some TSA-s
+ // return the token (not TimeStampResp) on success in spite
+ // of this conflicts with the RFC 3161.
+ try {
+ return (ContentInfo) ContentInfo.ASN1.decode(respBytes, 0,
+ respLen);
+ } catch (IOException ioe) {
+ String errMsg = "Cannot parse the response from TSA";
+ throw (IOException) new IOException(errMsg).initCause(e);
+ }
+ }
+ }
}
Modified: harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/UserInteractor.java
URL: http://svn.apache.org/viewvc/harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/UserInteractor.java?view=diff&rev=486218&r1=486217&r2=486218
==============================================================================
--- harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/UserInteractor.java (original)
+++ harmony/enhanced/classlib/trunk/modules/tools/src/main/java/org/apache/harmony/tools/jarsigner/UserInteractor.java Tue Dec 12 08:34:58 2006
@@ -19,16 +19,12 @@
import java.io.IOException;
import java.io.InputStreamReader;
-import java.io.OutputStream;
-import java.util.logging.Level;
-import java.util.logging.Logger;
-import java.util.logging.StreamHandler;
/**
* Class to interact with user - ask for confirmations, and necessary parameters
* which haven't been set in the command line.
*/
-public class UserInteractor {
+class UserInteractor {
// used to get additional data prompted
private static InputStreamReader in = new InputStreamReader(System.in);
@@ -42,81 +38,14 @@
// when ENTER is pressed.
private static int newLineLength = 2;
- // an instance of Logger, used to manage message output
- private final static Logger logger = Logger.getLogger("JarSignerLogger");
-
- // log handler
- private static StreamHandler logHandler = new StreamHandler(System.out,
- new JSLogFormatter());
-
- static {
- // Do not send massages to another handlers.
- logger.setUseParentHandlers(false);
- // log to System.out by default.
- logger.addHandler(logHandler);
- }
-
// Prints prompt and waits the user to enter the needed data,
// tha data is returned.
static char[] getDataFromUser(String prompt) throws IOException {
- print(prompt);
+ System.out.println(prompt);
charsRead = in.read(readData);
char[] password = new char[charsRead - newLineLength];
System.arraycopy(readData, 0, password, 0, charsRead - newLineLength);
return password;
- }
-
- static void setOutputStream(OutputStream out) {
- logger.removeHandler(logHandler);
- // reuse the Formatter from old handler
- logHandler = new StreamHandler(out, logHandler.getFormatter());
- logger.addHandler(logHandler);
- }
-
- // prints the given message, if the output is not turned off with
- // setNoOutput()
- static void print(String msg) {
- logger.info(msg);
- logHandler.flush();
- }
-
- // prints the given message and a new line symbol, if the output is not
- // turned off with setNoOutput()
- static void println(String msg) {
- logger.info(msg + "\n");
- logHandler.flush();
- }
-
- // prints the given message, if verbose output is set with
- // setVerboseOutput()
- static void printIfVerbose(String msg) {
- logger.fine(msg);
- logHandler.flush();
- }
-
- // prints the given message and a new line symbol, if verbose output is set
- // with setVerboseOutput()
- static void printlnIfVerbose(String msg) {
- logger.fine(msg + "\n");
- logHandler.flush();
- }
-
- // turns off the output
- static void setNoOutput() {
- logger.setLevel(Level.OFF);
- logger.setLevel(Level.OFF);
- }
-
- // sets the verbose output
- static void setVerboseOutput() {
- logger.setLevel(Level.ALL);
- logHandler.setLevel(Level.ALL);
- }
-
- // sets the normal output
- static void setNormalOutput() {
- logger.setLevel(Level.INFO);
- logHandler.setLevel(Level.INFO);
}
}