diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/Makefile ucspi-ssl-0.70/src/Makefile --- ucspi-ssl-0.70-ucspitls-0.1/src/Makefile 2005-07-18 02:59:02.000000000 +0300 +++ ucspi-ssl-0.70/src/Makefile 2007-09-13 14:14:52.323365195 +0300 @@ -5,10 +5,11 @@ SHELL=/bin/sh default: it clean: - rm -f alloc.o alloc_re.o auto-str auto-str.o auto_cadir.c auto_cadir.o \ + rm -f alloc_re.o auto-str auto-str.o auto_cadir.c auto_cadir.o \ auto_cafile.c auto_cafile.o auto_ccafile.c auto_ccafile.o \ - auto_certfile.c auto_certfile.o auto_ciphers.c auto_ciphers.o \ - auto_dhfile.c auto_dhfile.o auto_keyfile.c auto_keyfile.o buffer.o \ + auto_certfile.c auto_certfile.o auto_ciphers.c auto_crls.o \ + auto_dhfile.c auto_dhfile.o auto_keyfile.c auto_keyfile.o \ + auto_keyfile_ec.c auto_keyfile_ec.o buffer.o \ buffer_0.o buffer_1.o buffer_2.o buffer_copy.o buffer_get.o buffer_put.o \ buffer_read.o buffer_write.o byte_chr.o byte_copy.o byte_cr.o \ byte_diff.o byte_zero.o case_diffb.o case_diffs.o ccperl cdb.a cdb.o \ @@ -36,10 +37,7 @@ clean: tai_pack.o taia_add.o taia_approx.o taia_frac.o taia_less.o taia_now.o \ taia_pack.o taia_sub.o taia_uint.o timeoutconn.o uint16_pack.o \ uint16_unpack.o uint32.h uint32_pack.o uint32_unpack.o uint64.h unix.a \ - wait_nohang.o wait_pid.o - -alloc.o: compile alloc.c alloc.h error.h - ./compile alloc.c + wait_nohang.o wait_pid.o ssl_crls.o alloc_re.o: compile alloc_re.c alloc.h byte.h ./compile alloc_re.c @@ -80,6 +78,12 @@ auto_ciphers.c: auto-str conf-ciphers auto_ciphers.o: compile auto_ciphers.c ./compile auto_ciphers.c +auto_crls.c: auto-str conf-crls + ./auto-str auto_crls "`head -1 conf-crls`" > auto_crls.c + +auto_crls.o: compile auto_crls.c + ./compile auto_crls.c + auto_dhfile.c: auto-str conf-dhfile ./auto-str auto_dhfile "`head -1 conf-dhfile`" > auto_dhfile.c @@ -92,6 +96,12 @@ auto_keyfile.c: auto-str conf-keyfile auto_keyfile.o: compile auto_keyfile.c ./compile auto_keyfile.c +auto_keyfile_ec.c: auto-str conf-keyfile_ec + ./auto-str auto_keyfile_ec "`head -1 conf-keyfile_ec`" > auto_keyfile_ec.c + +auto_keyfile_ec.o: compile auto_keyfile_ec.c + ./compile auto_keyfile_ec.c + buffer.o: compile buffer.c buffer.h ./compile buffer.c @@ -310,7 +320,7 @@ ip4_fmt.o: compile ip4_fmt.c fmt.h ip4.h ip4_scan.o: compile ip4_scan.c scan.h ip4.h ./compile ip4_scan.c -it: it-base it-sslperl sysdeps +it: it-base sslperl sysdeps it-base: sslclient sslserver https@ sslcat sslconnect sslprint sysdeps @@ -443,10 +453,10 @@ socket_udp.o: compile socket_udp.c ndela ./compile socket_udp.c ssl.a: makelib ssl.o ssl_io.o ssl_context.o ssl_new.o ssl_timeoutconn.o \ -ssl_timeoutaccept.o ssl_certkey.o ssl_ca.o ssl_cca.o ssl_ciphers.o \ +ssl_timeoutaccept.o ssl_certkey.o ssl_ca.o ssl_cca.o ssl_ciphers.o ssl_crls.o \ ssl_verify.o ssl_params.o ssl_error.o ssl_env.o ./makelib ssl.a ssl.o ssl_io.o ssl_context.o ssl_new.o ssl_timeoutconn.o \ - ssl_timeoutaccept.o ssl_certkey.o ssl_ca.o ssl_cca.o ssl_ciphers.o \ + ssl_timeoutaccept.o ssl_certkey.o ssl_ca.o ssl_cca.o ssl_ciphers.o ssl_crls.o \ ssl_verify.o ssl_params.o ssl_error.o ssl_env.o ssl.o: compile ssl.c ssl.h stralloc.h gen_alloc.h @@ -464,6 +474,9 @@ ssl_certkey.o: compile ssl_certkey.c ssl ssl_ciphers.o: compile ssl_ciphers.c ssl.h stralloc.h gen_alloc.h ./compile ssl_ciphers.c +ssl_crls.o: compile ssl_crls.c ssl.h str.h stralloc.h gen_alloc.h case.h + ./compile ssl_crls.c + ssl_context.o: compile ssl_context.c ssl.h stralloc.h gen_alloc.h ./compile ssl_context.c @@ -504,14 +517,14 @@ sslcat: home warn-auto.sh sslcat.sh chmod 755 sslcat sslclient: load sslclient.o remoteinfo.o timeoutconn.o ssl.a unix.a \ -auto_cafile.o auto_cadir.o auto_ciphers.o socket.lib ssl.lib +auto_cafile.o auto_cadir.o auto_ciphers.o auto_crls.o socket.lib ssl.lib ./load sslclient remoteinfo.o timeoutconn.o ssl.a unix.a auto_cafile.o \ - auto_cadir.o auto_ciphers.o `cat socket.lib` `cat ssl.lib` + auto_cadir.o auto_ciphers.o auto_crls.o `cat socket.lib` `cat ssl.lib` sslclient.o: compile sslclient.c ssl.h sig.h exit.h sgetopt.h uint16.h \ fmt.h scan.h str.h ip4.h uint16.h socket.h fd.h stralloc.h buffer.h \ getln.h error.h strerr.h pathexec.h timeoutconn.h remoteinfo.h dns.h \ -auto_cafile.h auto_cadir.h auto_ciphers.h byte.h ndelay.h wait.h \ +auto_cafile.h auto_cadir.h auto_ciphers.h auto_crls.h byte.h ndelay.h wait.h \ stralloc.h subgetopt.h uint16.h gen_alloc.h buffer.h stralloc.h uint16.h \ stralloc.h uint16.h stralloc.h iopause.h taia.h gen_alloc.h gen_alloc.h \ gen_alloc.h gen_alloc.h taia.h tai.h tai.h uint64.h uint64.h @@ -529,7 +542,8 @@ sslhandle.o: compile sslhandle.c ssl.h u ip4.h fd.h exit.h env.h prot.h open.h wait.h stralloc.h alloc.h buffer.h \ getln.h error.h strerr.h sgetopt.h socket.h ndelay.h remoteinfo.h rules.h \ sig.h dns.h auto_cafile.h auto_cadir.h auto_ccafile.h auto_dhfile.h \ -auto_certfile.h auto_keyfile.h auto_ciphers.h iopause.h coe.h lock.h \ +auto_certfile.h auto_keyfile.h auto_keyfile_ec.h auto_ciphers.h auto_crls.h \ +iopause.h coe.h lock.h \ stralloc.h gen_alloc.h buffer.h stralloc.h subgetopt.h uint16.h \ stralloc.h uint16.h stralloc.h stralloc.h iopause.h taia.h taia.h \ gen_alloc.h gen_alloc.h gen_alloc.h gen_alloc.h gen_alloc.h taia.h tai.h \ @@ -537,11 +551,13 @@ tai.h tai.h uint64.h uint64.h uint64.h ./compile sslhandle.c sslperl: load sslperl.o auto_cafile.o auto_ccafile.o auto_cadir.o \ -auto_dhfile.o auto_certfile.o auto_keyfile.o auto_ciphers.o rules.o \ +auto_dhfile.o auto_certfile.o auto_keyfile.o auto_keyfile_ec.o auto_ciphers.o \ +auto_crls.o rules.o \ remoteinfo.o timeoutconn.o sslhandle.o cdb.a ssl.a unix.a cdb.a unix.a \ socket.lib ssl.lib socket.lib perlembed.lib ./load sslperl auto_cafile.o auto_ccafile.o auto_cadir.o auto_dhfile.o \ - auto_certfile.o auto_keyfile.o auto_ciphers.o rules.o remoteinfo.o \ + auto_certfile.o auto_keyfile.o auto_keyfile_ec.o auto_ciphers.o auto_crls.o \ + rules.o remoteinfo.o \ timeoutconn.o sslhandle.o cdb.a ssl.a unix.a cdb.a unix.a `cat \ socket.lib` `cat ssl.lib` `cat socket.lib` `cat perlembed.lib` @@ -549,11 +565,13 @@ sslperl.o: compile ccperl sslperl.c stre ./compile `cat ccperl` sslperl.c sslprint: load sslprint.o auto_cafile.o auto_ccafile.o auto_cadir.o \ -auto_dhfile.o auto_certfile.o auto_keyfile.o auto_ciphers.o rules.o \ +auto_dhfile.o auto_certfile.o auto_keyfile.o auto_keyfile_ec.o auto_ciphers.o \ +auto_crls.o rules.o \ remoteinfo.o timeoutconn.o sslhandle.o cdb.a ssl.a unix.a cdb.a unix.a \ socket.lib ssl.lib socket.lib ./load sslprint auto_cafile.o auto_ccafile.o auto_cadir.o auto_dhfile.o \ - auto_certfile.o auto_keyfile.o auto_ciphers.o rules.o remoteinfo.o \ + auto_certfile.o auto_keyfile.o auto_keyfile_ec.o auto_ciphers.o auto_crls.o \ + rules.o remoteinfo.o \ timeoutconn.o sslhandle.o cdb.a ssl.a unix.a cdb.a unix.a `cat \ socket.lib` `cat ssl.lib` `cat socket.lib` @@ -561,18 +579,19 @@ sslprint.o: compile sslprint.c buffer.h ./compile sslprint.c sslserver: load sslserver.o auto_cafile.o auto_ccafile.o auto_cadir.o \ -auto_dhfile.o auto_certfile.o auto_keyfile.o auto_ciphers.o rules.o \ -remoteinfo.o timeoutconn.o cdb.a ssl.a unix.a socket.lib ssl.lib +auto_dhfile.o auto_certfile.o auto_keyfile.o auto_keyfile_ec.o auto_ciphers.o \ +auto_crls.o rules.o remoteinfo.o timeoutconn.o cdb.a ssl.a unix.a socket.lib ssl.lib ./load sslserver auto_cafile.o auto_ccafile.o auto_cadir.o auto_dhfile.o \ - auto_certfile.o auto_keyfile.o auto_ciphers.o rules.o remoteinfo.o \ + auto_certfile.o auto_keyfile.o auto_keyfile_ec.o auto_ciphers.o auto_crls.o \ + rules.o remoteinfo.o \ timeoutconn.o cdb.a ssl.a unix.a `cat socket.lib` `cat ssl.lib` sslserver.o: compile sslserver.c ssl.h uint16.h str.h byte.h fmt.h scan.h \ ip4.h fd.h exit.h env.h prot.h open.h wait.h stralloc.h alloc.h buffer.h \ getln.h error.h strerr.h sgetopt.h pathexec.h socket.h ndelay.h \ remoteinfo.h rules.h sig.h dns.h auto_cafile.h auto_cadir.h \ -auto_ccafile.h auto_dhfile.h auto_certfile.h auto_keyfile.h \ -auto_ciphers.h stralloc.h gen_alloc.h buffer.h stralloc.h subgetopt.h \ +auto_ccafile.h auto_dhfile.h auto_certfile.h auto_keyfile.h auto_keyfile_ec.h \ +auto_ciphers.h auto_crls.h stralloc.h gen_alloc.h buffer.h stralloc.h subgetopt.h \ uint16.h stralloc.h uint16.h stralloc.h stralloc.h iopause.h taia.h \ gen_alloc.h gen_alloc.h gen_alloc.h gen_alloc.h gen_alloc.h taia.h tai.h \ tai.h uint64.h uint64.h @@ -692,7 +711,7 @@ uint32_unpack.o: compile uint32_unpack.c uint64.h: choose compile load tryulong64.c uint64.h1 uint64.h2 ./choose clr tryulong64 uint64.h1 uint64.h2 >uint64.h -unix.a: makelib alloc.o alloc_re.o buffer.o buffer_0.o buffer_1.o \ +unix.a: makelib alloc_re.o buffer.o buffer_0.o buffer_1.o \ buffer_2.o buffer_get.o buffer_put.o buffer_copy.o buffer_read.o \ buffer_write.o env.o error.o error_str.o fd_copy.o fd_move.o fmt_ulong.o \ getln.o getln2.o socket_accept.o socket_bind.o socket_conn.o \ @@ -712,7 +731,7 @@ taia_sub.o taia_uint.o dns_dfd.o dns_dom dns_ipq.o dns_name.o dns_nd.o dns_packet.o dns_random.o dns_rcip.o \ dns_rcrw.o dns_resolve.o dns_sortip.o dns_transmit.o dns_txt.o lock_ex.o \ lock_un.o coe.o - ./makelib unix.a alloc.o alloc_re.o buffer.o buffer_0.o buffer_1.o \ + ./makelib unix.a alloc_re.o buffer.o buffer_0.o buffer_1.o \ buffer_2.o buffer_get.o buffer_put.o buffer_copy.o buffer_read.o \ buffer_write.o env.o error.o error_str.o fd_copy.o fd_move.o fmt_ulong.o \ getln.o getln2.o socket_accept.o socket_bind.o socket_conn.o \ diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/alloc.h ucspi-ssl-0.70/src/alloc.h --- ucspi-ssl-0.70-ucspitls-0.1/src/alloc.h 2005-07-18 02:59:02.000000000 +0300 +++ ucspi-ssl-0.70/src/alloc.h 2006-05-01 00:30:26.521124000 +0300 @@ -1,10 +1,24 @@ -/* Public domain. */ - #ifndef ALLOC_H #define ALLOC_H -extern /*@null@*//*@out@*/char *alloc(unsigned int); -extern void alloc_free(char *); -extern int alloc_re(char **,unsigned int,unsigned int); +#include +#include "error.h" + +static inline /*@null@*//*@out@*/char *alloc(n) +unsigned int n; +{ + char *x; + x = malloc(n); + if (!x) errno = error_nomem; + return x; +} + +static inline void alloc_free(x) +char *x; +{ + free(x); +} + +extern int alloc_re(char **, unsigned int, unsigned int); #endif diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/auto-str.c ucspi-ssl-0.70/src/auto-str.c --- ucspi-ssl-0.70-ucspitls-0.1/src/auto-str.c 2005-07-18 02:59:02.000000000 +0300 +++ ucspi-ssl-0.70/src/auto-str.c 2005-09-18 13:46:57.482913000 +0300 @@ -4,7 +4,7 @@ char bspace[256]; buffer b = BUFFER_INIT(buffer_unixwrite,1,bspace,sizeof bspace); -void puts(const char *s) +void putsx(const char *s) { if (buffer_puts(&b,s) == -1) _exit(111); } @@ -21,20 +21,20 @@ int main(int argc,char **argv) value = argv[2]; if (!value) _exit(100); - puts("const char "); - puts(name); - puts("[] = \"\\\n"); + putsx("const char "); + putsx(name); + putsx("[] = \"\\\n"); while (ch = *value++) { - puts("\\"); + putsx("\\"); octal[3] = 0; octal[2] = '0' + (ch & 7); ch >>= 3; octal[1] = '0' + (ch & 7); ch >>= 3; octal[0] = '0' + (ch & 7); - puts(octal); + putsx(octal); } - puts("\\\n\";\n"); + putsx("\\\n\";\n"); if (buffer_flush(&b) == -1) _exit(111); _exit(0); } diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/auto_crls.h ucspi-ssl-0.70/src/auto_crls.h --- ucspi-ssl-0.70-ucspitls-0.1/src/auto_crls.h 1970-01-01 02:00:00.000000000 +0200 +++ ucspi-ssl-0.70/src/auto_crls.h 2005-09-17 20:46:06.297460000 +0300 @@ -0,0 +1,7 @@ +#ifndef _AUTO_CRLS_H_ +#define _AUTO_CRLS_H_ + +extern const char auto_crls[]; + +#endif + diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/auto_keyfile_ec.h ucspi-ssl-0.70/src/auto_keyfile_ec.h --- ucspi-ssl-0.70-ucspitls-0.1/src/auto_keyfile_ec.h 1970-01-01 02:00:00.000000000 +0200 +++ ucspi-ssl-0.70/src/auto_keyfile_ec.h 2007-01-31 15:36:09.159303582 +0200 @@ -0,0 +1,6 @@ +#ifndef AUTO_KEYFILE_EC_H +#define AUTO_KEYFILE_EC_H + +extern const char auto_keyfile_ec[]; + +#endif diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/byte.h ucspi-ssl-0.70/src/byte.h --- ucspi-ssl-0.70-ucspitls-0.1/src/byte.h 2005-07-18 02:59:02.000000000 +0300 +++ ucspi-ssl-0.70/src/byte.h 2006-05-01 00:26:56.051581000 +0300 @@ -1,14 +1,12 @@ -/* Public domain. */ - #ifndef BYTE_H #define BYTE_H -extern unsigned int byte_chr(); -extern unsigned int byte_rchr(); -extern void byte_copy(); -extern void byte_copyr(); -extern int byte_diff(); -extern void byte_zero(); +extern unsigned int byte_chr(char *, unsigned int, int); +extern unsigned int byte_rchr(char *, unsigned int, int); +extern void byte_copy(char *, unsigned int, char *); +extern void byte_copyr(char *, unsigned int, char *); +extern int byte_diff(char *, unsigned int, char *); +extern void byte_zero(char *, unsigned int); #define byte_equal(s,n,t) (!byte_diff((s),(n),(t))) diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/cdb.h ucspi-ssl-0.70/src/cdb.h --- ucspi-ssl-0.70-ucspitls-0.1/src/cdb.h 2005-07-18 02:59:02.000000000 +0300 +++ ucspi-ssl-0.70/src/cdb.h 2005-09-18 13:07:29.587749000 +0300 @@ -6,8 +6,7 @@ #include "uint32.h" #define CDB_HASHSTART 5381 -extern uint32 cdb_hashadd(uint32,unsigned char); -extern uint32 cdb_hash(const char *,unsigned int); +extern uint32 cdb_hash(unsigned char *,unsigned int); struct cdb { char *map; /* 0 if no map is available */ diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/cdb_hash.c ucspi-ssl-0.70/src/cdb_hash.c --- ucspi-ssl-0.70-ucspitls-0.1/src/cdb_hash.c 2005-07-18 02:59:02.000000000 +0300 +++ ucspi-ssl-0.70/src/cdb_hash.c 2007-02-22 14:36:03.703064872 +0200 @@ -2,20 +2,64 @@ #include "cdb.h" -uint32 cdb_hashadd(uint32 h,unsigned char c) -{ - h += (h << 5); - return h ^ c; +#define ROTATE(v,n) (((v) << (n)) | ((v) >> (32 - (n)))) +#define XOR(v,w) ((v) ^ (w)) +#define PLUS(v,w) (((v) + (w))) + +#define mix(a, b, c) \ +{ \ + a = XOR(a,ROTATE(PLUS(b, c), 7)); \ + b = XOR(b,ROTATE(PLUS(a, c), 9)); \ + c = XOR(c,ROTATE(PLUS(a, b), 13)); \ + \ + a = XOR(a,ROTATE(PLUS(b, c), 18)); \ + b = XOR(b,ROTATE(PLUS(a, c), 25)); \ + c = XOR(c,ROTATE(PLUS(a, b), 7)); \ + \ + a = XOR(a,ROTATE(PLUS(b, c), 9)); \ + b = XOR(b,ROTATE(PLUS(a, c), 13)); \ + c = XOR(c,ROTATE(PLUS(a, b), 18)); \ } -uint32 cdb_hash(const char *buf,unsigned int len) +uint32 cdb_hash(k,length) +unsigned char *k; +unsigned int length; { - uint32 h; + uint32 a, b, c = 0xdeadbeef, len; + + len = length; + a = b = 0x9e3779b9; /* the golden ratio; an arbitrary value */ - h = CDB_HASHSTART; - while (len) { - h = cdb_hashadd(h,*buf++); - --len; + /*---------------------------------------- handle most of the key */ + while (len >= 12) + { + a += (k[0] +((uint32)k[1]<<8) +((uint32)k[2]<<16) +((uint32)k[3]<<24)); + b += (k[4] +((uint32)k[5]<<8) +((uint32)k[6]<<16) +((uint32)k[7]<<24)); + c += (k[8] +((uint32)k[9]<<8) +((uint32)k[10]<<16)+((uint32)k[11]<<24)); + mix(a,b,c); + k += 12; len -= 12; } - return h; + + /*------------------------------------- handle the last 11 bytes */ + c += length; + switch(len) /* all the case statements fall through */ + { + case 11: c+=((uint32)k[10]<<24); + case 10: c+=((uint32)k[9]<<16); + case 9 : c+=((uint32)k[8]<<8); + /* the first byte of c is reserved for the length */ + case 8 : b+=((uint32)k[7]<<24); + case 7 : b+=((uint32)k[6]<<16); + case 6 : b+=((uint32)k[5]<<8); + case 5 : b+=k[4]; + case 4 : a+=((uint32)k[3]<<24); + case 3 : a+=((uint32)k[2]<<16); + case 2 : a+=((uint32)k[1]<<8); + case 1 : a+=k[0]; + /* case 0: nothing left to add */ + } + mix(a,b,c); + /*-------------------------------------------- report the result */ + return c; } + diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/conf-cadir ucspi-ssl-0.70/src/conf-cadir --- ucspi-ssl-0.70-ucspitls-0.1/src/conf-cadir 2005-07-18 02:59:02.000000000 +0300 +++ ucspi-ssl-0.70/src/conf-cadir 2005-09-17 21:47:39.034799000 +0300 @@ -1,4 +1,4 @@ -/usr/local/ssl/certs + This is the ucspi-ssl CA directory. An empty name means no certificate directory is compiled in. diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/conf-cc ucspi-ssl-0.70/src/conf-cc --- ucspi-ssl-0.70-ucspitls-0.1/src/conf-cc 2005-07-18 02:59:02.000000000 +0300 +++ ucspi-ssl-0.70/src/conf-cc 2008-05-18 01:55:52.230422684 +0300 @@ -1,3 +1,3 @@ -auto +/usr/bin/x86_64-redhat-linux-gcc -O2 -m64 -fstack-protector -std=gnu99 -fno-omit-frame-pointer -fPIC -pipe -g0 This will be used to compile .c files. diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/conf-crls ucspi-ssl-0.70/src/conf-crls --- ucspi-ssl-0.70-ucspitls-0.1/src/conf-crls 1970-01-01 02:00:00.000000000 +0200 +++ ucspi-ssl-0.70/src/conf-crls 2005-09-17 22:05:07.865352000 +0300 @@ -0,0 +1,2 @@ + +No default CRL dir. diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/conf-keyfile_ec ucspi-ssl-0.70/src/conf-keyfile_ec --- ucspi-ssl-0.70-ucspitls-0.1/src/conf-keyfile_ec 1970-01-01 02:00:00.000000000 +0200 +++ ucspi-ssl-0.70/src/conf-keyfile_ec 2007-01-31 15:26:33.197784753 +0200 @@ -0,0 +1,3 @@ + +This is the sslserver key file. +An empty name means no key file is compiled in. diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/conf-ld ucspi-ssl-0.70/src/conf-ld --- ucspi-ssl-0.70-ucspitls-0.1/src/conf-ld 2005-07-18 02:59:02.000000000 +0300 +++ ucspi-ssl-0.70/src/conf-ld 2008-05-18 01:55:59.571422787 +0300 @@ -1,3 +1,3 @@ -gcc -s +/usr/bin/x86_64-redhat-linux-gcc -m64 -ljemalloc This will be used to link .o files into an executable. diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/open.h ucspi-ssl-0.70/src/open.h --- ucspi-ssl-0.70-ucspitls-0.1/src/open.h 2005-07-18 02:59:02.000000000 +0300 +++ ucspi-ssl-0.70/src/open.h 2008-05-18 01:52:27.156425111 +0300 @@ -3,7 +3,16 @@ #ifndef OPEN_H #define OPEN_H +#include +#include +#include + +#ifndef O_CLOEXEC +#define O_CLOEXEC (0) +#endif + extern int open_read(const char *); +extern int open_read_cloexec(const char *); extern int open_excl(const char *); extern int open_append(const char *); extern int open_trunc(const char *); diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/open_read.c ucspi-ssl-0.70/src/open_read.c --- ucspi-ssl-0.70-ucspitls-0.1/src/open_read.c 2005-07-18 02:59:02.000000000 +0300 +++ ucspi-ssl-0.70/src/open_read.c 2008-05-18 01:47:45.717423443 +0300 @@ -2,7 +2,12 @@ #include #include +#include + #include "open.h" int open_read(const char *fn) { return open(fn,O_RDONLY | O_NDELAY); } + +int open_read_cloexec(const char *fn) +{ return open(fn,O_RDONLY | O_NDELAY | O_CLOEXEC); } diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/prot.c ucspi-ssl-0.70/src/prot.c --- ucspi-ssl-0.70-ucspitls-0.1/src/prot.c 2005-07-18 02:59:02.000000000 +0300 +++ ucspi-ssl-0.70/src/prot.c 2005-09-17 21:00:00.168986000 +0300 @@ -3,6 +3,7 @@ #include #include #include +#include #include "hasshsgr.h" #include "prot.h" diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/ssl.h ucspi-ssl-0.70/src/ssl.h --- ucspi-ssl-0.70-ucspitls-0.1/src/ssl.h 2005-09-18 13:36:31.536878000 +0300 +++ ucspi-ssl-0.70/src/ssl.h 2007-01-31 23:01:11.873043580 +0200 @@ -12,12 +12,14 @@ extern SSL_CTX *ssl_context(SSL_METHOD * extern int ssl_timeoutconn(SSL *,unsigned int); extern int ssl_timeoutaccept(SSL *,unsigned int); extern SSL *ssl_new(SSL_CTX *,int); -extern int ssl_certkey(SSL_CTX *,const char *,const char *,pem_password_cb *); -extern int ssl_ca(SSL_CTX *,const char *,const char *,int); +extern int ssl_certkey(SSL_CTX *,const char *,const char*, + const char *, const char *, pem_password_cb *); +extern int ssl_ca(SSL_CTX *,const char *,const char *,int,int); extern int ssl_cca(SSL_CTX *,const char *); extern int ssl_ciphers(SSL_CTX *,const char *); +extern int ssl_crls(SSL_CTX *,const char*); extern int ssl_verify(SSL *,const char *); -extern int ssl_params(SSL_CTX *,const char *,int); +extern int ssl_params(SSL_CTX *,const char *,int,int); extern int ssl_server_env(SSL *,stralloc *); extern int ssl_client_env(SSL *,stralloc *); extern char *ssl_error_str(int); diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/ssl.lib ucspi-ssl-0.70/src/ssl.lib --- ucspi-ssl-0.70-ucspitls-0.1/src/ssl.lib 2005-07-18 02:59:02.000000000 +0300 +++ ucspi-ssl-0.70/src/ssl.lib 2007-03-11 17:31:16.618715525 +0200 @@ -1 +1 @@ --lssl -lcrypto +-lssl -lcrypto -ldl diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/ssl_ca.c ucspi-ssl-0.70/src/ssl_ca.c --- ucspi-ssl-0.70-ucspitls-0.1/src/ssl_ca.c 2005-07-18 02:59:02.000000000 +0300 +++ ucspi-ssl-0.70/src/ssl_ca.c 2005-09-18 16:46:39.811195000 +0300 @@ -1,12 +1,21 @@ #include #include "ssl.h" -int ssl_ca(SSL_CTX *ctx,const char *certfile,const char *certdir,int d) +static int verify_cb(int preverify_ok, X509_STORE_CTX *ctx) +{ + return 1; +} + +int ssl_ca(SSL_CTX *ctx,const char *certfile,const char *certdir,int d, int vfy) { if (!SSL_CTX_load_verify_locations(ctx,certfile,certdir)) return 0; SSL_CTX_set_verify_depth(ctx,d); + if (vfy) { + SSL_CTX_set_verify(ctx, (SSL_VERIFY_PEER | SSL_VERIFY_CLIENT_ONCE), verify_cb); + } + return 1; } diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/ssl_certkey.c ucspi-ssl-0.70/src/ssl_certkey.c --- ucspi-ssl-0.70-ucspitls-0.1/src/ssl_certkey.c 2005-07-18 02:59:02.000000000 +0300 +++ ucspi-ssl-0.70/src/ssl_certkey.c 2007-01-31 23:01:00.602014036 +0200 @@ -1,20 +1,29 @@ #include #include "ssl.h" -int ssl_certkey(SSL_CTX *ctx,const char *certfile,const char *keyfile,pem_password_cb *passwd_cb) +int ssl_certkey(SSL_CTX *ctx,const char *certfile, const char *certfileec, + const char *keyfile, const char *keyfileec, pem_password_cb *passwd_cb) { if (!certfile) return 0; + SSL_CTX_set_default_passwd_cb(ctx,passwd_cb); + if (SSL_CTX_use_certificate_chain_file(ctx,certfile) != 1) return -1; + if (keyfile) { + if (SSL_CTX_use_PrivateKey_file(ctx,keyfile,SSL_FILETYPE_PEM) != 1) + return -2; + } - if (!keyfile) keyfile = certfile; - SSL_CTX_set_default_passwd_cb(ctx,passwd_cb); - if (SSL_CTX_use_RSAPrivateKey_file(ctx,keyfile,SSL_FILETYPE_PEM) != 1) - return -2; + if (SSL_CTX_use_certificate_chain_file(ctx,certfileec) != 1) + return -3; + if (keyfileec) { + if (SSL_CTX_use_PrivateKey_file(ctx,keyfileec,SSL_FILETYPE_PEM) != 1) + return -4; + } if (SSL_CTX_check_private_key(ctx) != 1) - return -3; + return -5; return 0; } diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/ssl_crls.c ucspi-ssl-0.70/src/ssl_crls.c --- ucspi-ssl-0.70-ucspitls-0.1/src/ssl_crls.c 1970-01-01 02:00:00.000000000 +0200 +++ ucspi-ssl-0.70/src/ssl_crls.c 2005-09-18 13:45:26.450904000 +0300 @@ -0,0 +1,49 @@ +#include +#include +#include +#include "stralloc.h" +#include "str.h" +#include "ssl.h" +#include "case.h" + +int ssl_crls(SSL_CTX *ctx, const char *crldir) +{ + X509_STORE *store; + X509_LOOKUP *x509lookup; + DIR *dip; + struct dirent *dire; + static stralloc dirstr = {0}; + + if (!crldir) return 1; + dip = opendir(crldir); + if (!dip) return 0; + + store = SSL_CTX_get_cert_store(ctx); + x509lookup = X509_STORE_add_lookup(store, X509_LOOKUP_file()); + if (x509lookup) { + const char *fn; + int fnlen; + int ok = 0; + + while ((dire = readdir(dip))) { + fn = dire->d_name; + fnlen = str_len(fn); + + if (!stralloc_copys(&dirstr, crldir)) return 0; + if (!stralloc_cats(&dirstr, "/")) return 0; + if (!stralloc_cats(&dirstr, fn)) return 0; + if (!stralloc_0(&dirstr)) return 0; + if ((fnlen > 4) && (!case_diffb(fn+fnlen-4, 4, ".pem"))) { + if (X509_load_crl_file(x509lookup, dirstr.s, X509_FILETYPE_PEM) == 1) ok++; + } + } + closedir(dip); + if (ok > 0) { + X509_STORE_set_flags(store, (X509_V_FLAG_CRL_CHECK | X509_V_FLAG_CRL_CHECK_ALL) ); + return 1; + } + } + closedir(dip); + return 0; +} + diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/ssl_io.c ucspi-ssl-0.70/src/ssl_io.c --- ucspi-ssl-0.70-ucspitls-0.1/src/ssl_io.c 2005-07-18 02:59:02.000000000 +0300 +++ ucspi-ssl-0.70/src/ssl_io.c 2008-09-14 00:10:39.433597893 +0300 @@ -1,5 +1,6 @@ #include #include +#include #include #include #include "iopause.h" @@ -27,16 +28,16 @@ int ssl_io(SSL *ssl,int fdleft,int fdrig iopause_fd *ioleft; iopause_fd *io1; iopause_fd *ioright; - int r; + int r, r2, r3; int rfd; int wfd; - rfd = SSL_get_fd(ssl); /* XXX */ + rfd = SSL_get_rfd(ssl); if (rfd == -1) { close(fdleft); close(fdright); return -1; } - wfd = SSL_get_fd(ssl); /* XXX */ + wfd = SSL_get_wfd(ssl); if (wfd == -1) { close(fdleft); close(fdright); return -1; @@ -77,10 +78,12 @@ int ssl_io(SSL *ssl,int fdleft,int fdrig taia_now(&now); taia_uint(&deadline,timeout); taia_add(&deadline,&now,&deadline); + iopause(x,xlen,&deadline,&now); for (r = 0;r < xlen;++r) - if (x[r].revents) goto events; - + if (x[r].revents) + goto events; + if (io0 && !ssl_pending(ssl)) { close(fdleft); leftstatus = -1; @@ -91,6 +94,7 @@ int ssl_io(SSL *ssl,int fdleft,int fdrig events: if (io0 && io0->revents) { + errno = 0; r = SSL_read(ssl,leftbuf,sizeof leftbuf); ssl_errno = SSL_get_error(ssl,r); switch (ssl_errno) { @@ -103,6 +107,7 @@ events: case SSL_ERROR_WANT_WRITE: case SSL_ERROR_WANT_X509_LOOKUP: break; + case SSL_ERROR_SSL: case SSL_ERROR_ZERO_RETURN: if (rightstatus == -1) goto done; close(fdleft); @@ -114,11 +119,7 @@ events: leftstatus = -1; if (!errno) break; /* premature close */ - if (errno == error_connreset && rightstatus == -1) goto done; - goto bomb; - case SSL_ERROR_SSL: - if (errno == error_again || errno == error_intr) break; - if (!errno) break; + if (errno == error_connreset && rightstatus == -1) goto done; goto bomb; default: close(fdleft); @@ -130,6 +131,7 @@ events: } if (ioleft && ioleft->revents) { + errno = 0; r = buffer_unixwrite(fdleft,leftbuf + leftpos,leftlen - leftpos); if (r == -1) { if (errno == error_again || errno == error_intr || errno == error_wouldblock) { @@ -147,10 +149,11 @@ events: leftpos += r; if (leftpos == leftlen) { leftstatus = 0; - if (r = ssl_pending(ssl)) { + if ((r = ssl_pending(ssl))) { if (r > sizeof leftbuf) r = sizeof leftbuf; + errno = 0; r = SSL_read(ssl,leftbuf,r); - ssl_errno = SSL_get_error(ssl,r); + ssl_errno = SSL_get_error(ssl,r); switch(ssl_errno) { case SSL_ERROR_NONE: leftstatus = 1; @@ -175,6 +178,7 @@ events: } if (ioright && ioright->revents) { + errno = 0; r = buffer_unixread(fdright,rightbuf,sizeof rightbuf); if (r == -1) { if (errno == error_again || errno == error_intr || errno == error_wouldblock) { @@ -197,6 +201,7 @@ events: } if (io1 && io1->revents) { + errno = 0; r = SSL_write(ssl,rightbuf + rightpos,rightlen - rightpos); ssl_errno = SSL_get_error(ssl,r); switch (ssl_errno) { @@ -240,10 +245,28 @@ bomb: return -1; done: + r = errno; if (!ssl_shutdown_sent(ssl)) ssl_shutdown(ssl); if (!ssl_shutdown_pending(ssl)) ssl_shutdown(ssl); - shutdown(wfd,2); + while ((r2 = ssl_shutdown(ssl)) == -1) { + int maxloops = 10; + + if (maxloops-- == 0) break; + r3 = SSL_get_error(ssl, r2); + if ((r3 == SSL_ERROR_WANT_READ) || (r3 == SSL_ERROR_WANT_WRITE)) { + usleep(100000); + continue; + } + break; + } + switch (r2) { + case -1: usleep (1111); break; + case 0: usleep (2222); break; + case 1: usleep (3333); shutdown(wfd,2); break; + } if (leftstatus != -1) close(fdleft); if (rightstatus != -1) close(fdright); + errno = r; return 0; } + diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/ssl_params.c ucspi-ssl-0.70/src/ssl_params.c --- ucspi-ssl-0.70-ucspitls-0.1/src/ssl_params.c 2005-07-18 02:59:02.000000000 +0300 +++ ucspi-ssl-0.70/src/ssl_params.c 2007-01-31 15:01:46.265104134 +0200 @@ -1,14 +1,14 @@ #include #include "ssl.h" -int ssl_params(SSL_CTX *ctx,const char *dhfile,int len) +int ssl_params(SSL_CTX *ctx,const char *dhfile,int rsalen, int eclen) { DH *dh; RSA *rsa; BIO *bio; + EC_KEY *ecdh; if (dhfile) { - dh = 0; bio = BIO_new_file(dhfile,"r"); if (!bio) return 0; dh = PEM_read_bio_DHparams(bio,0,0,0); @@ -17,12 +17,39 @@ int ssl_params(SSL_CTX *ctx,const char * if (!SSL_CTX_set_tmp_dh(ctx,dh)) return 0; } - if (len) { - rsa = RSA_generate_key(len,RSA_F4,0,0); + if (rsalen) { + rsa = RSA_generate_key(rsalen,RSA_F4,0,0); if (!rsa) return 0; if (!SSL_CTX_set_tmp_rsa(ctx,rsa)) return 0; } + if (eclen) { + switch (eclen) { + case 163: + ecdh = EC_KEY_new_by_curve_name(OBJ_sn2nid("sect163r2")); + break; + case 193: + ecdh = EC_KEY_new_by_curve_name(OBJ_sn2nid("sect193r2")); + break; + case 283: + ecdh = EC_KEY_new_by_curve_name(OBJ_sn2nid("sect283k1")); + break; + case 409: + ecdh = EC_KEY_new_by_curve_name(OBJ_sn2nid("sect409k1")); + break; + case 571: + ecdh = EC_KEY_new_by_curve_name(OBJ_sn2nid("sect571k1")); + break; + default: + return 0; + } + + if (!ecdh) return 0; + if (!SSL_CTX_set_tmp_ecdh(ctx,ecdh)) return 0; + SSL_CTX_set_options(ctx, SSL_OP_SINGLE_ECDH_USE); + EC_KEY_free(ecdh); + } + return 1; } diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/ssl_verify.c ucspi-ssl-0.70/src/ssl_verify.c --- ucspi-ssl-0.70-ucspitls-0.1/src/ssl_verify.c 2005-07-18 02:59:02.000000000 +0300 +++ ucspi-ssl-0.70/src/ssl_verify.c 2007-01-31 15:54:02.515787159 +0200 @@ -7,11 +7,19 @@ int ssl_verify(SSL *ssl,const char *host { X509 *cert; char buf[SSL_NAME_LEN]; + int ret; - if (SSL_get_verify_result(ssl) != X509_V_OK) return -1; + ret = SSL_get_verify_result(ssl); + if (ret != X509_V_OK) { + ssl_errno = SSL_get_error(ssl, ret); + return -1; + } cert = SSL_get_peer_certificate(ssl); - if (!cert) return -2; + if (!cert) { + ssl_errno = SSL_get_error(ssl, ret); + return -2; + } X509_NAME_get_text_by_NID(X509_get_subject_name(cert),NID_commonName,buf,sizeof buf); diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/sslclient.c ucspi-ssl-0.70/src/sslclient.c --- ucspi-ssl-0.70-ucspitls-0.1/src/sslclient.c 2005-07-18 02:59:02.000000000 +0300 +++ ucspi-ssl-0.70/src/sslclient.c 2007-01-31 23:03:20.911932378 +0200 @@ -58,6 +58,7 @@ void usage(void) { [ -A cadir ] \ [ -c certfile ] \ [ -C ciphers ] \ +[ -z crldir ] \ [ -k keyfile ] \ [ -V verifydepth ] \ [ -w progtimeout ] \ @@ -101,9 +102,11 @@ buffer b; SSL_CTX *ctx; const char *certfile = 0; const char *keyfile = 0; +const char *keyfileec = 0; const char *cafile = auto_cafile; const char *cadir = auto_cadir; const char *ciphers = auto_ciphers; +const char *crldir = 0; stralloc password = {0}; int match = 0; int verifydepth = 1; @@ -145,7 +148,7 @@ int main(int argc,char * const *argv) { close(6); close(7); sig_ignore(sig_pipe); - + while ((opt = getopt(argc,argv,"dDvqQhHrRi:p:t:T:l:a:A:c:C:k:V:3eEsSnN0xXw:")) != opteof) switch(opt) { case 'd': flagdelay = 1; break; @@ -170,7 +173,9 @@ int main(int argc,char * const *argv) { case 'A': cadir = optarg; break; case 'c': certfile = optarg; break; case 'C': ciphers = optarg; break; + case 'z': crldir = optarg; break; case 'k': keyfile = optarg; break; + case 'K': keyfileec = optarg; break; case 'V': scan_ulong(optarg,&u); verifydepth = u; break; case '3': flag3 = 1; break; case 'S': flagsslenv = 0; break; @@ -210,9 +215,11 @@ int main(int argc,char * const *argv) { if (cafile && str_equal(cafile,"")) cafile = 0; if (cadir && str_equal(cadir,"")) cadir= 0; if (ciphers && str_equal(ciphers,"")) ciphers= 0; + if (crldir && str_equal(crldir,"")) crldir = 0; if (certfile && str_equal(certfile,"")) certfile = 0; if (keyfile && str_equal(keyfile,"")) keyfile = 0; + if (keyfileec && str_equal(keyfileec,"")) keyfileec = 0; if (!*++argv) usage(); @@ -311,19 +318,22 @@ int main(int argc,char * const *argv) { if (!ctx) strerr_die2x(111,FATAL,"unable to create SSL context"); - switch (ssl_certkey(ctx,certfile,keyfile,passwd_cb)) { + switch (ssl_certkey(ctx,certfile,0 /* XXX */, keyfile,keyfileec,passwd_cb)) { case -1: strerr_die2x(111,FATAL,"unable to load certificate"); case -2: strerr_die2x(111,FATAL,"unable to load key pair"); case -3: strerr_die2x(111,FATAL,"key does not match certificate"); default: break; } - if (!ssl_ca(ctx,cafile,cadir,verifydepth)) + if (!ssl_ca(ctx,cafile,cadir,verifydepth,0)) strerr_die2x(111,FATAL,"unable to load CA list"); if (!ssl_ciphers(ctx,ciphers)) strerr_die2x(111,FATAL,"unable to set cipher list"); + if (!ssl_crls(ctx,crldir)) + strerr_die2x(111,FATAL,"unable to initialize CRL dir"); + ssl = ssl_new(ctx,s); if (!ssl) strerr_die2x(111,FATAL,"unable to create SSL instance"); diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/sslhandle.c ucspi-ssl-0.70/src/sslhandle.c --- ucspi-ssl-0.70-ucspitls-0.1/src/sslhandle.c 2005-07-18 02:59:02.000000000 +0300 +++ ucspi-ssl-0.70/src/sslhandle.c 2007-01-31 23:03:01.219628117 +0200 @@ -38,7 +38,9 @@ #include "auto_dhfile.h" #include "auto_certfile.h" #include "auto_keyfile.h" +#include "auto_keyfile_ec.h" #include "auto_ciphers.h" +#include "auto_crls.h" #include "iopause.h" #include "coe.h" #include "lock.h" @@ -97,15 +99,18 @@ buffer b; SSL_CTX *ctx; const char *certfile = auto_certfile; const char *keyfile = auto_keyfile; +const char *keyfileec = auto_keyfile_ec; stralloc password = {0}; int match = 0; const char *cafile = auto_cafile; const char *ccafile = auto_ccafile; const char *cadir = auto_cadir; const char *ciphers = auto_ciphers; +const char *crldir = auto_crls; int verifydepth = 1; const char *dhfile = auto_dhfile; int rsalen = 1024; +int eclen = 233; int pi[2]; int po[2]; @@ -650,12 +655,18 @@ int main(int argc,char * const *argv) { if (x = env_get("KEYFILE")) keyfile = x; if (keyfile && str_equal(keyfile,"")) keyfile = 0; + if (x = env_get("KEYFILEEC")) keyfileec = x; + if (keyfileec && str_equal(keyfileec,"")) keyfileec = 0; + if (x = env_get("DHFILE")) dhfile = x; if (dhfile && str_equal(dhfile,"")) dhfile = 0; if (x = env_get("CIPHERS")) ciphers = x; if (ciphers && str_equal(ciphers,"")) ciphers = 0; + if (x = env_get("CRLDIR")) crldir = x; + if (crldir && str_equal(crldir,"")) crldir = 0; + if (setsid() == -1) if (getpgrp() != getpid()) strerr_die3sys(111,self,FATAL,"unable to create process group: "); @@ -718,20 +729,20 @@ int main(int argc,char * const *argv) { ssl_errstr(); if (!ctx) strerr_die3x(111,self,FATAL,"unable to create SSL context"); - switch (ssl_certkey(ctx,certfile,keyfile,passwd_cb)) { + switch (ssl_certkey(ctx,certfile,0 /* XXX */,keyfile,keyfileec,passwd_cb)) { case -1: strerr_die3x(111,self,FATAL,"unable to load certificate"); case -2: strerr_die3x(111,self,FATAL,"unable to load key"); case -3: strerr_die3x(111,self,FATAL,"key does not match certificate"); default: break; } - if (!ssl_ca(ctx,cafile,cadir,verifydepth)) + if (!ssl_ca(ctx,cafile,cadir,verifydepth,0)) strerr_die3x(111,self,FATAL,"unable to load CA list"); if (!ssl_cca(ctx,ccafile)) strerr_die3x(111,self,FATAL,"unable to load client CA list"); - if (!ssl_params(ctx,dhfile,rsalen)) + if (!ssl_params(ctx,dhfile,rsalen,eclen)) strerr_die3x(111,self,FATAL,"unable to set cipher parameters"); if (flagafter) { @@ -744,6 +755,9 @@ int main(int argc,char * const *argv) { if (!ssl_ciphers(ctx,ciphers)) strerr_die2x(111,FATAL,"unable to set cipher list"); + if (!ssl_crls(ctx, crldir)) + strerr_die2x(111,FATAL,"unable to initialize CRL dir"); + if (verbosity >= 2) { strnum[fmt_ulong(strnum,getpid())] = 0; strnum2[fmt_ulong(strnum2,rsalen)] = 0; @@ -752,6 +766,7 @@ int main(int argc,char * const *argv) { strerr_warn5(self,": cadir ",strnum," ",cadir,0); strerr_warn5(self,": cert ",strnum," ",certfile,0); strerr_warn5(self,": key ",strnum," ",keyfile,0); + strerr_warn5(self,": crl ",strnum," ",crldir,0); /* XXX */ buffer_puts(buffer_2,self); strerr_warn6(": param ",strnum," ",dhfile," ",strnum2,0); diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/sslserver.c ucspi-ssl-0.70/src/sslserver.c --- ucspi-ssl-0.70-ucspitls-0.1/src/sslserver.c 2005-09-18 13:36:31.560871000 +0300 +++ ucspi-ssl-0.70/src/sslserver.c 2008-09-02 02:05:44.806621380 +0300 @@ -4,8 +4,12 @@ #include #include #include +#include +#include #include #include +#include + #include "ssl.h" #include "uint16.h" #include "str.h" @@ -39,7 +43,9 @@ #include "auto_dhfile.h" #include "auto_certfile.h" #include "auto_keyfile.h" +#include "auto_keyfile_ec.h" #include "auto_ciphers.h" +#include "auto_crls.h" #include "fmt.h" int verbosity = 1; @@ -50,6 +56,7 @@ int flagremoteinfo = 1; int flagremotehost = 1; int flagparanoid = 0; int flagclientcert = 0; +int flagverifyonce = 0; int flagsslenv = 0; int flagtcpenv = 0; int flagsslwait = 0; @@ -79,6 +86,9 @@ unsigned long gid = 0; char strnum[FMT_ULONG]; char strnum2[FMT_ULONG]; +char strnum3[FMT_ULONG]; +char strnum4[FMT_ULONG]; +char strnum5[FMT_ULONG]; static stralloc tmp; static stralloc fqdn; @@ -86,19 +96,26 @@ static stralloc addresses; char bspace[16]; buffer b; +char retbuf[1024]; SSL_CTX *ctx; const char *certfile = auto_certfile; +const char *certfileec; const char *keyfile = auto_keyfile; +const char *keyfileec = auto_keyfile_ec; stralloc password = {0}; int match = 0; const char *cafile = auto_cafile; const char *ccafile = auto_ccafile; const char *cadir = auto_cadir; const char *ciphers = auto_ciphers; -int verifydepth = 1; +const char *crldir = auto_crls; +int verifydepth = 10; const char *dhfile = auto_dhfile; int rsalen = 1024; +int eclen = 283; + +static int randfd; char * const *prog; @@ -183,23 +200,48 @@ void found(char *data,unsigned int datal } } +static void termchild(int childfd) +{ + write(childfd, "\0\0", 2); +} + +static inline void ssl_rand_seed(void) +{ + ssize_t nread; + char randbuf[32]; + + nread = read(randfd, randbuf, sizeof(randbuf)); + if (nread > 0) { + RAND_add(randbuf, nread, nread); + byte_zero(randbuf, nread); + } +} + void doit(int t) { int j; - SSL *ssl; + SSL *ssl=0; int wstat; int sslctl[2]; char *s; long tmp_long; char ssl_cmd; - stralloc ssl_env = { 0 }; + stralloc ssl_env = {0}; int bytesleft; char envbuf[8192]; - + int ret; + stralloc dnserror = {0}; + char *bannerok; + char *bannererr; + static char bdelay[] = "0"; + int save_errno; + pid_t ppid; + int crashed; + if (pipe(pi) == -1) strerr_die2sys(111,DROP,"unable to create pipe: "); if (pipe(po) == -1) strerr_die2sys(111,DROP,"unable to create pipe: "); if (socketpair(AF_UNIX, SOCK_STREAM, 0, sslctl) == -1) strerr_die2sys(111,DROP,"unable to create socketpair: "); - - switch(fork()) { + + switch((ppid=fork())) { case -1: strerr_die2sys(111,DROP,"unable to fork: "); case 0: @@ -207,13 +249,16 @@ void doit(int t) { break; default: /* Parent */ - + close(pi[0]); close(po[1]); close(sslctl[1]); - if ((s=env_get("SSL_CHROOT"))) + if ((s=env_get("SSL_CHROOT"))) { if (chroot(s) == -1) strerr_die2x(111,DROP,"unable to chroot"); - + if (chdir("/") == -1) + strerr_die2x(111,DROP,"unable to chdir"); + } + if ((s=env_get("SSL_GID"))) { scan_ulong(s,&tmp_long); gid = tmp_long; @@ -233,47 +278,105 @@ void doit(int t) { if (read(sslctl[0],&ssl_cmd,1) == 1) { ssl = ssl_new(ctx,t); if (!ssl) strerr_die2x(111,DROP,"unable to create SSL instance"); - if (ndelay_on(t) == -1) + + ssl_rand_seed(); + + if (ndelay_on(t) == -1) { + SSL_free(ssl); strerr_die2sys(111,DROP,"unable to set socket options: "); - if (ssl_timeoutaccept(ssl,ssltimeout) == -1) + } + if (ssl_timeoutaccept(ssl,ssltimeout) == -1) { + SSL_free(ssl); + termchild(sslctl[0]); strerr_die3x(111,DROP,"unable to accept SSL: ",ssl_error_str(ssl_errno)); + } + } else { + save_errno = errno; + if ((save_errno != error_noent) && (save_errno != error_intr) && + (save_errno != ECHILD)) { + termchild(sslctl[0]); + strerr_die3x(111,DROP,"unable to read TLS command socket: ", error_str(save_errno)); + } else { + /* child exited without issuing STARTTLS */ + _exit(0); + } } - + if (verbosity >= 2) { strnum[fmt_ulong(strnum,getpid())] = 0; - strerr_warn3("sslserver: ssl ",strnum," accept ",0); + strerr_warn3("sslserver: ssl ",strnum," accept",0); } - + if (flagclientcert) { switch(ssl_verify(ssl,verifyhost)) { case -1: - strerr_die2x(111,DROP,"unable to verify client certificate"); + SSL_free(ssl); + termchild(sslctl[0]); + strerr_die3x(111,DROP,"unable to verify client certificate: ", + ssl_error_str(ssl_errno)); case -2: - strerr_die2x(111,DROP,"no client certificate"); + SSL_free(ssl); + termchild(sslctl[0]); + strerr_die3x(111,DROP,"no client certificate: ", + ssl_error_str(ssl_errno)); case -3: + SSL_free(ssl); + termchild(sslctl[0]); strerr_die2x(111,DROP,"client name does not match certificate"); default: break; } } - + if (ssl_cmd == 'Y') { ssl_server_env(ssl, &ssl_env); - stralloc_0(&ssl_env); /* Add another NUL */ + /* Add another NUL */ + if (!stralloc_0(&ssl_env)) { + termchild(sslctl[0]); + SSL_free(ssl); + drop_nomem(); + } for(bytesleft = ssl_env.len; bytesleft>0; bytesleft-=j) - if ( (j=write(sslctl[0], ssl_env.s, bytesleft)) < 0) + if ( (j=write(sslctl[0], ssl_env.s, bytesleft)) < 0) { + SSL_free(ssl); strerr_die2sys(111, FATAL, "unable to write SSL environment: "); + } } - if (ssl_io(ssl,pi[1],po[0],3600) != 0) + if (ssl_io(ssl,pi[1],po[0],progtimeout) != 0) { + SSL_free(ssl); strerr_die3x(111,DROP,"unable to speak SSL: ",ssl_error_str(ssl_errno)); - if (wait_nohang(&wstat) > 0) - _exit(wait_exitcode(wstat)); - ssl_close(ssl); + } + + save_errno = errno; + if (wait_pid(&wstat, ppid) == ppid) { + crashed = wait_crashed(wstat); + strnum[fmt_ulong(strnum,ppid)] = 0; + strnum2[fmt_ulong(strnum2,crashed ? crashed : wait_exitcode(wstat))] = 0; + if (verbosity >= 2) { + strerr_warn10("sslserver: child ", strnum, ": ", + crashed ? "signal " : "exit ", strnum2, " error \"", + error_str(save_errno), "\" ssl_error \"", + ssl_error_str(ssl_errno), "\"", 0); + } + } + if (verbosity >= 2) { + strnum[fmt_ulong(strnum,getpid())] = 0; + strnum2[fmt_ulong(strnum2,BIO_number_read(SSL_get_rbio(ssl)))] = 0; + strnum3[fmt_ulong(strnum3,BIO_number_written(SSL_get_wbio(ssl)))] = 0; + strnum4[fmt_ulong(strnum4,BIO_pending(SSL_get_rbio(ssl)))] = 0; + strnum5[fmt_ulong(strnum5,BIO_wpending(SSL_get_wbio(ssl)))] = 0; + strerr_warn11("sslserver: ssl ", strnum, + " bytes read: ",strnum2," (pending: ", strnum4, + ") written: ",strnum3, " (pending: ", strnum5, ")", 0); + } + SSL_free(ssl); _exit(0); } /* Child-only below this point */ + ssl_rand_seed(); + remoteipstr[ip4_fmt(remoteipstr,remoteip)] = 0; if (verbosity >= 2) { @@ -303,24 +406,72 @@ void doit(int t) { env("TCPLOCALHOST",localhost); } - if (flagremotehost) - if (dns_name4(&remotehostsa,remoteip) == 0) + bannerok = env_get("BANNERDELAY_DNSOK"); + if (!bannerok) bannerok = bdelay; + bannererr = env_get("BANNERDELAY_DNSERROR"); + if (!bannererr) bannererr = bdelay; + + if (flagremotehost) { + ret = dns_name4(&remotehostsa,remoteip); + if (ret == -1) { + if (!stralloc_copys(&dnserror, "PTR record")) drop_nomem(); + if (!stralloc_0(&dnserror)) drop_nomem(); + env("DNSSOFT", dnserror.s); + env("BANNERDELAY", bannererr); + } + if (ret == 0) { if (remotehostsa.len) { if (flagparanoid) { verifyhost = remoteipstr; - if (dns_ip4(&tmp,&remotehostsa) == 0) - for (j = 0;j + 4 <= tmp.len;j += 4) - if (byte_equal(remoteip,4,tmp.s + j)) { - flagparanoid = 0; - break; - } - } - if (!flagparanoid) { - if (!stralloc_0(&remotehostsa)) drop_nomem(); - remotehost = remotehostsa.s; - verifyhost = remotehostsa.s; - } + ret = dns_ip4(&tmp,&remotehostsa); + if (ret == -1) { + if (!stralloc_copys(&dnserror, "A record for ")) drop_nomem(); + if (!stralloc_cat(&dnserror, &remotehostsa)) drop_nomem(); + if (!stralloc_0(&dnserror)) drop_nomem(); + env("DNSSOFT", dnserror.s); + env("BANNERDELAY", bannererr); + } + if (ret == 0) { + if (tmp.len == 0) { + if (!stralloc_copys(&dnserror, "A record for ")) drop_nomem(); + if (!stralloc_cat(&dnserror, &remotehostsa)) drop_nomem(); + if (!stralloc_0(&dnserror)) drop_nomem(); + env("DNSHARD", dnserror.s); + env("BANNERDELAY", bannererr); + } else { + for (j = 0;j + 4 <= tmp.len;j += 4) { + if (byte_equal(remoteip,4,tmp.s + j)) { + flagparanoid = 0; + env("BANNERDELAY", bannerok); + break; + } + } + if (flagparanoid) { + if (!stralloc_copys(&dnserror, "matching A record for ")) drop_nomem(); + if (!stralloc_cat(&dnserror, &remotehostsa)) drop_nomem(); + if (!stralloc_0(&dnserror)) drop_nomem(); + env("DNSHARD", dnserror.s); + env("BANNERDELAY", bannererr); + } + } + } + if (!flagparanoid) { + if (!stralloc_0(&remotehostsa)) drop_nomem(); + remotehost = remotehostsa.s; + verifyhost = remotehostsa.s; + } + } else { + env("BANNERDELAY", bannerok); + } + } else { + if (!stralloc_copys(&dnserror, "PTR record")) drop_nomem(); + if (!stralloc_0(&dnserror)) drop_nomem(); + env("BANNERDELAY", bannererr); + env("DNSHARD", dnserror.s); } + } + } + env("SSLREMOTEIP",remoteipstr); env("SSLREMOTEPORT",remoteportstr); env("SSLREMOTEHOST",remotehost); @@ -426,8 +577,9 @@ void doit(int t) { if (write(sslctl[1], &ssl_cmd, 1) < 1) strerr_die2sys(111,DROP,"unable to start SSL: "); if (flagsslenv) { - while ((j=read(sslctl[1],envbuf,8192)) > 0) { - stralloc_catb(&ssl_env,envbuf,j); + while ((j=read(sslctl[1],envbuf,sizeof(envbuf))) > 0) { + if (!stralloc_catb(&ssl_env,envbuf,j)) + strerr_die2x(111,DROP,"out of memory while appending to ssl_env"); if (ssl_env.len >= 2 && ssl_env.s[ssl_env.len-2]==0 && ssl_env.s[ssl_env.len-1]==0) break; } @@ -436,7 +588,7 @@ void doit(int t) { pathexec_multienv(&ssl_env); } } - + pathexec(prog); strerr_die4sys(111,DROP,"unable to run ",*prog,": "); } @@ -449,7 +601,7 @@ void usage(void) { strerr_warn1("\ sslserver: usage: sslserver \ -[ -13UXpPhHrRoOdDqQviIeEsSnN ] \ +[ -13UXpPhHrRoOdDqQviIeEsSnNV ] \ [ -c limit ] \ [ -x rules.cdb ] \ [ -B banner ] \ @@ -487,12 +639,15 @@ void sigterm(void) void sigchld(void) { int wstat; int pid; - + int crashed; + while ((pid = wait_nohang(&wstat)) > 0) { if (verbosity >= 2) { + crashed = wait_crashed(wstat); strnum[fmt_ulong(strnum,pid)] = 0; - strnum2[fmt_ulong(strnum2,wstat)] = 0; - strerr_warn4("sslserver: end ",strnum," status ",strnum2,0); + strnum2[fmt_ulong(strnum2,crashed ? crashed : wait_exitcode(wstat))] = 0; + strerr_warn4("sslserver: end ",strnum, crashed ? " status signal " : " status exit ", + strnum2,0); } if (numchildren) --numchildren; printstatus(); } @@ -524,8 +679,9 @@ int main(int argc,char * const *argv) { unsigned long u; int s; int t; - - while ((opt = getopt(argc,argv,"dDvqQhHrR1UXx:t:T:u:g:l:b:B:c:pPoO3IiEeSsaAw:nN")) != opteof) + int fd; + + while ((opt = getopt(argc,argv,"VdDvqQhHrR1UXx:t:T:u:g:l:b:B:c:pPoO3IiEeSsaAw:nN")) != opteof) switch(opt) { case 'b': scan_ulong(optarg,&backlog); break; case 'c': scan_ulong(optarg,&limit); break; @@ -557,6 +713,7 @@ int main(int argc,char * const *argv) { case '3': flag3 = 1; break; case 'I': flagclientcert = 0; break; case 'i': flagclientcert = 1; break; + case 'V': flagverifyonce = 1; break; case 'S': flagsslenv = 0; break; case 's': flagsslenv = 1; break; case 'E': flagtcpenv = 0; break; @@ -570,7 +727,7 @@ int main(int argc,char * const *argv) { if (!verbosity) buffer_2->fd = -1; - + hostname = *argv++; if (!hostname) usage(); if (str_equal(hostname,"")) hostname = "0.0.0.0"; @@ -589,38 +746,47 @@ int main(int argc,char * const *argv) { localport = ntohs(se->s_port); } - if (x = env_get("VERIFYDEPTH")) { + if ((x = env_get("VERIFYDEPTH"))) { scan_ulong(x,&u); verifydepth = u; } - if (x = env_get("CAFILE")) cafile = x; + if ((x = env_get("CAFILE"))) cafile = x; if (cafile && str_equal(cafile,"")) cafile = 0; - if (x = env_get("CCAFILE")) ccafile = x; + if ((x = env_get("CCAFILE"))) ccafile = x; if (ccafile && str_equal(ccafile,"")) ccafile = 0; if (!flagclientcert) ccafile = 0; - if (x = env_get("CADIR")) cadir = x; + if ((x = env_get("CADIR"))) cadir = x; if (cadir && str_equal(cadir,"")) cadir= 0; - if (x = env_get("CERTFILE")) certfile = x; + if ((x = env_get("CERTFILE"))) certfile = x; if (certfile && str_equal(certfile,"")) certfile = 0; - if (x = env_get("KEYFILE")) keyfile = x; + if ((x = env_get("CERTFILEEC"))) certfileec = x; + if (certfileec && str_equal(certfileec,"")) certfileec = 0; + + if ((x = env_get("KEYFILE"))) keyfile = x; if (keyfile && str_equal(keyfile,"")) keyfile = 0; - if (x = env_get("DHFILE")) dhfile = x; + if ((x = env_get("KEYFILEEC"))) keyfileec = x; + if (keyfileec && str_equal(keyfileec,"")) keyfileec = 0; + + if ((x = env_get("DHFILE"))) dhfile = x; if (dhfile && str_equal(dhfile,"")) dhfile = 0; - if (x = env_get("CIPHERS")) ciphers = x; + if ((x = env_get("CIPHERS"))) ciphers = x; if (ciphers && str_equal(ciphers,"")) ciphers = 0; + if ((x = env_get("CRLDIR"))) crldir = x; + if (crldir && str_equal(crldir,"")) crldir = 0; + sig_block(sig_child); sig_catch(sig_child,sigchld); sig_catch(sig_term,sigterm); sig_ignore(sig_pipe); - + if (!stralloc_copys(&tmp,hostname)) strerr_die2x(111,FATAL,"out of memory"); if (dns_ip4_qualify(&addresses,&fqdn,&tmp) == -1) @@ -649,31 +815,48 @@ int main(int argc,char * const *argv) { buffer_puts(&b,"\n"); buffer_flush(&b); } - + if (flag3) read_passwd(); - ctx = ssl_server(); + SSL_library_init(); ssl_errstr(); + ctx = ssl_server(); if (!ctx) strerr_die2x(111,FATAL,"unable to create SSL context"); - switch (ssl_certkey(ctx,certfile,keyfile,passwd_cb)) { - case -1: strerr_die2x(111,FATAL,"unable to load certificate"); - case -2: strerr_die2x(111,FATAL,"unable to load key"); - case -3: strerr_die2x(111,FATAL,"key does not match certificate"); + switch (ssl_certkey(ctx, certfile, certfileec, + keyfile, keyfileec, passwd_cb)) { + case -1: strerr_die3x(111,FATAL,"unable to load certificate #1: ", + ERR_error_string(ERR_get_error(), retbuf)); + case -2: strerr_die3x(111,FATAL,"unable to load key #1: ", + ERR_error_string(ERR_get_error(), retbuf)); + case -3: strerr_die3x(111,FATAL,"unable to load certificate #2: ", + ERR_error_string(ERR_get_error(), retbuf)); + case -4: strerr_die3x(111,FATAL,"unable to load key #2: ", + ERR_error_string(ERR_get_error(), retbuf)); + case -5: strerr_die3x(111,FATAL,"key does not match certificate: ", + ERR_error_string(ERR_get_error(), retbuf)); default: break; } - if (!ssl_ca(ctx,cafile,cadir,verifydepth)) - strerr_die2x(111,FATAL,"unable to load CA list"); + if (!ssl_ca(ctx,cafile,cadir,verifydepth,flagverifyonce)) + strerr_die3x(111,FATAL,"unable to load CA list: ", + ERR_error_string(ERR_get_error(), retbuf)); if (!ssl_cca(ctx,ccafile)) - strerr_die2x(111,FATAL,"unable to load client CA list"); + strerr_die3x(111,FATAL,"unable to load client CA list: ", + ERR_error_string(ERR_get_error(), retbuf)); - if (!ssl_params(ctx,dhfile,rsalen)) - strerr_die2x(111,FATAL,"unable to set cipher parameters"); + if (!ssl_params(ctx,dhfile,rsalen,eclen)) + strerr_die3x(111,FATAL,"unable to set cipher parameters: ", + ERR_error_string(ERR_get_error(), retbuf)); if (!ssl_ciphers(ctx,ciphers)) - strerr_die2x(111,FATAL,"unable to set cipher list"); + strerr_die3x(111,FATAL,"unable to set cipher list: ", + ERR_error_string(ERR_get_error(), retbuf)); + + if (!ssl_crls(ctx,crldir)) + strerr_die3x(111,FATAL,"unable to load any CRL files: ", + ERR_error_string(ERR_get_error(), retbuf)); if (verbosity >= 2) { strnum[fmt_ulong(strnum,getpid())] = 0; @@ -683,14 +866,26 @@ int main(int argc,char * const *argv) { strerr_warn4("sslserver: cadir ",strnum," ",cadir,0); strerr_warn4("sslserver: cert ",strnum," ",certfile,0); strerr_warn4("sslserver: key ",strnum," ",keyfile,0); + strerr_warn4("sslserver: crldir ",strnum," ",crldir,0); strerr_warn6("sslserver: param ",strnum," ",dhfile," ",strnum2,0); } - close(0); open_read("/dev/null"); - close(1); open_append("/dev/null"); + fd = open_append("/dev/null"); + if (fd == -1) + strerr_die2x(111,FATAL,"unable to open /dev/null"); + + randfd = open_read_cloexec("/dev/urandom"); + if (randfd == -1) + strerr_die2x(111,FATAL,"unable to open /dev/urandom"); + + if (dup2(fd, 0) == -1) + strerr_die2x(111,FATAL,"dup2(fd, 0) failed"); + if (dup2(fd, 1) == -1) + strerr_die2x(111,FATAL,"dup2(fd, 1) failed"); + if (fd > 2) close(fd); printstatus(); - + for (;;) { while (numchildren >= limit) sig_pause(); @@ -700,7 +895,7 @@ int main(int argc,char * const *argv) { if (t == -1) continue; ++numchildren; printstatus(); - + switch(fork()) { case 0: close(s); @@ -717,7 +912,6 @@ int main(int argc,char * const *argv) { /* taken from 0.68 */ char *ssl_error_str(int e) { - SSL_load_error_strings(); - return ERR_error_string(e,0); + return ERR_error_string(e,retbuf); } diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/strerr.h ucspi-ssl-0.70/src/strerr.h --- ucspi-ssl-0.70-ucspitls-0.1/src/strerr.h 2005-07-18 02:59:02.000000000 +0300 +++ ucspi-ssl-0.70/src/strerr.h 2007-01-31 01:35:03.389990439 +0200 @@ -1,21 +1,21 @@ -/* Public domain. */ - #ifndef STRERR_H #define STRERR_H -struct strerr { +struct strerr + { struct strerr *who; - const char *x; - const char *y; - const char *z; -} ; + char *x; + char *y; + char *z; + } +; extern struct strerr strerr_sys; extern void strerr_sysinit(void); -extern const char *strerr(const struct strerr *); -extern void strerr_warn(const char *,const char *,const char *,const char *,const char *,const char *,const struct strerr *); -extern void strerr_die(int,const char *,const char *,const char *,const char *,const char *,const char *,const struct strerr *); +extern char *strerr(); +extern void strerr_warn(const char*, const char*, const char*, const char*, const char*, const char*, const char*, const char*, const char *, const char *, const char *, const char *, struct strerr*); +extern void strerr_die(int, const char*, const char*, const char*, const char*, const char*, const char*, const char*, const char*, struct strerr*); #define STRERR(r,se,a) \ { se.who = 0; se.x = a; se.y = 0; se.z = 0; return r; } @@ -25,56 +25,80 @@ extern void strerr_die(int,const char *, #define STRERR_SYS3(r,se,a,b,c) \ { se.who = &strerr_sys; se.x = a; se.y = b; se.z = c; return r; } +#define strerr_warn12(x1,x2,x3,x4,x5,x6,x7,x8,x9,x10,x11,x12,se) \ +strerr_warn((x1),(x2),(x3),(x4),(x5),(x6),(x7),(x8),(x9),(x10),(x11),(x12),(struct strerr *) (se)) +#define strerr_warn11(x1,x2,x3,x4,x5,x6,x7,x8,x9,x10,x11,se) \ +strerr_warn((x1),(x2),(x3),(x4),(x5),(x6),(x7),(x8),(x9),(x10),(x11),(char *) 0,(struct strerr *) (se)) +#define strerr_warn10(x1,x2,x3,x4,x5,x6,x7,x8,x9,x10,se) \ +strerr_warn((x1),(x2),(x3),(x4),(x5),(x6),(x7),(x8),(x9),(x10),(char *) 0,(char *) 0,(struct strerr *) (se)) +#define strerr_warn9(x1,x2,x3,x4,x5,x6,x7,x8,x9,se) \ +strerr_warn((x1),(x2),(x3),(x4),(x5),(x6),(x7),(x8),(x9),(char* ) 0,(char *) 0,(char *) 0,(struct strerr *) (se)) +#define strerr_warn8(x1,x2,x3,x4,x5,x6,x7,x8,se) \ +strerr_warn((x1),(x2),(x3),(x4),(x5),(x6),(x7),(x8),(char *) 0,(char *) 0,(char *) 0,(char *) 0,(struct strerr *) (se)) +#define strerr_warn7(x1,x2,x3,x4,x5,x6,x7,se) \ +strerr_warn((x1),(x2),(x3),(x4),(x5),(x6),(x7),(char *) 0,(char *) 0,(char *) 0,(char *) 0,(char *) 0,(struct strerr *) (se)) #define strerr_warn6(x1,x2,x3,x4,x5,x6,se) \ -strerr_warn((x1),(x2),(x3),(x4),(x5),(x6),(se)) +strerr_warn((x1),(x2),(x3),(x4),(x5),(x6),(char *) 0,(char*) 0,(char *) 0,(char *) 0,(char *) 0,(char *) 0,(struct strerr *) (se)) #define strerr_warn5(x1,x2,x3,x4,x5,se) \ -strerr_warn((x1),(x2),(x3),(x4),(x5),0,(se)) +strerr_warn((x1),(x2),(x3),(x4),(x5),(char *) 0,(char *) 0,(char* ) 0,(char *) 0,(char *) 0,(char* ) 0,(char *) 0,(struct strerr *) (se)) #define strerr_warn4(x1,x2,x3,x4,se) \ -strerr_warn((x1),(x2),(x3),(x4),0,0,(se)) +strerr_warn((x1),(x2),(x3),(x4),(char *) 0,(char *) 0,(char *) 0,(char* ) 0,(char* ) 0,(char *) 0,(char *) 0,(char *) 0,(struct strerr *) (se)) #define strerr_warn3(x1,x2,x3,se) \ -strerr_warn((x1),(x2),(x3),0,0,0,(se)) +strerr_warn((x1),(x2),(x3),(char *) 0,(char *) 0,(char *) 0,(char *) 0,(char* ) 0,(char *) 0,(char *) 0,(char* ) 0,(char *) 0,(struct strerr *) (se)) #define strerr_warn2(x1,x2,se) \ -strerr_warn((x1),(x2),0,0,0,0,(se)) +strerr_warn((x1),(x2),(char *) 0,(char *) 0,(char *) 0,(char *) 0,(char *) 0,(char* ) 0,(char *) 0,(char *) 0,(char* ) 0,(char *) 0,(struct strerr *) (se)) #define strerr_warn1(x1,se) \ -strerr_warn((x1),0,0,0,0,0,(se)) +strerr_warn((x1),(char *) 0,(char *) 0,(char* ) 0,(char* ) 0,(char *) 0,(char *) 0,(char *) 0,(char *) 0,(char *) 0,(char *) 0,(char *) 0,(struct strerr *) (se)) +#define strerr_die8(e,x1,x2,x3,x4,x5,x6,x7,x8,se) \ +strerr_die((e),(x1),(x2),(x3),(x4),(x5),(x6),(x7),(x8),(struct strerr *) (se)) +#define strerr_die7(e,x1,x2,x3,x4,x5,x6,x7,se) \ +strerr_die((e),(x1),(x2),(x3),(x4),(x5),(x6),(x7),(char *) 0,(struct strerr *) (se)) #define strerr_die6(e,x1,x2,x3,x4,x5,x6,se) \ -strerr_die((e),(x1),(x2),(x3),(x4),(x5),(x6),(se)) +strerr_die((e),(x1),(x2),(x3),(x4),(x5),(x6),(char *) 0,(char *) 0,(struct strerr *) (se)) #define strerr_die5(e,x1,x2,x3,x4,x5,se) \ -strerr_die((e),(x1),(x2),(x3),(x4),(x5),0,(se)) +strerr_die((e),(x1),(x2),(x3),(x4),(x5),(char *) 0,(char *) 0,(char *) 0,(struct strerr *) (se)) #define strerr_die4(e,x1,x2,x3,x4,se) \ -strerr_die((e),(x1),(x2),(x3),(x4),0,0,(se)) +strerr_die((e),(x1),(x2),(x3),(x4),(char *) 0,(char *) 0,(char *) 0,(char *) 0,(struct strerr *) (se)) #define strerr_die3(e,x1,x2,x3,se) \ -strerr_die((e),(x1),(x2),(x3),0,0,0,(se)) +strerr_die((e),(x1),(x2),(x3),(char *) 0,(char *) 0,(char *) 0,(char *) 0,(char *) 0,(struct strerr *) (se)) #define strerr_die2(e,x1,x2,se) \ -strerr_die((e),(x1),(x2),0,0,0,0,(se)) +strerr_die((e),(x1),(x2),(char *) 0,(char *) 0,(char *) 0,(char *) 0,(char *) 0,(char *) 0,(struct strerr *) (se)) #define strerr_die1(e,x1,se) \ -strerr_die((e),(x1),0,0,0,0,0,(se)) +strerr_die((e),(x1),(char *) 0,(char *) 0,(char *) 0,(char *) 0,(char *) 0,(char *) 0,(char *) 0,(struct strerr *) (se)) +#define strerr_die8sys(e,x1,x2,x3,x4,x5,x6,x7,x8) \ +strerr_die((e),(x1),(x2),(x3),(x4),(x5),(x6),(x7),(x8),&strerr_sys) +#define strerr_die7sys(e,x1,x2,x3,x4,x5,x6,x7) \ +strerr_die((e),(x1),(x2),(x3),(x4),(x5),(x6),(x7),(char *) 0,&strerr_sys) #define strerr_die6sys(e,x1,x2,x3,x4,x5,x6) \ -strerr_die((e),(x1),(x2),(x3),(x4),(x5),(x6),&strerr_sys) +strerr_die((e),(x1),(x2),(x3),(x4),(x5),(x6),(char *) 0,(char *) 0,&strerr_sys) #define strerr_die5sys(e,x1,x2,x3,x4,x5) \ -strerr_die((e),(x1),(x2),(x3),(x4),(x5),0,&strerr_sys) +strerr_die((e),(x1),(x2),(x3),(x4),(x5),(char *) 0,(char *) 0,(char *) 0,&strerr_sys) #define strerr_die4sys(e,x1,x2,x3,x4) \ -strerr_die((e),(x1),(x2),(x3),(x4),0,0,&strerr_sys) +strerr_die((e),(x1),(x2),(x3),(x4),(char *) 0,(char *) 0,(char *) 0,(char *) 0,&strerr_sys) #define strerr_die3sys(e,x1,x2,x3) \ -strerr_die((e),(x1),(x2),(x3),0,0,0,&strerr_sys) +strerr_die((e),(x1),(x2),(x3),(char *) 0,(char *) 0,(char *) 0,(char *) 0,(char *) 0,&strerr_sys) #define strerr_die2sys(e,x1,x2) \ -strerr_die((e),(x1),(x2),0,0,0,0,&strerr_sys) +strerr_die((e),(x1),(x2),(char *) 0,(char *) 0,(char *) 0,(char *) 0,(char *) 0,(char *) 0,&strerr_sys) #define strerr_die1sys(e,x1) \ -strerr_die((e),(x1),0,0,0,0,0,&strerr_sys) +strerr_die((e),(x1),(char *) 0,(char *) 0,(char *) 0,(char *) 0,(char *) 0,(char *) 0,(char *) 0,&strerr_sys) +#define strerr_die8x(e,x1,x2,x3,x4,x5,x6,x7,x8) \ +strerr_die((e),(x1),(x2),(x3),(x4),(x5),(x6),(x7),(x8),(struct strerr *) 0) +#define strerr_die7x(e,x1,x2,x3,x4,x5,x6,x7) \ +strerr_die((e),(x1),(x2),(x3),(x4),(x5),(x6),(x7),(char *) 0,(struct strerr *) 0) #define strerr_die6x(e,x1,x2,x3,x4,x5,x6) \ -strerr_die((e),(x1),(x2),(x3),(x4),(x5),(x6),0) +strerr_die((e),(x1),(x2),(x3),(x4),(x5),(x6),(char *) 0,(char *) 0,(struct strerr *) 0) #define strerr_die5x(e,x1,x2,x3,x4,x5) \ -strerr_die((e),(x1),(x2),(x3),(x4),(x5),0,0) +strerr_die((e),(x1),(x2),(x3),(x4),(x5),(char *) 0,(char *) 0,(char *) 0,(struct strerr *) 0) #define strerr_die4x(e,x1,x2,x3,x4) \ -strerr_die((e),(x1),(x2),(x3),(x4),0,0,0) +strerr_die((e),(x1),(x2),(x3),(x4),(char *) 0,(char *) 0,(char *) 0,(char *) 0,(struct strerr *) 0) #define strerr_die3x(e,x1,x2,x3) \ -strerr_die((e),(x1),(x2),(x3),0,0,0,0) +strerr_die((e),(x1),(x2),(x3),(char *) 0,(char *) 0,(char *) 0,(char *) 0,(char *) 0,(struct strerr *) 0) #define strerr_die2x(e,x1,x2) \ -strerr_die((e),(x1),(x2),0,0,0,0,0) +strerr_die((e),(x1),(x2),(char *) 0,(char *) 0,(char *) 0,(char *) 0,(char *) 0,(char *) 0,(struct strerr *) 0) #define strerr_die1x(e,x1) \ -strerr_die((e),(x1),0,0,0,0,0,0) +strerr_die((e),(x1),(char *) 0,(char *) 0,(char *) 0,(char *) 0,(char *) 0,(char *) 0,(char *) 0,(struct strerr *) 0) #endif diff -Nurp ucspi-ssl-0.70-ucspitls-0.1/src/strerr_die.c ucspi-ssl-0.70/src/strerr_die.c --- ucspi-ssl-0.70-ucspitls-0.1/src/strerr_die.c 2005-07-18 02:59:02.000000000 +0300 +++ ucspi-ssl-0.70/src/strerr_die.c 2007-01-31 01:37:32.680828731 +0200 @@ -4,7 +4,9 @@ #include "exit.h" #include "strerr.h" -void strerr_warn(const char *x1,const char *x2,const char *x3,const char *x4,const char *x5,const char *x6,const struct strerr *se) +void strerr_warn(x1,x2,x3,x4,x5,x6,x7,x8,x9,x10,x11,x12,se) +const char *x1; const char *x2; const char *x3; const char *x4; const char *x5; const char *x6; const char *x7; const char *x8; const char *x9; const char *x10; const char *x11; const char *x12; +struct strerr *se; { strerr_sysinit(); @@ -14,6 +16,12 @@ void strerr_warn(const char *x1,const ch if (x4) buffer_puts(buffer_2,x4); if (x5) buffer_puts(buffer_2,x5); if (x6) buffer_puts(buffer_2,x6); + if (x7) buffer_puts(buffer_2,x7); + if (x8) buffer_puts(buffer_2,x8); + if (x9) buffer_puts(buffer_2,x9); + if (x10) buffer_puts(buffer_2,x10); + if (x11) buffer_puts(buffer_2,x11); + if (x12) buffer_puts(buffer_2,x12); while(se) { if (se->x) buffer_puts(buffer_2,se->x); @@ -26,8 +34,8 @@ void strerr_warn(const char *x1,const ch buffer_flush(buffer_2); } -void strerr_die(int e,const char *x1,const char *x2,const char *x3,const char *x4,const char *x5,const char *x6,const struct strerr *se) +void strerr_die(int e,const char *x1,const char *x2,const char *x3,const char *x4,const char *x5,const char *x6,const char *x7, const char *x8, struct strerr *se) { - strerr_warn(x1,x2,x3,x4,x5,x6,se); + strerr_warn(x1,x2,x3,x4,x5,x6,x7,x8,0,0,0,0,se); _exit(e); } --- ucspi-ssl-0.70.orig/src/ssl_env.c 2005-07-18 02:59:02.000000000 +0300 +++ ucspi-ssl/src/ssl_env.c 2009-01-08 20:22:24.132014575 +0200 @@ -67,10 +67,46 @@ SSL_CIPHER *cipher; unsigned char u; unsigned char c; + const char *vfystring; + X509 *cert; + X509_STORE *store; + X509_STORE_CTX store_ctx; + int storeok = 0; + int x509ret = 0; + EVP_PKEY *pktmp; if (!env_str("SSL_PROTOCOL",SSL_get_version(ssl))) return 0; + if (!ssl->ctx) + return 0; + store = SSL_CTX_get_cert_store(ssl->ctx); + cert = SSL_get_peer_certificate(ssl); + if (cert) { + if (X509_STORE_CTX_init(&store_ctx, store, cert, NULL) != 1) { + X509_free(cert); + return 0; + } + pktmp = X509_get_pubkey(cert); + if (!env_val("SSL_PUBKEY_SIZE", strnum, + fmt_ulong(strnum,EVP_PKEY_bits(pktmp)))) return 0; + EVP_PKEY_free(pktmp); + X509_STORE_CTX_set_cert(&store_ctx, cert); + storeok = X509_verify_cert(&store_ctx); + x509ret = X509_STORE_CTX_get_error(&store_ctx); + X509_STORE_CTX_cleanup(&store_ctx); + X509_free(cert); + vfystring = X509_verify_cert_error_string(x509ret); + if (!env_str("SSL_VERIFY_STRING",vfystring)) return 0; + if ((x509ret == X509_V_OK) && (storeok == 1)) { + if (!env_str("SSL_VERIFY_STATUS","OK")) return 0; + } else { + if (!env_str("SSL_VERIFY_STATUS","FAIL")) return 0; + } + } else { + if (!env_str("SSL_VERIFY_STRING","FAIL")) return 0; + if (!env_str("SSL_VERIFY_STATUS","NOCERT")) return 0; + } session = SSL_get_session(ssl); x = session->session_id; n = session->session_id_length; @@ -86,15 +122,17 @@ } if (!env_val("SSL_SESSION_ID",btemp.s,btemp.len)) return 0; - if (!env_str("SSL_CIPHER",SSL_get_cipher_name(ssl))) return 0; - cipher = SSL_get_current_cipher(ssl); if (!cipher) return 0; + if (!env_str("SSL_CIPHER",SSL_CIPHER_get_name(cipher))) return 0; + n = SSL_CIPHER_get_bits(cipher,&m); if (!env_str("SSL_CIPHER_EXPORT",n < 56 ? "true" : "false")) return 0; if (!env_val("SSL_CIPHER_USEKEYSIZE",strnum,fmt_ulong(strnum,n))) return 0; if (!env_val("SSL_CIPHER_ALGKEYSIZE",strnum,fmt_ulong(strnum,m))) return 0; + if (!env_val("SSL_RFD",strnum,fmt_ulong(strnum,SSL_get_rfd(ssl)))) return 0; + if (!env_val("SSL_WFD",strnum,fmt_ulong(strnum,SSL_get_wfd(ssl)))) return 0; if (!env_str("SSL_VERSION_INTERFACE","ucspi-ssl")) return 0; if (!env_str("SSL_VERSION_LIBRARY",OPENSSL_VERSION_TEXT)) return 0; @@ -153,6 +191,40 @@ return 1; } +static const unsigned char hextbl[] = "0123456789abcdef"; + +static char *x509digest_sha1(X509* peer) +{ + unsigned char md[EVP_MAX_MD_SIZE]; + unsigned int mdlen, i; + static unsigned char nibbles[EVP_MAX_MD_SIZE*2+1]; + const EVP_MD *sha1dg = EVP_sha1(); + + if (!X509_digest(peer, sha1dg, md, &mdlen)) return NULL; + for (i = 0; i < mdlen; i++) { + nibbles[i*2+0] = hextbl[(md[i] >> 4)]; + nibbles[i*2+1] = hextbl[(md[i] & 15)]; + } + nibbles[i*2] = 0; + return nibbles; +} + +static char *x509digest_md5(X509* peer) +{ + unsigned char md[EVP_MAX_MD_SIZE]; + unsigned int mdlen, i; + static unsigned char nibbles[EVP_MAX_MD_SIZE*2+1]; + const EVP_MD *md5dg = EVP_md5(); + + if (!X509_digest(peer, md5dg, md, &mdlen)) return NULL; + for (i = 0; i < mdlen; i++) { + nibbles[i*2+0] = hextbl[(md[i] >> 4)]; + nibbles[i*2+1] = hextbl[(md[i] & 15)]; + } + nibbles[i*2] = 0; + return nibbles; +} + static int ssl_client_vars(X509 *cert,STACK_OF(X509) *chain) { X509_NAME *xname; char *x; @@ -225,6 +297,14 @@ if (!env_str("SSL_CLIENT_A_KEY",(n == NID_undef) ? "UNKNOWN" : OBJ_nid2ln(n))) return 0; + x = x509digest_sha1(cert); + if (!x) return 0; + if (!env_str("SSL_CLIENT_DIGEST_SHA1", x)) return 0; + + x = x509digest_md5(cert); + if (!x) return 0; + if (!env_str("SSL_CLIENT_DIGEST_MD5", x)) return 0; + bio = BIO_new(BIO_s_mem()); if (!bio) return 0; n = ssl_client_bio_vars(cert,chain,bio); @@ -351,6 +431,14 @@ if (!env_str("SSL_SERVER_A_KEY",(n == NID_undef) ? "UNKNOWN" : OBJ_nid2ln(n))) return 0; + x = x509digest_sha1(cert); + if (!x) return 0; + if (!env_str("SSL_SERVER_DIGEST_SHA1", x)) return 0; + + x = x509digest_md5(cert); + if (!x) return 0; + if (!env_str("SSL_SERVER_DIGEST_MD5", x)) return 0; + bio = BIO_new(BIO_s_mem()); if (!bio) return 0; n = ssl_server_bio_vars(cert,chain,bio); @@ -362,22 +450,33 @@ } int ssl_client_env(SSL *ssl,stralloc *sa) { + X509 *cert; + envsa = sa; if (!ssl_session_vars(ssl)) return 0; if (!ssl_client_vars(SSL_get_certificate(ssl),0)) return 0; - if (!ssl_server_vars(SSL_get_peer_certificate(ssl),SSL_get_peer_cert_chain(ssl))) + cert = SSL_get_peer_certificate(ssl); + if (!ssl_server_vars(cert,SSL_get_peer_cert_chain(ssl))) { + X509_free(cert); return 0; + } + X509_free(cert); return 1; } int ssl_server_env(SSL *ssl,stralloc *sa) { + X509 *cert; + envsa = sa; if (!ssl_session_vars(ssl)) return 0; if (!ssl_server_vars(SSL_get_certificate(ssl),0)) return 0; - if (!ssl_client_vars(SSL_get_peer_certificate(ssl),SSL_get_peer_cert_chain(ssl))) + cert = SSL_get_peer_certificate(ssl); + if (!ssl_client_vars(cert,SSL_get_peer_cert_chain(ssl))) { + X509_free(cert); return 0; + } return 1; } --- ucspi-ssl-0.70.orig/src/ssl_context.c 2005-07-18 02:59:02.000000000 +0300 +++ ucspi-ssl/src/ssl_context.c 2014-10-15 01:40:47.581645101 +0300 @@ -1,13 +1,27 @@ #include #include "ssl.h" +#ifndef SSL_OP_NO_SESSION_RESUMPTION_ON_RENEGOTIATION +# define SSL_OP_NO_SESSION_RESUMPTION_ON_RENEGOTIATION (0) +#endif + +#ifndef SSL_OP_NO_COMPRESSION +# define SSL_OP_NO_COMPRESSION (0) +#endif + SSL_CTX *ssl_context(SSL_METHOD *m) { SSL_CTX *ctx; - SSL_library_init(); ctx = SSL_CTX_new(m); - SSL_CTX_set_options(ctx,SSL_OP_SINGLE_DH_USE); + if (ctx) { + SSL_CTX_set_options(ctx, SSL_OP_NO_COMPRESSION | SSL_OP_NO_SESSION_RESUMPTION_ON_RENEGOTIATION | + SSL_OP_NO_SSLv2 | SSL_OP_NO_SSLv3); + SSL_CTX_set_ecdh_auto(ctx, 1); + SSL_CTX_set_mode(ctx, SSL_MODE_ACCEPT_MOVING_WRITE_BUFFER | + SSL_MODE_ENABLE_PARTIAL_WRITE); + } + return ctx; }