SSL support for socket module for server sockets

Drew Csillag drew.csillag at starmedia.net
Fri Sep 22 16:26:15 EDT 2000


I don't think anybody has posted a patch for this, so I will.  The SSL
support in the socket module doesn't support server sockets (ones where
you call s.accept() on them).  This patch creates a function in the socket
module named sslserv which is analogous to the ssl function except this one
will work for server sockets.


*** /home/drew/build/Python-2.0b1/Modules/socketmodule.c	Wed Aug 16 10:18:30 2000
--- socketmodule.c	Fri Sep 22 16:25:24 2000
***************
*** 2045,2048 ****
--- 2045,2131 ----
  }
  
+ /* This is a C function to be called for new object initialization */
+ static SSLObject *
+ newServerSSLObject(PySocketSockObject *Sock, char *key_file, char *cert_file)
+ {
+ 	SSLObject *self;
+ 
+ 	self = PyObject_New(SSLObject, &SSL_Type); /* Create new object */
+ 	if (self == NULL){
+ 		PyErr_SetObject(SSLErrorObject,
+ 				PyString_FromString("newSSLObject error"));
+ 		return NULL;
+ 	}
+ 	memset(self->server, '\0', sizeof(char) * 256);
+ 	memset(self->issuer, '\0', sizeof(char) * 256);  
+   
+ 	self->x_attr = PyDict_New();
+ 	self->ctx = SSL_CTX_new(SSLv23_method()); /* Set up context */
+ 	if (self->ctx == NULL) {
+ 		PyErr_SetObject(SSLErrorObject,
+ 				PyString_FromString("SSL_CTX_new error"));
+ 		PyObject_Del(self);
+ 		return NULL;
+ 	}
+ 
+ 	if ( (key_file && !cert_file) || (!key_file && cert_file) )
+ 	{
+ 		PyErr_SetObject(SSLErrorObject,
+ 		      PyString_FromString(
+ 			"Both the key & certificate files must be specified"));
+ 		PyObject_Del(self);
+ 		return NULL;
+ 	}
+ 
+ 	if (key_file && cert_file)
+ 	{
+ 		if (SSL_CTX_use_PrivateKey_file(self->ctx, key_file,
+ 						SSL_FILETYPE_PEM) < 1)
+ 		{
+ 			PyErr_SetObject(SSLErrorObject,
+ 				PyString_FromString(
+ 				  "SSL_CTX_use_PrivateKey_file error"));
+ 			PyObject_Del(self);
+ 			return NULL;
+ 		}
+ 
+ 		if (SSL_CTX_use_certificate_chain_file(self->ctx,
+ 						       cert_file) < 1)
+ 		{
+ 			PyErr_SetObject(SSLErrorObject,
+ 				PyString_FromString(
+ 				  "SSL_CTX_use_certificate_chain_file error"));
+ 			PyObject_Del(self);
+ 			return NULL;
+ 		}
+ 	}
+ 
+ 	SSL_CTX_set_verify(self->ctx,
+ 			   SSL_VERIFY_NONE, NULL); /* set verify lvl */
+ 	self->ssl = SSL_new(self->ctx); /* New ssl struct */
+ 	SSL_set_fd(self->ssl, Sock->sock_fd);	/* Set the socket for SSL */
+ 	SSL_set_accept_state(self->ssl);
+ 
+ 	if ((SSL_accept(self->ssl)) == -1) {
+ 		/* Actually negotiate SSL connection */
+ 		PyErr_SetObject(SSLErrorObject,
+ 				PyString_FromString("SSL_accept error"));
+ 		PyObject_Del(self);
+ 		return NULL;
+ 	}
+ 	self->ssl->debug = 1;
+ 
+ 	if ((self->server_cert = SSL_get_peer_certificate(self->ssl))) {
+ 		X509_NAME_oneline(X509_get_subject_name(self->server_cert),
+ 				  self->server, 256);
+ 		X509_NAME_oneline(X509_get_issuer_name(self->server_cert),
+ 				  self->issuer, 256);
+ 	}
+ 	self->x_attr = NULL;
+ 	self->Socket = Sock;
+ 	Py_INCREF(self->Socket);
+ 	return self;
+ }
+ 
  /* This is the Python function called for new object initialization */
  static PyObject *
***************
*** 2068,2071 ****
--- 2151,2177 ----
  "ssl(socket, keyfile, certfile) -> sslobject";
  
+ /* This is the Python function called for new object initialization */
+ static PyObject *
+ PySocket_sslserv(PyObject *self, PyObject *args)
+ {
+ 	SSLObject *rv;
+ 	PySocketSockObject *Sock;
+ 	char *key_file;
+ 	char *cert_file;
+   
+ 	if (!PyArg_ParseTuple(args, "O!zz:ssl",
+ 			      &PySocketSock_Type, (PyObject*)&Sock,
+ 			      &key_file, &cert_file) )
+ 		return NULL;
+   
+ 	rv = newServerSSLObject(Sock, key_file, cert_file);
+ 	if ( rv == NULL )
+ 		return NULL;
+ 	return (PyObject *)rv;
+ }
+ 
+ static char sslserv_doc[] =
+ "sslserv(socket, keyfile, certfile) -> sslobject";
+ 
  static PyObject *
  SSL_server(SSLObject *self, PyObject *args)
***************
*** 2223,2226 ****
--- 2329,2334 ----
  	{"ssl",			PySocket_ssl, 
  	 METH_VARARGS, ssl_doc},
+ 	{"sslserv",			PySocket_sslserv, 
+ 	 METH_VARARGS, sslserv_doc},
  #endif /* USE_SSL */
  	{NULL,			NULL}		 /* Sentinel */

-- 
print'e=%s'%(lambda x:'%s.%s'%(x[0],x[1:-1]))(str(reduce(lambda
(a,b),y,z=10L**1835:(a+z/b,b*y),[[0L,1L]]+range(1,752))[0]))




More information about the Python-list mailing list