--- opensc-0.9.6/src/tools/pkcs15-crypt.c	2005-04-14 12:02:05.000000000 +0300
+++ opensc-20050924/src/tools/pkcs15-crypt.c	2005-09-24 03:14:32.000000000 +0300
@@ -1,5 +1,5 @@
 /*
- * pkcs15-crypt.c: Tool for cryptography operations with SmartCards
+ * pkcs15-crypt.c: Tool for cryptography operations with smart cards
  *
  * Copyright (C) 2001  Juha Yrjölä <juha.yrjola@iki.fi>
  *
@@ -39,7 +39,7 @@
 
 const char *app_name = "pkcs15-crypt";
 
-int opt_reader = -1, verbose = 0, opt_wait = 0;
+int opt_reader = -1, verbose = 0, opt_wait = 0, opt_raw = 0;
 char * opt_pincode = NULL, * opt_key_id = NULL;
 char * opt_input = NULL, * opt_output = NULL;
 int opt_crypt_flags = 0;
@@ -57,6 +57,7 @@
 	{ "reader",		1, 0,		'r' },
 	{ "input",		1, 0,		'i' },
 	{ "output",		1, 0,		'o' },
+	{ "raw",		0, 0,		'R' },
 	{ "sha-1",		0, 0,		OPT_SHA1 },
 	{ "md5",		0, 0,		OPT_MD5 },
 	{ "pkcs1",		0, 0,		OPT_PKCS1 },
@@ -73,6 +74,7 @@
 	"Uses reader number <arg>",
 	"Selects the input file to use",
 	"Outputs to file <arg>",
+	"Outputs raw 8 bit data",
 	"Input file is a SHA-1 hash",
 	"Input file is a MD5 hash",
 	"Use PKCS #1 v1.5 padding",
@@ -81,11 +83,11 @@
 	"Verbose operation. Use several times to enable debug output.",
 };
 
-struct sc_context *ctx = NULL;
-struct sc_card *card = NULL;
+sc_context_t *ctx = NULL;
+sc_card_t *card = NULL;
 struct sc_pkcs15_card *p15card = NULL;
 
-char * get_pin(struct sc_pkcs15_object *obj)
+static char * get_pin(struct sc_pkcs15_object *obj)
 {
 	char buf[80];
 	char *pincode;
@@ -105,7 +107,7 @@
 	}
 }
 
-int read_input(u8 *buf, int buflen)
+static int read_input(u8 *buf, int buflen)
 {
 	FILE *inf;
 	int c;
@@ -124,10 +126,10 @@
 	return c;
 }
 
-int write_output(const u8 *buf, int len)
+static int write_output(const u8 *buf, int len)
 {
 	FILE *outf;
-	int output_binary = 1;
+	int output_binary = (opt_output == NULL && opt_raw == 0 ? 0 : 1);
 	
 	if (opt_output != NULL) {
 		outf = fopen(opt_output, "wb");
@@ -137,7 +139,6 @@
 		}
 	} else {
 		outf = stdout;
-		output_binary = 0;
 	}
 	if (output_binary == 0)
 		print_binary(outf, buf, len);
@@ -150,7 +151,7 @@
 
 #ifdef HAVE_OPENSSL
 #define GETBN(bn)	((bn)->len? BN_bin2bn((bn)->data, (bn)->len, NULL) : NULL)
-int extract_key(struct sc_pkcs15_object *obj, EVP_PKEY **pk)
+static int extract_key(struct sc_pkcs15_object *obj, EVP_PKEY **pk)
 {
 	struct sc_pkcs15_prkey	*key;
 	const char	*pass = NULL;
@@ -227,7 +228,7 @@
 	return r;
 }
 
-int sign_ext(struct sc_pkcs15_object *obj,
+static int sign_ext(struct sc_pkcs15_object *obj,
 		u8 *data, size_t len, u8 *out, size_t out_len)
 {
 	EVP_PKEY *pkey = NULL;
@@ -274,7 +275,7 @@
 }
 #endif
 
-int sign(struct sc_pkcs15_object *obj)
+static int sign(struct sc_pkcs15_object *obj)
 {
 	u8 buf[1024], out[1024];
 	struct sc_pkcs15_prkey_info *key = (struct sc_pkcs15_prkey_info *) obj->data;
@@ -284,19 +285,14 @@
 		fprintf(stderr, "No input file specified.\n");
 		return 2;
 	}
-#if 0
-	if (opt_output == NULL) {
-		fprintf(stderr, "No output file specified.\n");
-		return 2;
-	}
-#endif
+
 	c = read_input(buf, sizeof(buf));
 	if (c < 0)
 		return 2;
 	len = sizeof(out);
 	if (obj->type == SC_PKCS15_TYPE_PRKEY_RSA
 	 && !(opt_crypt_flags & SC_ALGORITHM_RSA_PAD_PKCS1)
-	 && c != key->modulus_length/8) {
+	 && (size_t)c != key->modulus_length/8) {
 		fprintf(stderr, "Input has to be exactly %d bytes, when using no padding.\n",
 			key->modulus_length/8);
 		return 2;
@@ -350,7 +346,7 @@
 }
 #endif
 
-int decipher(struct sc_pkcs15_object *obj)
+static int decipher(struct sc_pkcs15_object *obj)
 {
 	u8 buf[1024], out[1024];
 	int r, c, len;
@@ -432,11 +428,12 @@
 			return 0;
 
 		pincode = get_pin(pin);
-		if (pincode == NULL || *pincode == '\0')
-			return 5;
+		if (((pincode == NULL || *pincode == '\0')) &&
+		    !(p15card->card->slot->capabilities & SC_SLOT_CAP_PIN_PAD))
+				return 5;
 
 		r = sc_pkcs15_verify_pin(p15card, (struct sc_pkcs15_pin_info *) pin->data,
-					(const u8 *) pincode, strlen(pincode));
+				(const u8 *) pincode, pincode == NULL ? 0 : strlen(pincode));
 		if (r) {
 			fprintf(stderr, "PIN code verification failed: %s\n", sc_strerror(r));
 			return 5;
@@ -459,7 +456,7 @@
         struct sc_pkcs15_object *key;
 		
 	while (1) {
-		c = getopt_long(argc, argv, "sck:r:i:o:p:vw", options, &long_optind);
+		c = getopt_long(argc, argv, "sck:r:i:o:Rp:vw", options, &long_optind);
 		if (c == -1)
 			break;
 		if (c == '?')
@@ -486,6 +483,9 @@
 		case 'o':
 			opt_output = optarg;
 			break;
+		case 'R':
+			opt_raw = 1;
+			break;
 		case OPT_SHA1:
 			opt_crypt_flags |= SC_ALGORITHM_RSA_HASH_SHA1;
 			break;

