libfreerdp-core: start implement TSG OpenSSL BIO
authorMarc-André Moreau <marcandre.moreau@gmail.com>
Fri, 11 Oct 2013 10:12:50 +0000 (06:12 -0400)
committerDan Bungert <bungert@hp.com>
Thu, 24 Oct 2013 18:56:43 +0000 (12:56 -0600)
include/freerdp/crypto/tls.h
libfreerdp/core/transport.c
libfreerdp/core/transport.h
libfreerdp/crypto/tls.c

index 7e9aca9..a185973 100644 (file)
@@ -39,9 +39,12 @@ typedef struct rdp_tls rdpTls;
 struct rdp_tls
 {
        SSL* ssl;
+       BIO* bio;
+       void* tsg;
        int sockfd;
        SSL_CTX* ctx;
        BYTE* PublicKey;
+       BIO_METHOD* methods;
        DWORD PublicKeyLength;
        rdpSettings* settings;
        SecPkgContext_Bindings* Bindings;
index e06e928..fb3c013 100644 (file)
@@ -104,10 +104,114 @@ BOOL transport_connect_rdp(rdpTransport* transport)
        return TRUE;
 }
 
+static int transport_bio_tsg_write(BIO* bio, const char* buf, int num)
+{
+       printf("transport_bio_tsg_write: %d\n", num);
+
+       tsg_write((rdpTsg*) bio->ptr, (BYTE*) buf, num);
+       BIO_clear_retry_flags(bio);
+
+       return num;
+}
+
+static int transport_bio_tsg_read(BIO* bio, char* buf, int size)
+{
+       printf("transport_bio_tsg_read: %d\n", size);
+
+       BIO_clear_retry_flags(bio);
+
+       return 1;
+}
+
+static int transport_bio_tsg_puts(BIO* bio, const char* str)
+{
+       printf("transport_bio_tsg_puts: %d\n", strlen(str));
+       return 1;
+}
+
+static int transport_bio_tsg_gets(BIO* bio, char* str, int size)
+{
+       printf("transport_bio_tsg_gets: %d\n", size);
+       return 1;
+}
+
+static long transport_bio_tsg_ctrl(BIO* bio, int cmd, long arg1, void* arg2)
+{
+       printf("transport_bio_tsg_puts: cmd: %d arg1: %d arg2: %p\n", cmd, arg1, arg2);
+       return 1;
+}
+
+static int transport_bio_tsg_new(BIO* bio)
+{
+       printf("transport_bio_tsg_new\n");
+
+       bio->init = 1;
+       bio->num = 0;
+       bio->ptr = NULL;
+       bio->flags = 0;
+
+       return 1;
+}
+
+static int transport_bio_tsg_free(BIO* bio)
+{
+       printf("transport_bio_tsg_free\n");
+       return 1;
+}
+
+#define BIO_TYPE_TSG   65
+
+static BIO_METHOD transport_bio_tsg_methods =
+{
+       BIO_TYPE_TSG,
+       "TSGateway",
+       transport_bio_tsg_write,
+       transport_bio_tsg_read,
+       transport_bio_tsg_puts,
+       transport_bio_tsg_gets,
+       transport_bio_tsg_ctrl,
+       transport_bio_tsg_new,
+       transport_bio_tsg_free,
+       NULL,
+};
+
+BIO_METHOD* BIO_s_tsg(void)
+{
+       return &transport_bio_tsg_methods;
+}
+
 BOOL transport_connect_tls(rdpTransport* transport)
 {
        if (transport->layer == TRANSPORT_LAYER_TSG)
+       {
+               if (!transport->TlsIn)
+                       transport->TlsIn = tls_new(transport->settings);
+
+               if (!transport->TlsOut)
+                       transport->TlsOut = transport->TlsIn;
+
+               transport->TlsIn->methods = BIO_s_tsg();
+               transport->TlsIn->tsg = (void*) transport->tsg;
+
+               transport->layer = TRANSPORT_LAYER_TLS;
+
+               if (tls_connect(transport->TlsIn) != TRUE)
+               {
+                       if (!connectErrorCode)
+                               connectErrorCode = TLSCONNECTERROR;
+
+                       tls_free(transport->TlsIn);
+
+                       if (transport->TlsIn == transport->TlsOut)
+                               transport->TlsIn = transport->TlsOut = NULL;
+                       else
+                               transport->TlsIn = NULL;
+
+                       return FALSE;
+               }
+
                return TRUE;
+       }
 
        if (transport->TlsIn == NULL)
                transport->TlsIn = tls_new(transport->settings);
index bb573b6..821ab37 100644 (file)
@@ -25,6 +25,7 @@ typedef enum
        TRANSPORT_LAYER_TCP,
        TRANSPORT_LAYER_TLS,
        TRANSPORT_LAYER_TSG,
+       TRANSPORT_LAYER_TSG_TLS,
        TRANSPORT_LAYER_CLOSED
 } TRANSPORT_LAYER;
 
index 3e089e4..7b58645 100644 (file)
@@ -106,7 +106,7 @@ BOOL tls_connect(rdpTls* tls)
 
        tls->ctx = SSL_CTX_new(TLSv1_client_method());
 
-       if (tls->ctx == NULL)
+       if (!tls->ctx)
        {
                fprintf(stderr, "SSL_CTX_new failed\n");
                return FALSE;
@@ -147,16 +147,33 @@ BOOL tls_connect(rdpTls* tls)
 
        tls->ssl = SSL_new(tls->ctx);
 
-       if (tls->ssl == NULL)
+       if (!tls->ssl)
        {
                fprintf(stderr, "SSL_new failed\n");
                return FALSE;
        }
 
-       if (SSL_set_fd(tls->ssl, tls->sockfd) < 1)
+       if (tls->tsg)
        {
-               fprintf(stderr, "SSL_set_fd failed\n");
-               return FALSE;
+               tls->bio = BIO_new(tls->methods);
+
+               if (!tls->bio)
+               {
+                       fprintf(stderr, "BIO_new failed\n");
+                       return FALSE;
+               }
+
+               tls->bio->ptr = tls->tsg;
+
+               SSL_set_bio(tls->ssl, tls->bio, tls->bio);
+       }
+       else
+       {
+               if (SSL_set_fd(tls->ssl, tls->sockfd) < 1)
+               {
+                       fprintf(stderr, "SSL_set_fd failed\n");
+                       return FALSE;
+               }
        }
 
        connection_status = SSL_connect(tls->ssl);