00001 /* 00002 * RSA/SHA-1 signature creation program 00003 * 00004 * Copyright (C) 2006-2007 Christophe Devine 00005 * 00006 * This program is free software; you can redistribute it and/or modify 00007 * it under the terms of the GNU General Public License as published by 00008 * the Free Software Foundation; either version 2 of the License, or 00009 * (at your option) any later version. 00010 * 00011 * This program is distributed in the hope that it will be useful, 00012 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00013 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00014 * GNU General Public License for more details. 00015 * 00016 * You should have received a copy of the GNU General Public License along 00017 * with this program; if not, write to the Free Software Foundation, Inc., 00018 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. 00019 */ 00020 00021 #ifndef _CRT_SECURE_NO_DEPRECATE 00022 #define _CRT_SECURE_NO_DEPRECATE 1 00023 #endif 00024 00025 #include <string.h> 00026 #include <stdio.h> 00027 00028 #include "xyssl/rsa.h" 00029 #include "xyssl/sha1.h" 00030 00031 int main( int argc, char *argv[] ) 00032 { 00033 FILE *f; 00034 int ret, i; 00035 rsa_context rsa; 00036 unsigned char hash[20]; 00037 unsigned char buf[512]; 00038 00039 ret = 1; 00040 00041 if( argc != 2 ) 00042 { 00043 printf( "usage: rsa_sign <filename>\n" ); 00044 00045 #ifdef WIN32 00046 printf( "\n" ); 00047 #endif 00048 00049 goto exit; 00050 } 00051 00052 printf( "\n . Reading private key from rsa_priv.txt" ); 00053 fflush( stdout ); 00054 00055 if( ( f = fopen( "rsa_priv.txt", "rb" ) ) == NULL ) 00056 { 00057 ret = 1; 00058 printf( " failed\n ! Could not open rsa_priv.txt\n" \ 00059 " ! Please run rsa_genkey first\n\n" ); 00060 goto exit; 00061 } 00062 00063 rsa_init( &rsa, RSA_PKCS_V15, 0, NULL, NULL ); 00064 00065 if( ( ret = mpi_read_file( &rsa.N , 16, f ) ) != 0 || 00066 ( ret = mpi_read_file( &rsa.E , 16, f ) ) != 0 || 00067 ( ret = mpi_read_file( &rsa.D , 16, f ) ) != 0 || 00068 ( ret = mpi_read_file( &rsa.P , 16, f ) ) != 0 || 00069 ( ret = mpi_read_file( &rsa.Q , 16, f ) ) != 0 || 00070 ( ret = mpi_read_file( &rsa.DP, 16, f ) ) != 0 || 00071 ( ret = mpi_read_file( &rsa.DQ, 16, f ) ) != 0 || 00072 ( ret = mpi_read_file( &rsa.QP, 16, f ) ) != 0 ) 00073 { 00074 printf( " failed\n ! mpi_read_file returned %d\n\n", ret ); 00075 goto exit; 00076 } 00077 00078 rsa.len = ( mpi_msb( &rsa.N ) + 7 ) >> 3; 00079 00080 fclose( f ); 00081 00082 /* 00083 * Compute the SHA-1 hash of the input file, 00084 * then calculate the RSA signature of the hash. 00085 */ 00086 printf( "\n . Generating the RSA/SHA-1 signature" ); 00087 fflush( stdout ); 00088 00089 if( ( ret = sha1_file( argv[1], hash ) ) != 0 ) 00090 { 00091 printf( " failed\n ! Could not open or read %s\n\n", argv[1] ); 00092 goto exit; 00093 } 00094 00095 if( ( ret = rsa_pkcs1_sign( &rsa, RSA_PRIVATE, RSA_SHA1, 00096 20, hash, buf ) ) != 0 ) 00097 { 00098 printf( " failed\n ! rsa_pkcs1_sign returned %d\n\n", ret ); 00099 goto exit; 00100 } 00101 00102 /* 00103 * Write the signature into <filename>-sig.txt 00104 */ 00105 memcpy( argv[1] + strlen( argv[1] ), ".sig", 5 ); 00106 00107 if( ( f = fopen( argv[1], "wb+" ) ) == NULL ) 00108 { 00109 ret = 1; 00110 printf( " failed\n ! Could not create %s\n\n", argv[1] ); 00111 goto exit; 00112 } 00113 00114 for( i = 0; i < rsa.len; i++ ) 00115 fprintf( f, "%02X%s", buf[i], 00116 ( i + 1 ) % 16 == 0 ? "\r\n" : " " ); 00117 00118 fclose( f ); 00119 00120 printf( "\n . Done (created \"%s\")\n\n", argv[1] ); 00121 00122 exit: 00123 00124 #ifdef WIN32 00125 printf( " + Press Enter to exit this program.\n" ); 00126 fflush( stdout ); getchar(); 00127 #endif 00128 00129 return( ret ); 00130 }