Пример #1
0
BOOL tls_accept(rdpTls* tls, BIO *underlying, const char* cert_file, const char* privatekey_file)
{
	long options = 0;

	/**
	 * SSL_OP_NO_SSLv2:
	 *
	 * We only want SSLv3 and TLSv1, so disable SSLv2.
	 * SSLv3 is used by, eg. Microsoft RDC for Mac OS X.
	 */
	options |= SSL_OP_NO_SSLv2;

	/**
	 * SSL_OP_NO_COMPRESSION:
	 *
	 * The Microsoft RDP server does not advertise support
	 * for TLS compression, but alternative servers may support it.
	 * This was observed between early versions of the FreeRDP server
	 * and the FreeRDP client, and caused major performance issues,
	 * which is why we're disabling it.
	 */
#ifdef SSL_OP_NO_COMPRESSION
	options |= SSL_OP_NO_COMPRESSION;
#endif
	 
	/**
	 * SSL_OP_TLS_BLOCK_PADDING_BUG:
	 *
	 * The Microsoft RDP server does *not* support TLS padding.
	 * It absolutely needs to be disabled otherwise it won't work.
	 */
	options |= SSL_OP_TLS_BLOCK_PADDING_BUG;

	/**
	 * SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS:
	 *
	 * Just like TLS padding, the Microsoft RDP server does not
	 * support empty fragments. This needs to be disabled.
	 */
	options |= SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS;

	if (!tls_prepare(tls, underlying, SSLv23_server_method(), options, FALSE))
		return FALSE;

	if (SSL_use_RSAPrivateKey_file(tls->ssl, privatekey_file, SSL_FILETYPE_PEM) <= 0)
	{
		DEBUG_WARN( "%s: SSL_CTX_use_RSAPrivateKey_file failed\n", __FUNCTION__);
		DEBUG_WARN( "PrivateKeyFile: %s\n", privatekey_file);
		return FALSE;
	}

	if (SSL_use_certificate_file(tls->ssl, cert_file, SSL_FILETYPE_PEM) <= 0)
	{
		DEBUG_WARN( "%s: SSL_use_certificate_file failed\n", __FUNCTION__);
		return FALSE;
	}

	return tls_do_handshake(tls, FALSE) > 0;
}
Пример #2
0
int tls_connect(rdpTls* tls, BIO* underlying)
{
	int options = 0;

	/**
	 * SSL_OP_NO_COMPRESSION:
	 *
	 * The Microsoft RDP server does not advertise support
	 * for TLS compression, but alternative servers may support it.
	 * This was observed between early versions of the FreeRDP server
	 * and the FreeRDP client, and caused major performance issues,
	 * which is why we're disabling it.
	 */
#ifdef SSL_OP_NO_COMPRESSION
	options |= SSL_OP_NO_COMPRESSION;
#endif

	/**
	 * SSL_OP_TLS_BLOCK_PADDING_BUG:
	 *
	 * The Microsoft RDP server does *not* support TLS padding.
	 * It absolutely needs to be disabled otherwise it won't work.
	 */
	options |= SSL_OP_TLS_BLOCK_PADDING_BUG;

	/**
	 * SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS:
	 *
	 * Just like TLS padding, the Microsoft RDP server does not
	 * support empty fragments. This needs to be disabled.
	 */
	options |= SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS;

	/**
	 * disable SSLv2 and SSLv3
	 */
	options |= SSL_OP_NO_SSLv2;
	options |= SSL_OP_NO_SSLv3;

	if (!tls_prepare(tls, underlying, SSLv23_client_method(), options, TRUE))
		return FALSE;

#ifndef OPENSSL_NO_TLSEXT
	SSL_set_tlsext_host_name(tls->ssl, tls->hostname);
#endif

	return tls_do_handshake(tls, TRUE);
}
Пример #3
0
BOOL tls_accept(rdpTls* tls, BIO* underlying, rdpSettings* settings)
{
	long options = 0;
	BIO* bio;
	RSA* rsa;
	X509* x509;
	/**
	 * SSL_OP_NO_SSLv2:
	 *
	 * We only want SSLv3 and TLSv1, so disable SSLv2.
	 * SSLv3 is used by, eg. Microsoft RDC for Mac OS X.
	 */
	options |= SSL_OP_NO_SSLv2;
	/**
	 * SSL_OP_NO_COMPRESSION:
	 *
	 * The Microsoft RDP server does not advertise support
	 * for TLS compression, but alternative servers may support it.
	 * This was observed between early versions of the FreeRDP server
	 * and the FreeRDP client, and caused major performance issues,
	 * which is why we're disabling it.
	 */
#ifdef SSL_OP_NO_COMPRESSION
	options |= SSL_OP_NO_COMPRESSION;
#endif
	/**
	 * SSL_OP_TLS_BLOCK_PADDING_BUG:
	 *
	 * The Microsoft RDP server does *not* support TLS padding.
	 * It absolutely needs to be disabled otherwise it won't work.
	 */
	options |= SSL_OP_TLS_BLOCK_PADDING_BUG;
	/**
	 * SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS:
	 *
	 * Just like TLS padding, the Microsoft RDP server does not
	 * support empty fragments. This needs to be disabled.
	 */
	options |= SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS;

	if (!tls_prepare(tls, underlying, SSLv23_server_method(), options, FALSE))
		return FALSE;

	if (settings->PrivateKeyFile)
	{
		bio = BIO_new_file(settings->PrivateKeyFile, "rb");

		if (!bio)
		{
			WLog_ERR(TAG, "BIO_new_file failed for private key %s",
			         settings->PrivateKeyFile);
			return FALSE;
		}
	}
	else if (settings->PrivateKeyContent)
	{
		bio = BIO_new_mem_buf(settings->PrivateKeyContent,
		                      strlen(settings->PrivateKeyContent));

		if (!bio)
		{
			WLog_ERR(TAG, "BIO_new_mem_buf failed for private key");
			return FALSE;
		}
	}
	else
	{
		WLog_ERR(TAG, "no private key defined");
		return FALSE;
	}

	rsa = PEM_read_bio_RSAPrivateKey(bio, NULL, NULL, NULL);
	BIO_free(bio);

	if (!rsa)
	{
		WLog_ERR(TAG, "invalid private key");
		return FALSE;
	}

	if (SSL_use_RSAPrivateKey(tls->ssl, rsa) <= 0)
	{
		WLog_ERR(TAG, "SSL_CTX_use_RSAPrivateKey_file failed");
		RSA_free(rsa);
		return FALSE;
	}

	if (settings->CertificateFile)
	{
		bio = BIO_new_file(settings->CertificateFile, "rb");

		if (!bio)
		{
			WLog_ERR(TAG, "BIO_new_file failed for certificate %s",
			         settings->CertificateFile);
			return FALSE;
		}
	}
	else if (settings->CertificateContent)
	{
		bio = BIO_new_mem_buf(settings->CertificateContent,
		                      strlen(settings->CertificateContent));

		if (!bio)
		{
			WLog_ERR(TAG, "BIO_new_mem_buf failed for certificate");
			return FALSE;
		}
	}
	else
	{
		WLog_ERR(TAG, "no certificate defined");
		return FALSE;
	}

	x509 = PEM_read_bio_X509(bio, NULL, NULL, 0);
	BIO_free(bio);

	if (!x509)
	{
		WLog_ERR(TAG, "invalid certificate");
		return FALSE;
	}

	if (SSL_use_certificate(tls->ssl, x509) <= 0)
	{
		WLog_ERR(TAG, "SSL_use_certificate_file failed");
		X509_free(x509);
		return FALSE;
	}

#if defined(MICROSOFT_IOS_SNI_BUG) && !defined(OPENSSL_NO_TLSEXT)
	SSL_set_tlsext_debug_callback(tls->ssl, tls_openssl_tlsext_debug_callback);
#endif
	return tls_do_handshake(tls, FALSE) > 0;
}
Пример #4
0
/*-------------------------------------------------------------------------*/
int
tls_continue_handshake (interactive_t *ip)

/* Continue the TLS initialisation handshake for interactive <ip>.
 * Return a negative error code if the connection can not be set up.
 * Return 0 if the connection is still begin set up.
 * Return 1 if the connection is now active (or if no secure connection
 * had been requested).
 *
 * If a callback is set for <ip> and connection comes out of the handshaking
 * state, it will be called with the result code.
 */

{
    int ret;

    if (ip->tls_status != TLS_HANDSHAKING)
        return 1;

    ret = tls_do_handshake(ip);
    if (!ret)
	return 0;


    if (ret < 0)
    {
        ip->tls_status = TLS_INACTIVE;
    }
    else
    {
        ip->tls_status = TLS_ACTIVE;
    }

    /* If the connection is no longer in handshake, execute the callback */
    if (ip->tls_cb != NULL)
    {
        tls_cb_handler_t * handler;

        xallocate( handler, sizeof(*handler)
                 , "TLS: Callback handler protector");
        handler->cb = ip->tls_cb;
        ip->tls_cb = NULL;
            /* Protect the callback during its execution. */

        push_error_handler (handle_tls_cb_error, &(handler->head));

        push_number(inter_sp, ret < 0 ? ret : 0);
        push_ref_object(inter_sp, ip->ob, "tls_handshake");

        command_giver = ip->ob;
        current_interactive = ip->ob;
        /* Set current_interactive as it would be for a normal logon() call. */

        (void)apply_callback(handler->cb, 2);

        if (!(ip->ob->flags & O_DESTRUCTED))
            print_prompt();

        command_giver = NULL;

        free_svalue(inter_sp); inter_sp--; /* free the callback */
    }

    return ret;
} /* tls_continue_handshake() */
Пример #5
0
BOOL tls_accept(rdpTls* tls, BIO* underlying, rdpSettings* settings)
{
	long options = 0;
	BIO* bio;
	RSA* rsa;
	X509* x509;
	/**
	 * SSL_OP_NO_SSLv2:
	 *
	 * We only want SSLv3 and TLSv1, so disable SSLv2.
	 * SSLv3 is used by, eg. Microsoft RDC for Mac OS X.
	 */
	options |= SSL_OP_NO_SSLv2;
	/**
	 * SSL_OP_NO_COMPRESSION:
	 *
	 * The Microsoft RDP server does not advertise support
	 * for TLS compression, but alternative servers may support it.
	 * This was observed between early versions of the FreeRDP server
	 * and the FreeRDP client, and caused major performance issues,
	 * which is why we're disabling it.
	 */
#ifdef SSL_OP_NO_COMPRESSION
	options |= SSL_OP_NO_COMPRESSION;
#endif
	/**
	 * SSL_OP_TLS_BLOCK_PADDING_BUG:
	 *
	 * The Microsoft RDP server does *not* support TLS padding.
	 * It absolutely needs to be disabled otherwise it won't work.
	 */
	options |= SSL_OP_TLS_BLOCK_PADDING_BUG;
	/**
	 * SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS:
	 *
	 * Just like TLS padding, the Microsoft RDP server does not
	 * support empty fragments. This needs to be disabled.
	 */
	options |= SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS;

	if (!tls_prepare(tls, underlying, SSLv23_server_method(), options, FALSE))
		return FALSE;

	if (settings->PrivateKeyFile)
	{
		bio = BIO_new_file(settings->PrivateKeyFile, "rb+");

		if (!bio)
		{
			WLog_ERR(TAG, "BIO_new_file failed for private key %s",
			         settings->PrivateKeyFile);
			return FALSE;
		}
	}
	else if (settings->PrivateKeyContent)
	{
		bio = BIO_new_mem_buf(settings->PrivateKeyContent,
		                      strlen(settings->PrivateKeyContent));

		if (!bio)
		{
			WLog_ERR(TAG, "BIO_new_mem_buf failed for private key");
			return FALSE;
		}
	}
	else
	{
		WLog_ERR(TAG, "no private key defined");
		return FALSE;
	}

	rsa = PEM_read_bio_RSAPrivateKey(bio, NULL, NULL, NULL);
	BIO_free(bio);

	if (!rsa)
	{
		WLog_ERR(TAG, "invalid private key");
		return FALSE;
	}

	if (SSL_use_RSAPrivateKey(tls->ssl, rsa) <= 0)
	{
		WLog_ERR(TAG, "SSL_CTX_use_RSAPrivateKey_file failed");
		RSA_free(rsa);
		return FALSE;
	}

	if (settings->CertificateFile)
	{
		bio = BIO_new_file(settings->CertificateFile, "rb+");

		if (!bio)
		{
			WLog_ERR(TAG, "BIO_new_file failed for certificate %s",
			         settings->CertificateFile);
			return FALSE;
		}
	}
	else if (settings->CertificateContent)
	{
		bio = BIO_new_mem_buf(settings->CertificateContent,
		                      strlen(settings->CertificateContent));

		if (!bio)
		{
			WLog_ERR(TAG, "BIO_new_mem_buf failed for certificate");
			return FALSE;
		}
	}
	else
	{
		WLog_ERR(TAG, "no certificate defined");
		return FALSE;
	}

	x509 = PEM_read_bio_X509(bio, NULL, NULL, 0);
	BIO_free(bio);

	if (!x509)
	{
		WLog_ERR(TAG, "invalid certificate");
		return FALSE;
	}

	if (SSL_use_certificate(tls->ssl, x509) <= 0)
	{
		WLog_ERR(TAG, "SSL_use_certificate_file failed");
		X509_free(x509);
		return FALSE;
	}

#ifndef OPENSSL_NO_TLSEXT
	/**
	 * The Microsoft iOS clients eventually send a null or even double null
	 * terminated hostname in the SNI TLS extension!
	 * If the length indicator does not equal the hostname strlen OpenSSL
	 * will abort (see openssl:ssl/t1_lib.c).
	 * Here is a tcpdump segment of Microsoft Remote Desktop Client Version
	 * 8.1.7 running on an iPhone 4 with iOS 7.1.2 showing the transmitted
	 * SNI hostname TLV blob when connection to server "abcd":
	 * 00                  name_type 0x00 (host_name)
	 * 00 06               length_in_bytes 0x0006
	 * 61 62 63 64 00 00   host_name "abcd\0\0"
	 *
	 * Currently the only (runtime) workaround is setting an openssl tls
	 * extension debug callback that sets the SSL context's servername_done
	 * to 1 which effectively disables the parsing of that extension type.
	 */
	SSL_set_tlsext_debug_callback(tls->ssl, tls_openssl_tlsext_debug_callback);
#endif
	return tls_do_handshake(tls, FALSE) > 0;
}