Pier Fumagalli wrote: > > jean-frederic clere at [EMAIL PROTECTED] wrote: > > > Hi, > > > > I have started to add SSL support to mod_webapp. I have prepared a test patch > > for client certificates, it works. > > > > I will now add the missing part and improve it a little: > > Storing the ssl_cert and other in a substructure of wa_request instead > > directly > > in wa_request. > > Something like: > > +++ > > typedef struct wa_ssldata wa_ssldata; > > struct wa_ssldata { > > char *ssl_cert; > > char *ssl_cipher; > > char *ssl_session; > > int ssl_key_size; > > } > > struct wa_request { > > ... > > wa_ssldata *ssld; > > } > > +++ > > Dunno why but I like this structure...
:) Thanks for the idea :) > > > Changing the protocol elements: > > TYPE_CBK_READ to TYPE_ASK_READ > > TYPE_CBK_DATA to TYPE_REP_DATA > > TYPE_CBK_DOME to TYPE_REP_DONE > > To see more easly was it from web server (REP: Reponse) and to web server > > (ASK: Ask). > > REP=Reply :) Sure... One day may be I will stop using french words in the "foreign" languages I use every day. > > > I will (from the patch) remove (TYPE_REP_SSL_SESSION, TYPE_REP_SSL_CIPHER, > > TYPE_REP_SSL_KEYSIZ and replace them by TYPE_REP_SSL that will carry > > SSL_SESSION, SSL_CIPHER and KEYSIZ in its payload. > > > > The things like "SSL_CLIENT_CERT", that are extracted from mod_ssl I will put > > them in an include file I think that they have fixed values in a webserver > > implementation. > > req->ssl_cert = (char *)ap_table_get(r->subprocess_env,"SSL_CLIENT_CERT"); > > > > Any comments? > > Ok... Regarding variable names, I'm pretty sure that on all mod_ssl based > Apaches this is going to work... Regarding Ben's Apache-SSL, I'm going to > see him this Saturday, and I'll ask him details about SSL sessions (that I > don't see in his code) and the difference between his SSL_CLIENT_CERT > (encoded in Base64), and mod_ssl's (encoded in PEM)... We have in mod_ssl (trace from the patched mod_webapp): +++ [Thu Oct 18 18:35:04 2001] [error] CC bytes: (Sent=-----BEGIN CERTIFICATE----- MIIDsjCCAxugAwIBAgIBAjANBgkqhkiG9w0BAQQFADCBgzELMAkGA1UEBhMCRVMx EjAQBgNVBAgTCUJhcmNlbG9uYTESMBAGA1UEBxMJQmFyY2Vsb25hMRcwFQYDVQQK Ew5UZXN0cyB2dHhjbGVyZTEQMA4GA1UEAxMHamZjbGVyZTEhMB8GCSqGSIb3DQEJ ARYSamZjbGVyZUBhcGFjaGUub3JnMB4XDTAxMDkxMDEwNTQ0NloXDTAyMDkxMDEw NTQ0NlowgaYxCzAJBgNVBAYTAkVTMRIwEAYDVQQIEwlDYXRhbHVueWExEjAQBgNV BAcTCUJhcmNlbG9uYTEbMBkGA1UEChMSSmVhbi1GcmVkZXJpYyBVc2VyMREwDwYD VQQLEwh2dHhjbGVyZTEcMBoGA1UEAxMTSmVhbi1GcmVkZXJpYyBDbGVyZTEhMB8G CSqGSIb3DQEJARYSamZjbGVyZUBhcGFjaGUub3JnMIGfMA0GCSqGSIb3DQEBAQUA A4GNADCBiQKBgQCRbBIK019yoEERo8UptWiRToj+agQOMxszKOwtASMi94UOXf7L +++ I think that it is PEM . The Java documentation says that base64 and binary are supported. "man x509" says: +++ The DER format is the DER encoding of the certificate and PEM is the base64 encoding of the DER encoding with header and footer lines added. +++ So I hope it works for both :-) > > That might be the only difference between the two, for the rest I can't > really see much... > > Pier > > > Cheers > > > > Jean-frederic > > Index: apache-1.3/mod_webapp.c > > =================================================================== > > RCS file: > > /home/cvs/mirror/jakarta-tomcat-connectors/webapp/apache-1.3/mod_webapp.c,v > > retrieving revision 1.24 > > diff -u -r1.24 mod_webapp.c > > --- apache-1.3/mod_webapp.c 2001/10/09 10:41:25 1.24 > > +++ apache-1.3/mod_webapp.c 2001/10/18 15:15:59 > > @@ -462,6 +462,7 @@ > > req->clen=0; > > req->ctyp="\0"; > > req->rlen=0; > > + req->ssl_cert = (char > > *)ap_table_get(r->subprocess_env,"SSL_CLIENT_CERT"); > > > > /* Copy headers into webapp request structure */ > > if (r->headers_in!=NULL) { > > Index: include/wa_request.h > > =================================================================== > > RCS file: > > /home/cvs/mirror/jakarta-tomcat-connectors/webapp/include/wa_request.h,v > > retrieving revision 1.6 > > diff -u -r1.6 wa_request.h > > --- include/wa_request.h 2001/07/19 23:47:31 1.6 > > +++ include/wa_request.h 2001/10/18 15:16:02 > > @@ -128,6 +128,8 @@ > > long rlen; > > /** The current headers table. */ > > apr_table_t *hdrs; > > + /** The client certificate string */ > > + char *ssl_cert; > > }; > > > > /** > > Index: java/Constants.java.in > > =================================================================== > > RCS file: > > /home/cvs/mirror/jakarta-tomcat-connectors/webapp/java/Constants.java.in,v > > retrieving revision 1.11 > > diff -u -r1.11 Constants.java.in > > --- java/Constants.java.in 2001/08/09 20:02:15 1.11 > > +++ java/Constants.java.in 2001/10/18 15:16:03 > > @@ -363,4 +363,62 @@ > > * No payload.<br> > > */ > > public static final int TYPE_CBK_DONE=0x42; > > + > > + /** > > + * ASK_SSL: The WARP client (HTTP server) asks the WARP server to > > + * transfer the basic SSL information (cypher, keysize and session). > > + * <br> > > + * No payload.<br> > > + */ > > + public static final int TYPE_ASK_SSL=0x43; > > + > > + /** > > + * ASK_SSL_CLIENT: The WARP client (HTTP server) asks the WARP server to > > + * transfer the client certificate. > > + * (just the first element of the chain and the webserver should request > > + * for it to the browser if possible). > > + * <br> > > + * No payload.<br> > > + */ > > + public static final int TYPE_ASK_SSL_CLIENT=0x44; > > + > > + /** > > + * REP_SSL_CERT: The client certificate (remote peer). > > + * <br> > > + * Payload description:<br> > > + * [string] The client certificate. > > + */ > > + public static final int TYPE_REP_SSL_CERT=0x52; > > + > > + /** > > + * REP_SSL_CIPHER: The cipher used between client and server. > > + * <br> > > + * Payload description:<br> > > + * [string] The cipher_suite. > > + */ > > + public static final int TYPE_REP_SSL_CIPHER=0x53; > > + > > + /** > > + * REP_SSL_SESSION: The ssl session. > > + * <br> > > + * Payload description:<br> > > + * [string] The ssl session. (That is not in the spec's). > > + */ > > + public static final int TYPE_REP_SSL_SESSION=0x54; > > + > > + /** > > + * REP_SSL_KEYSIZ: size of the used algorithm. > > + * <br> > > + * Payload description:<br> > > + * [ushort] size of the algorithm (56-128). > > + */ > > + public static final int TYPE_REP_SSL_KEYSIZ=0x55; > > + > > + /** > > + * REP_SSL_NO: Request SSL information is not available. > > + * <br> > > + * No payload.<br> > > + */ > > + public static final int TYPE_REP_SSL_NO=0x5F; > > } > > + > > Index: java/Makefile.in > > =================================================================== > > RCS file: /home/cvs/mirror/jakarta-tomcat-connectors/webapp/java/Makefile.in,v > > retrieving revision 1.3 > > diff -u -r1.3 Makefile.in > > --- java/Makefile.in 2001/09/17 05:04:02 1.3 > > +++ java/Makefile.in 2001/10/18 15:16:04 > > @@ -70,6 +70,7 @@ > > WarpRequest.java \ > > WarpRequestHandler.java \ > > WarpResponse.java \ > > + WarpCertificates.java > > > > ARCHIVE = warp.jar > > > > Index: java/WarpConnector.java > > =================================================================== > > RCS file: > > /home/cvs/mirror/jakarta-tomcat-connectors/webapp/java/WarpConnector.java,v > > retrieving revision 1.21 > > diff -u -r1.21 WarpConnector.java > > --- java/WarpConnector.java 2001/10/13 01:33:00 1.21 > > +++ java/WarpConnector.java 2001/10/18 15:16:06 > > @@ -481,6 +481,8 @@ > > } > > } catch (IOException e) { > > throw new LifecycleException("Error creating server socket",e); > > + } catch (java.security.GeneralSecurityException e) { > > + throw new LifecycleException("Error creating SSL server > > socket",e); > > } > > } > > > > Index: java/WarpRequest.java > > =================================================================== > > RCS file: > > /home/cvs/mirror/jakarta-tomcat-connectors/webapp/java/WarpRequest.java,v > > retrieving revision 1.9 > > diff -u -r1.9 WarpRequest.java > > --- java/WarpRequest.java 2001/07/25 22:32:05 1.9 > > +++ java/WarpRequest.java 2001/10/18 15:16:06 > > @@ -77,6 +77,20 @@ > > this.setStream(this.localstream); > > } > > > > + /** Process the SSL attributes */ > > + public Object getAttribute(String name) { > > + if (name.equals("javax.servlet.request.X509Certificate")) { > > + WarpCertificates cert = null; > > + try { > > + cert = new > > WarpCertificates(localstream.getX509Certificates()); > > + } catch (IOException e) { > > + return null; > > + } > > + return(cert.getCertificates()); > > + } > > + return(super.getAttribute(name)); > > + } > > + > > public void setHost(Host host) { > > this.host=host; > > } > > @@ -150,6 +164,22 @@ > > this.request.getConnection().recv(packet); > > return(this.read()); > > } > > + public String getX509Certificates() > > + throws IOException { > > + if (closed) throw new IOException("Stream closed"); > > + this.packet.reset(); > > + this.packet.setType(Constants.TYPE_ASK_SSL_CLIENT); > > + this.request.getConnection().send(packet); > > + packet.reset(); > > + > > + this.request.getConnection().recv(packet); > > + if (closed) throw new IOException("Stream closed"); > > + if (packet.getType()==Constants.TYPE_REP_SSL_NO) return(null); > > + if (packet.getType()!=Constants.TYPE_REP_SSL_CERT) > > + throw new IOException("Invalid WARP packet type for CC"); > > + return(this.packet.readString()); > > + } > > + > > > > public void close() > > throws IOException { > > Index: lib/pr_warp.c > > =================================================================== > > RCS file: /home/cvs/mirror/jakarta-tomcat-connectors/webapp/lib/pr_warp.c,v > > retrieving revision 1.16 > > diff -u -r1.16 pr_warp.c > > --- lib/pr_warp.c 2001/10/09 10:41:25 1.16 > > +++ lib/pr_warp.c 2001/10/18 15:16:08 > > @@ -428,6 +428,22 @@ > > } > > break; > > } > > + case TYPE_ASK_SSL_CLIENT: { > > + /* Request for client certificate */ > > + if (r->ssl_cert==NULL) { > > + pack->type=TYPE_REP_SSL_NO; > > + pack->size=0; > > + } else { > > + pack->type=TYPE_REP_SSL_CERT; > > + p_write_string(pack,r->ssl_cert); > > + } > > + wa_debug(WA_MARK,"CC bytes: (Sent=%d)",pack->size); > > + if (n_send(conf->sock,pack)!=wa_true) { > > + n_disconnect(conn); > > + return(wa_rerror(WA_MARK,r,500,"Communitcation > > interrupted")); > > + } > > + break; > > + } > > case TYPE_ERROR: { > > char *mesg=NULL; > > p_read_string(pack,&mesg); > > > > package org.apache.catalina.connector.warp; > > > > import java.security.cert.X509Certificate; > > import java.security.cert.CertificateFactory; > > > > import java.io.ByteArrayInputStream; > > > > /* > > * Certificates handling. > > */ > > > > public class WarpCertificates { > > X509Certificate jsseCerts[] = null; > > /** > > * Create the certificate using the String. > > */ > > public WarpCertificates(String certString) { > > byte[] certData = certString.getBytes(); > > ByteArrayInputStream bais = new ByteArrayInputStream(certData); > > > > // Fill the first element. > > try { > > CertificateFactory cf = > > CertificateFactory.getInstance("X.509"); > > X509Certificate cert = (X509Certificate) > > cf.generateCertificate(bais); > > jsseCerts = new X509Certificate[1]; > > jsseCerts[0] = cert; > > } catch(java.security.cert.CertificateException e) { > > // Certificate convertion failed. > > return; > > } > > } > > public X509Certificate [] getCertificates() { > > return jsseCerts; > > } > > } > >